diff options
author | Argyrios Kyrtzidis <akyrtzi@gmail.com> | 2010-08-20 23:31:11 +0000 |
---|---|---|
committer | Argyrios Kyrtzidis <akyrtzi@gmail.com> | 2010-08-20 23:31:11 +0000 |
commit | f08b1bb341fde5c755ec3dbe7e1b3114fb7438db (patch) | |
tree | f68b633d6a0e6ca509ab9fd9e6da7f61ff14575d /include/clang/Basic/OnDiskHashTable.h | |
parent | 4b6e6567f778133e25ec21e98e3e7e93d2c81e6a (diff) |
Add an iterator to OnDiskChainedHashTable to allow iterating over all the key/data pairs.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@111697 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'include/clang/Basic/OnDiskHashTable.h')
-rw-r--r-- | include/clang/Basic/OnDiskHashTable.h | 65 |
1 files changed, 65 insertions, 0 deletions
diff --git a/include/clang/Basic/OnDiskHashTable.h b/include/clang/Basic/OnDiskHashTable.h index aa3f344a6a..8909e47146 100644 --- a/include/clang/Basic/OnDiskHashTable.h +++ b/include/clang/Basic/OnDiskHashTable.h @@ -334,6 +334,71 @@ public: iterator end() const { return iterator(); } + /// \brief Iterates over all the entries in the table, returning + /// a key/data pair. + class item_iterator { + const unsigned char* Ptr; + unsigned NumItemsInBucketLeft; + unsigned NumEntriesLeft; + Info *InfoObj; + public: + typedef std::pair<external_key_type, data_type> value_type; + + item_iterator(const unsigned char* const Ptr, unsigned NumEntries, + Info *InfoObj) + : Ptr(Ptr), NumItemsInBucketLeft(0), NumEntriesLeft(NumEntries), + InfoObj(InfoObj) { } + item_iterator() + : Ptr(0), NumItemsInBucketLeft(0), NumEntriesLeft(0), InfoObj(0) { } + + bool operator==(const item_iterator& X) const { + return X.NumEntriesLeft == NumEntriesLeft; + } + bool operator!=(const item_iterator& X) const { + return X.NumEntriesLeft != NumEntriesLeft; + } + + item_iterator& operator++() { // Preincrement + if (!NumItemsInBucketLeft) { + // 'Items' starts with a 16-bit unsigned integer representing the + // number of items in this bucket. + NumItemsInBucketLeft = io::ReadUnalignedLE16(Ptr); + } + Ptr += 4; // Skip the hash. + // Determine the length of the key and the data. + const std::pair<unsigned, unsigned>& L = Info::ReadKeyDataLength(Ptr); + Ptr += L.first + L.second; + assert(NumItemsInBucketLeft); + --NumItemsInBucketLeft; + assert(NumEntriesLeft); + --NumEntriesLeft; + return *this; + } + item_iterator operator++(int) { // Postincrement + item_iterator tmp = *this; ++*this; return tmp; + } + + value_type operator*() const { + const unsigned char* LocalPtr = Ptr; + if (!NumItemsInBucketLeft) + LocalPtr += 2; // number of items in bucket + LocalPtr += 4; // Skip the hash. + + // Determine the length of the key and the data. + const std::pair<unsigned, unsigned>& L = Info::ReadKeyDataLength(LocalPtr); + + // Read the key. + const internal_key_type& Key = + InfoObj->ReadKey(LocalPtr, L.first); + return std::make_pair(InfoObj->GetExternalKey(Key), + InfoObj->ReadData(Key, LocalPtr + L.first, L.second)); + } + }; + + item_iterator item_begin() { + return item_iterator(Base + 4, getNumEntries(), &InfoObj); + } + item_iterator item_end() { return item_iterator(); } static OnDiskChainedHashTable* Create(const unsigned char* buckets, const unsigned char* const base, |