aboutsummaryrefslogtreecommitdiffstats
path: root/lib/Bitcode
diff options
context:
space:
mode:
authorTed Kremenek <kremenek@apple.com>2007-10-28 21:17:59 +0000
committerTed Kremenek <kremenek@apple.com>2007-10-28 21:17:59 +0000
commit5973ef40ca290903e0b3a4952162c14b55af5d72 (patch)
treecdf6969c92acad8154ce83c273b947944a9ad824 /lib/Bitcode
parentdc84650679b6330e0fcdd4cf8bc2a351387db7ca (diff)
downloadexternal_llvm-5973ef40ca290903e0b3a4952162c14b55af5d72.zip
external_llvm-5973ef40ca290903e0b3a4952162c14b55af5d72.tar.gz
external_llvm-5973ef40ca290903e0b3a4952162c14b55af5d72.tar.bz2
Updated backpatching logic during object deserialization to perform
eager backpatching instead of waithing until all objects have been deserialized. This allows us to reduce the memory footprint needed for backpatching. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@43422 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Bitcode')
-rw-r--r--lib/Bitcode/Reader/Deserialize.cpp62
1 files changed, 38 insertions, 24 deletions
diff --git a/lib/Bitcode/Reader/Deserialize.cpp b/lib/Bitcode/Reader/Deserialize.cpp
index 66df46e..9caef6d 100644
--- a/lib/Bitcode/Reader/Deserialize.cpp
+++ b/lib/Bitcode/Reader/Deserialize.cpp
@@ -16,14 +16,14 @@
using namespace llvm;
Deserializer::Deserializer(BitstreamReader& stream)
- : Stream(stream), RecIdx(0) {
+ : Stream(stream), RecIdx(0), FreeList(NULL) {
}
Deserializer::~Deserializer() {
assert (RecIdx >= Record.size() &&
"Still scanning bitcode record when deserialization completed.");
- BackpatchPointers();
+ assert (FreeList == NULL && "Some pointers were not backpatched.");
}
@@ -96,11 +96,11 @@ void Deserializer::ReadCStr(std::vector<char>& buff, bool isNullTerm) {
void Deserializer::RegisterPtr(unsigned PtrId,void* Ptr) {
BPatchEntry& E = BPatchMap[PtrId];
- assert (E.Ptr == NULL && "Pointer already registered.");
- E.Ptr = Ptr;
+ assert (E.hasFinalPtr() && "Pointer already registered.");
+ E.setFinalPtr(FreeList,Ptr);
}
-void Deserializer::ReadPtr(void*& PtrRef) {
+void Deserializer::ReadUIntPtr(uintptr_t& PtrRef) {
unsigned PtrId = ReadInt();
if (PtrId == 0) {
@@ -110,32 +110,46 @@ void Deserializer::ReadPtr(void*& PtrRef) {
BPatchEntry& E = BPatchMap[PtrId];
- if (E.Ptr == NULL) {
- // Register backpatch.
- void* P = Allocator.Allocate<BPatchNode>();
- E.Head = new (P) BPatchNode(E.Head,PtrRef);
+ if (E.hasFinalPtr())
+ PtrRef = E.getRawPtr();
+ else {
+ // Register backpatch. Check the freelist for a BPNode.
+ BPNode* N;
+
+ if (FreeList) {
+ N = FreeList;
+ FreeList = FreeList->Next;
+ }
+ else // No available BPNode. Allocate one.
+ N = (BPNode*) Allocator.Allocate<BPNode>();
+
+ new (N) BPNode(E.getBPNode(),PtrRef);
+ E.setBPNode(N);
}
- else
- PtrRef = E.Ptr;
}
-void Deserializer::BackpatchPointers() {
- for (MapTy::iterator I=BPatchMap.begin(),E=BPatchMap.end(); I!=E; ++I) {
-
- BPatchEntry& Entry = I->second;
- assert (Entry.Ptr && "No pointer found for backpatch.");
-
- for (BPatchNode* N = Entry.Head; N != NULL; N = N->Next)
- // Bitwise-OR in the pointer to support "smart" pointers that use
- // unused bits to store extra data.
- N->PtrRef |= reinterpret_cast<uintptr_t>(Entry.Ptr);
-
- Entry.Head = NULL;
+
+void Deserializer::BPatchEntry::setFinalPtr(BPNode*& FreeList, void* P) {
+ assert (!hasFinalPtr());
+
+ // Perform backpatching.
+
+ BPNode* Last = NULL;
+
+ for (BPNode* N = getBPNode() ; N != NULL; N = N->Next) {
+ Last = N;
+ N->PtrRef |= reinterpret_cast<uintptr_t>(P);
}
- Allocator.Reset();
+ if (Last) {
+ Last->Next = FreeList;
+ FreeList = getBPNode();
+ }
+
+ Ptr = reinterpret_cast<uintptr_t>(P);
}
+
#define INT_READ(TYPE)\
void SerializeTrait<TYPE>::Read(Deserializer& D, TYPE& X) {\
X = (TYPE) D.ReadInt(); }\