unsigned Raw;
public:
- BPKey(unsigned PtrId) : Raw(PtrId << 1) { assert (PtrId > 0); }
+ BPKey(SerializedPtrID PtrId) : Raw(PtrId << 1) { assert (PtrId > 0); }
BPKey(unsigned code, unsigned) : Raw(code) {}
void MarkFinal() { Raw |= 0x1; }
bool hasFinalPtr() const { return Raw & 0x1 ? true : false; }
- unsigned getID() const { return Raw >> 1; }
+ SerializedPtrID getID() const { return Raw >> 1; }
static inline BPKey getEmptyKey() { return BPKey(0,0); }
static inline BPKey getTombstoneKey() { return BPKey(1,0); }
typedef llvm::DenseMap<BPKey,BPEntry,BPKey,BPEntry> MapTy;
//===----------------------------------------------------------===//
- // Internal data members.
+ // Publicly visible types.
//===----------------------------------------------------------===//
+public:
+ typedef uint64_t Location;
+
+ //===----------------------------------------------------------===//
+ // Internal data members.
+ //===----------------------------------------------------------===//
+
+private:
BitstreamReader& Stream;
SmallVector<uint64_t,10> Record;
unsigned RecIdx;
BumpPtrAllocator Allocator;
BPNode* FreeList;
- MapTy BPatchMap;
+ MapTy BPatchMap;
+ llvm::SmallVector<uint64_t,5> BlockLocs;
//===----------------------------------------------------------===//
// Public Interface.
//===----------------------------------------------------------===//
-public:
+public:
Deserializer(BitstreamReader& stream);
~Deserializer();
uint64_t ReadInt();
int64_t ReadSInt();
+ SerializedPtrID ReadPtrID() { return (SerializedPtrID) ReadInt(); }
+
bool ReadBool() {
return ReadInt() ? true : false;
template <typename T>
inline T* ReadOwnedPtr(bool AutoRegister = true) {
- unsigned PtrID = ReadInt();
+ SerializedPtrID PtrID = ReadPtrID();
if (!PtrID)
return NULL;
void BatchReadOwnedPtrs(T1*& P1, T2*& P2,
bool A1=true, bool A2=true) {
- unsigned ID1 = ReadInt();
- unsigned ID2 = ReadInt();
+ SerializedPtrID ID1 = ReadPtrID();
+ SerializedPtrID ID2 = ReadPtrID();
P1 = (ID1) ? SerializeTrait<T1>::Materialize(*this) : NULL;
if (ID1 && A1) RegisterPtr(ID1,P1);
void BatchReadOwnedPtrs(T1*& P1, T2*& P2, T3*& P3,
bool A1=true, bool A2=true, bool A3=true) {
- unsigned ID1 = ReadInt();
- unsigned ID2 = ReadInt();
- unsigned ID3 = ReadInt();
+ SerializedPtrID ID1 = ReadPtrID();
+ SerializedPtrID ID2 = ReadPtrID();
+ SerializedPtrID ID3 = ReadPtrID();
P1 = (ID1) ? SerializeTrait<T1>::Materialize(*this) : NULL;
if (ID1 && A1) RegisterPtr(ID1,P1);
template <typename T>
void BatchReadOwnedPtrs(unsigned NumPtrs, T** Ptrs, bool AutoRegister=true) {
for (unsigned i = 0; i < NumPtrs; ++i)
- reinterpret_cast<uintptr_t&>(Ptrs[i]) = ReadInt();
+ reinterpret_cast<SerializedPtrID&>(Ptrs[i]) = ReadPtrID();
for (unsigned i = 0; i < NumPtrs; ++i) {
- unsigned PtrID = reinterpret_cast<uintptr_t>(Ptrs[i]);
+ SerializedPtrID PtrID = reinterpret_cast<SerializedPtrID>(Ptrs[i]);
T* p = PtrID ? SerializeTrait<T>::Materialize(*this) : NULL;
if (PtrID && AutoRegister)
return *p;
}
- void RegisterPtr(unsigned PtrId, const void* Ptr);
+ void RegisterPtr(SerializedPtrID PtrId, const void* Ptr);
void RegisterPtr(const void* Ptr) {
- RegisterPtr(ReadInt(),Ptr);
+ RegisterPtr(ReadPtrID(),Ptr);
+ }
+
+ template<typename T>
+ void RegisterRef(const T& x) {
+ RegisterPtr(&x);
}
+ template<typename T>
+ void RegisterRef(SerializedPtrID PtrID, const T& x) {
+ RegisterPtr(PtrID,&x);
+ }
+
+ Location GetCurrentBlockLocation();
+ bool FinishedBlock(Location BlockLoc);
+
bool AtEnd();
-
bool inRecord();
+
private:
void ReadRecord();
uintptr_t ReadInternalRefPtr();
Code = Stream.ReadCode();
if (Code == bitc::ENTER_SUBBLOCK) {
- // No known subblocks, always skip them.
+ BlockLocs.push_back(Stream.GetCurrentBitNo());
unsigned id = Stream.ReadSubBlockID();
Stream.EnterSubBlock(id);
continue;
}
- if (Code == bitc::END_BLOCK) {
+ if (Code == bitc::END_BLOCK) {
bool x = Stream.ReadBlockEnd();
assert (!x && "Error at block end.");
+ BlockLocs.pop_back();
continue;
}
assert (Record.size() > 0 || Stream.AtEndOfStream());
}
+Deserializer::Location Deserializer::GetCurrentBlockLocation() {
+ if (!inRecord())
+ ReadRecord();
+
+ assert (!BlockLocs.empty());
+ return BlockLocs.back();
+}
+
+bool Deserializer::FinishedBlock(Location BlockLoc) {
+ if (!inRecord())
+ ReadRecord();
+
+ for (llvm::SmallVector<Location,5>::reverse_iterator
+ I=BlockLocs.rbegin(), E=BlockLocs.rend(); I!=E; ++I)
+ if (*I == BlockLoc)
+ return false;
+
+ return true;
+}
+
bool Deserializer::AtEnd() {
if (inRecord())
return false;
}
void Deserializer::ReadUIntPtr(uintptr_t& PtrRef, bool AllowBackpatch) {
- unsigned PtrId = ReadInt();
+ SerializedPtrID PtrId = ReadPtrID();
if (PtrId == 0) {
PtrRef = 0;
}
uintptr_t Deserializer::ReadInternalRefPtr() {
- unsigned PtrId = ReadInt();
+ SerializedPtrID PtrId = ReadPtrID();
assert (PtrId != 0 && "References cannot refer the NULL address.");