]> git.saurik.com Git - apple/objc4.git/blob - runtime/llvm-DenseMap.h
objc4-532.2.tar.gz
[apple/objc4.git] / runtime / llvm-DenseMap.h
1 //===- llvm/ADT/DenseMap.h - Dense probed hash table ------------*- C++ -*-===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This file defines the DenseMap class.
11 //
12 //===----------------------------------------------------------------------===//
13
14 #ifndef LLVM_ADT_DENSEMAP_H
15 #define LLVM_ADT_DENSEMAP_H
16
17 #include "llvm-type_traits.h"
18 #include <algorithm>
19 #include <iterator>
20 #include <new>
21 #include <utility>
22 #include <cassert>
23 #include <cstddef>
24 #include <cstring>
25 #include <TargetConditionals.h>
26
27 namespace objc {
28
29 #if TARGET_OS_IPHONE
30
31 // lifted from <MathExtras.h>:
32
33 /// CountLeadingZeros_32 - this function performs the platform optimal form of
34 /// counting the number of zeros from the most significant bit to the first one
35 /// bit. Ex. CountLeadingZeros_32(0x00F000FF) == 8.
36 /// Returns 32 if the word is zero.
37 inline unsigned CountLeadingZeros_32(uint32_t Value) {
38 unsigned Count; // result
39 #if __GNUC__ >= 4
40 // PowerPC is defined for __builtin_clz(0)
41 #if !defined(__ppc__) && !defined(__ppc64__)
42 if (!Value) return 32;
43 #endif
44 Count = __builtin_clz(Value);
45 #else
46 if (!Value) return 32;
47 Count = 0;
48 // bisection method for count leading zeros
49 for (unsigned Shift = 32 >> 1; Shift; Shift >>= 1) {
50 uint32_t Tmp = Value >> Shift;
51 if (Tmp) {
52 Value = Tmp;
53 } else {
54 Count |= Shift;
55 }
56 }
57 #endif
58 return Count;
59 }
60 /// CountLeadingOnes_32 - this function performs the operation of
61 /// counting the number of ones from the most significant bit to the first zero
62 /// bit. Ex. CountLeadingOnes_32(0xFF0FFF00) == 8.
63 /// Returns 32 if the word is all ones.
64 inline unsigned CountLeadingOnes_32(uint32_t Value) {
65 return CountLeadingZeros_32(~Value);
66 }
67 /// CountLeadingZeros_64 - This function performs the platform optimal form
68 /// of counting the number of zeros from the most significant bit to the first
69 /// one bit (64 bit edition.)
70 /// Returns 64 if the word is zero.
71 inline unsigned CountLeadingZeros_64(uint64_t Value) {
72 unsigned Count; // result
73 #if __GNUC__ >= 4
74 // PowerPC is defined for __builtin_clzll(0)
75 #if !defined(__ppc__) && !defined(__ppc64__)
76 if (!Value) return 64;
77 #endif
78 Count = __builtin_clzll(Value);
79 #else
80 if (sizeof(long) == sizeof(int64_t)) {
81 if (!Value) return 64;
82 Count = 0;
83 // bisection method for count leading zeros
84 for (unsigned Shift = 64 >> 1; Shift; Shift >>= 1) {
85 uint64_t Tmp = Value >> Shift;
86 if (Tmp) {
87 Value = Tmp;
88 } else {
89 Count |= Shift;
90 }
91 }
92 } else {
93 // get hi portion
94 uint32_t Hi = Hi_32(Value);
95 // if some bits in hi portion
96 if (Hi) {
97 // leading zeros in hi portion plus all bits in lo portion
98 Count = CountLeadingZeros_32(Hi);
99 } else {
100 // get lo portion
101 uint32_t Lo = Lo_32(Value);
102 // same as 32 bit value
103 Count = CountLeadingZeros_32(Lo)+32;
104 }
105 }
106 #endif
107 return Count;
108 }
109 /// CountLeadingOnes_64 - This function performs the operation
110 /// of counting the number of ones from the most significant bit to the first
111 /// zero bit (64 bit edition.)
112 /// Returns 64 if the word is all ones.
113 inline unsigned CountLeadingOnes_64(uint64_t Value) {
114 return CountLeadingZeros_64(~Value);
115 }
116 /// CountTrailingZeros_32 - this function performs the platform optimal form of
117 /// counting the number of zeros from the least significant bit to the first one
118 /// bit. Ex. CountTrailingZeros_32(0xFF00FF00) == 8.
119 /// Returns 32 if the word is zero.
120 inline unsigned CountTrailingZeros_32(uint32_t Value) {
121 #if __GNUC__ >= 4
122 return Value ? __builtin_ctz(Value) : 32;
123 #else
124 static const unsigned Mod37BitPosition[] = {
125 32, 0, 1, 26, 2, 23, 27, 0, 3, 16, 24, 30, 28, 11, 0, 13,
126 4, 7, 17, 0, 25, 22, 31, 15, 29, 10, 12, 6, 0, 21, 14, 9,
127 5, 20, 8, 19, 18
128 };
129 return Mod37BitPosition[(-Value & Value) % 37];
130 #endif
131 }
132 /// CountTrailingOnes_32 - this function performs the operation of
133 /// counting the number of ones from the least significant bit to the first zero
134 /// bit. Ex. CountTrailingOnes_32(0x00FF00FF) == 8.
135 /// Returns 32 if the word is all ones.
136 inline unsigned CountTrailingOnes_32(uint32_t Value) {
137 return CountTrailingZeros_32(~Value);
138 }
139 /// CountTrailingZeros_64 - This function performs the platform optimal form
140 /// of counting the number of zeros from the least significant bit to the first
141 /// one bit (64 bit edition.)
142 /// Returns 64 if the word is zero.
143 inline unsigned CountTrailingZeros_64(uint64_t Value) {
144 #if __GNUC__ >= 4
145 return Value ? __builtin_ctzll(Value) : 64;
146 #else
147 static const unsigned Mod67Position[] = {
148 64, 0, 1, 39, 2, 15, 40, 23, 3, 12, 16, 59, 41, 19, 24, 54,
149 4, 64, 13, 10, 17, 62, 60, 28, 42, 30, 20, 51, 25, 44, 55,
150 47, 5, 32, 65, 38, 14, 22, 11, 58, 18, 53, 63, 9, 61, 27,
151 29, 50, 43, 46, 31, 37, 21, 57, 52, 8, 26, 49, 45, 36, 56,
152 7, 48, 35, 6, 34, 33, 0
153 };
154 return Mod67Position[(-Value & Value) % 67];
155 #endif
156 }
157
158 /// CountTrailingOnes_64 - This function performs the operation
159 /// of counting the number of ones from the least significant bit to the first
160 /// zero bit (64 bit edition.)
161 /// Returns 64 if the word is all ones.
162 inline unsigned CountTrailingOnes_64(uint64_t Value) {
163 return CountTrailingZeros_64(~Value);
164 }
165 /// CountPopulation_32 - this function counts the number of set bits in a value.
166 /// Ex. CountPopulation(0xF000F000) = 8
167 /// Returns 0 if the word is zero.
168 inline unsigned CountPopulation_32(uint32_t Value) {
169 #if __GNUC__ >= 4
170 return __builtin_popcount(Value);
171 #else
172 uint32_t v = Value - ((Value >> 1) & 0x55555555);
173 v = (v & 0x33333333) + ((v >> 2) & 0x33333333);
174 return ((v + (v >> 4) & 0xF0F0F0F) * 0x1010101) >> 24;
175 #endif
176 }
177 /// CountPopulation_64 - this function counts the number of set bits in a value,
178 /// (64 bit edition.)
179 inline unsigned CountPopulation_64(uint64_t Value) {
180 #if __GNUC__ >= 4
181 return __builtin_popcountll(Value);
182 #else
183 uint64_t v = Value - ((Value >> 1) & 0x5555555555555555ULL);
184 v = (v & 0x3333333333333333ULL) + ((v >> 2) & 0x3333333333333333ULL);
185 v = (v + (v >> 4)) & 0x0F0F0F0F0F0F0F0FULL;
186 return unsigned((uint64_t)(v * 0x0101010101010101ULL) >> 56);
187 #endif
188 }
189 /// Log2_32 - This function returns the floor log base 2 of the specified value,
190 /// -1 if the value is zero. (32 bit edition.)
191 /// Ex. Log2_32(32) == 5, Log2_32(1) == 0, Log2_32(0) == -1, Log2_32(6) == 2
192 inline unsigned Log2_32(uint32_t Value) {
193 return 31 - CountLeadingZeros_32(Value);
194 }
195 /// Log2_64 - This function returns the floor log base 2 of the specified value,
196 /// -1 if the value is zero. (64 bit edition.)
197 inline unsigned Log2_64(uint64_t Value) {
198 return 63 - CountLeadingZeros_64(Value);
199 }
200 /// Log2_32_Ceil - This function returns the ceil log base 2 of the specified
201 /// value, 32 if the value is zero. (32 bit edition).
202 /// Ex. Log2_32_Ceil(32) == 5, Log2_32_Ceil(1) == 0, Log2_32_Ceil(6) == 3
203 inline unsigned Log2_32_Ceil(uint32_t Value) {
204 return 32-CountLeadingZeros_32(Value-1);
205 }
206
207 #endif /* TARGET_OS_IPHONE */
208
209 template<typename T>
210 struct DenseMapInfo {
211 //static inline T getEmptyKey();
212 //static inline T getTombstoneKey();
213 //static unsigned getHashValue(const T &Val);
214 //static bool isEqual(const T &LHS, const T &RHS);
215 };
216
217 // Provide DenseMapInfo for all pointers.
218 template<typename T>
219 struct DenseMapInfo<T*> {
220 static inline T* getEmptyKey() {
221 intptr_t Val = -1;
222 return reinterpret_cast<T*>(Val);
223 }
224 static inline T* getTombstoneKey() {
225 intptr_t Val = -2;
226 return reinterpret_cast<T*>(Val);
227 }
228 static unsigned getHashValue(const T *PtrVal) {
229 return (unsigned((uintptr_t)PtrVal) >> 4) ^
230 (unsigned((uintptr_t)PtrVal) >> 9);
231 }
232 static bool isEqual(const T *LHS, const T *RHS) { return LHS == RHS; }
233 };
234
235 // Provide DenseMapInfo for chars.
236 template<> struct DenseMapInfo<char> {
237 static inline char getEmptyKey() { return ~0; }
238 static inline char getTombstoneKey() { return ~0 - 1; }
239 static unsigned getHashValue(const char& Val) { return Val * 37; }
240 static bool isEqual(const char &LHS, const char &RHS) {
241 return LHS == RHS;
242 }
243 };
244
245 // Provide DenseMapInfo for unsigned ints.
246 template<> struct DenseMapInfo<unsigned> {
247 static inline unsigned getEmptyKey() { return ~0; }
248 static inline unsigned getTombstoneKey() { return ~0U - 1; }
249 static unsigned getHashValue(const unsigned& Val) { return Val * 37; }
250 static bool isEqual(const unsigned& LHS, const unsigned& RHS) {
251 return LHS == RHS;
252 }
253 };
254
255 // Provide DenseMapInfo for unsigned longs.
256 template<> struct DenseMapInfo<unsigned long> {
257 static inline unsigned long getEmptyKey() { return ~0UL; }
258 static inline unsigned long getTombstoneKey() { return ~0UL - 1L; }
259 static unsigned getHashValue(const unsigned long& Val) {
260 return (unsigned)(Val * 37UL);
261 }
262 static bool isEqual(const unsigned long& LHS, const unsigned long& RHS) {
263 return LHS == RHS;
264 }
265 };
266
267 // Provide DenseMapInfo for unsigned long longs.
268 template<> struct DenseMapInfo<unsigned long long> {
269 static inline unsigned long long getEmptyKey() { return ~0ULL; }
270 static inline unsigned long long getTombstoneKey() { return ~0ULL - 1ULL; }
271 static unsigned getHashValue(const unsigned long long& Val) {
272 return (unsigned)(Val * 37ULL);
273 }
274 static bool isEqual(const unsigned long long& LHS,
275 const unsigned long long& RHS) {
276 return LHS == RHS;
277 }
278 };
279
280 // Provide DenseMapInfo for ints.
281 template<> struct DenseMapInfo<int> {
282 static inline int getEmptyKey() { return 0x7fffffff; }
283 static inline int getTombstoneKey() { return -0x7fffffff - 1; }
284 static unsigned getHashValue(const int& Val) { return (unsigned)(Val * 37); }
285 static bool isEqual(const int& LHS, const int& RHS) {
286 return LHS == RHS;
287 }
288 };
289
290 // Provide DenseMapInfo for longs.
291 template<> struct DenseMapInfo<long> {
292 static inline long getEmptyKey() {
293 return (1UL << (sizeof(long) * 8 - 1)) - 1L;
294 }
295 static inline long getTombstoneKey() { return getEmptyKey() - 1L; }
296 static unsigned getHashValue(const long& Val) {
297 return (unsigned)(Val * 37L);
298 }
299 static bool isEqual(const long& LHS, const long& RHS) {
300 return LHS == RHS;
301 }
302 };
303
304 // Provide DenseMapInfo for long longs.
305 template<> struct DenseMapInfo<long long> {
306 static inline long long getEmptyKey() { return 0x7fffffffffffffffLL; }
307 static inline long long getTombstoneKey() { return -0x7fffffffffffffffLL-1; }
308 static unsigned getHashValue(const long long& Val) {
309 return (unsigned)(Val * 37LL);
310 }
311 static bool isEqual(const long long& LHS,
312 const long long& RHS) {
313 return LHS == RHS;
314 }
315 };
316
317 // Provide DenseMapInfo for all pairs whose members have info.
318 template<typename T, typename U>
319 struct DenseMapInfo<std::pair<T, U> > {
320 typedef std::pair<T, U> Pair;
321 typedef DenseMapInfo<T> FirstInfo;
322 typedef DenseMapInfo<U> SecondInfo;
323
324 static inline Pair getEmptyKey() {
325 return std::make_pair(FirstInfo::getEmptyKey(),
326 SecondInfo::getEmptyKey());
327 }
328 static inline Pair getTombstoneKey() {
329 return std::make_pair(FirstInfo::getTombstoneKey(),
330 SecondInfo::getEmptyKey());
331 }
332 static unsigned getHashValue(const Pair& PairVal) {
333 uint64_t key = (uint64_t)FirstInfo::getHashValue(PairVal.first) << 32
334 | (uint64_t)SecondInfo::getHashValue(PairVal.second);
335 key += ~(key << 32);
336 key ^= (key >> 22);
337 key += ~(key << 13);
338 key ^= (key >> 8);
339 key += (key << 3);
340 key ^= (key >> 15);
341 key += ~(key << 27);
342 key ^= (key >> 31);
343 return (unsigned)key;
344 }
345 static bool isEqual(const Pair& LHS, const Pair& RHS) { return LHS == RHS; }
346 };
347
348 } // end namespace objc
349
350
351
352 namespace objc {
353
354 template<typename KeyT, typename ValueT,
355 typename KeyInfoT = DenseMapInfo<KeyT>,
356 typename ValueInfoT = DenseMapInfo<ValueT>, bool IsConst = false>
357 class DenseMapIterator;
358
359 // ZeroValuesArePurgeable=true is used by the refcount table.
360 // A key/value pair with value==0 is not required to be stored
361 // in the refcount table; it could correctly be erased instead.
362 // For performance, we do keep zero values in the table when the
363 // true refcount decreases to 1: this makes any future retain faster.
364 // For memory size, we allow rehashes and table insertions to
365 // remove a zero value as if it were a tombstone.
366
367 template<typename KeyT, typename ValueT,
368 bool ZeroValuesArePurgeable = false,
369 typename KeyInfoT = DenseMapInfo<KeyT>,
370 typename ValueInfoT = DenseMapInfo<ValueT> >
371 class DenseMap {
372 typedef std::pair<KeyT, ValueT> BucketT;
373 unsigned NumBuckets;
374 BucketT *Buckets;
375
376 unsigned NumEntries;
377 unsigned NumTombstones;
378 public:
379 typedef KeyT key_type;
380 typedef ValueT mapped_type;
381 typedef BucketT value_type;
382
383 DenseMap(const DenseMap &other) {
384 NumBuckets = 0;
385 CopyFrom(other);
386 }
387
388 explicit DenseMap(unsigned NumInitBuckets = 64) {
389 init(NumInitBuckets);
390 }
391
392 template<typename InputIt>
393 DenseMap(const InputIt &I, const InputIt &E) {
394 init(64);
395 insert(I, E);
396 }
397
398 ~DenseMap() {
399 const KeyT EmptyKey = getEmptyKey(), TombstoneKey = getTombstoneKey();
400 for (BucketT *P = Buckets, *E = Buckets+NumBuckets; P != E; ++P) {
401 if (!KeyInfoT::isEqual(P->first, EmptyKey) &&
402 !KeyInfoT::isEqual(P->first, TombstoneKey))
403 P->second.~ValueT();
404 P->first.~KeyT();
405 }
406 #ifndef NDEBUG
407 memset(Buckets, 0x5a, sizeof(BucketT)*NumBuckets);
408 #endif
409 operator delete(Buckets);
410 }
411
412 typedef DenseMapIterator<KeyT, ValueT, KeyInfoT> iterator;
413 typedef DenseMapIterator<KeyT, ValueT,
414 KeyInfoT, ValueInfoT, true> const_iterator;
415 inline iterator begin() {
416 // When the map is empty, avoid the overhead of AdvancePastEmptyBuckets().
417 return empty() ? end() : iterator(Buckets, Buckets+NumBuckets);
418 }
419 inline iterator end() {
420 return iterator(Buckets+NumBuckets, Buckets+NumBuckets);
421 }
422 inline const_iterator begin() const {
423 return empty() ? end() : const_iterator(Buckets, Buckets+NumBuckets);
424 }
425 inline const_iterator end() const {
426 return const_iterator(Buckets+NumBuckets, Buckets+NumBuckets);
427 }
428
429 bool empty() const { return NumEntries == 0; }
430 unsigned size() const { return NumEntries; }
431
432 /// Grow the densemap so that it has at least Size buckets. Does not shrink
433 void resize(size_t Size) { grow(Size); }
434
435 void clear() {
436 if (NumEntries == 0 && NumTombstones == 0) return;
437
438 // If the capacity of the array is huge, and the # elements used is small,
439 // shrink the array.
440 if (NumEntries * 4 < NumBuckets && NumBuckets > 64) {
441 shrink_and_clear();
442 return;
443 }
444
445 const KeyT EmptyKey = getEmptyKey(), TombstoneKey = getTombstoneKey();
446 for (BucketT *P = Buckets, *E = Buckets+NumBuckets; P != E; ++P) {
447 if (!KeyInfoT::isEqual(P->first, EmptyKey)) {
448 if (!KeyInfoT::isEqual(P->first, TombstoneKey)) {
449 P->second.~ValueT();
450 --NumEntries;
451 }
452 P->first = EmptyKey;
453 }
454 }
455 assert(NumEntries == 0 && "Node count imbalance!");
456 NumTombstones = 0;
457 }
458
459 /// count - Return true if the specified key is in the map.
460 bool count(const KeyT &Val) const {
461 BucketT *TheBucket;
462 return LookupBucketFor(Val, TheBucket);
463 }
464
465 iterator find(const KeyT &Val) {
466 BucketT *TheBucket;
467 if (LookupBucketFor(Val, TheBucket))
468 return iterator(TheBucket, Buckets+NumBuckets);
469 return end();
470 }
471 const_iterator find(const KeyT &Val) const {
472 BucketT *TheBucket;
473 if (LookupBucketFor(Val, TheBucket))
474 return const_iterator(TheBucket, Buckets+NumBuckets);
475 return end();
476 }
477
478 /// lookup - Return the entry for the specified key, or a default
479 /// constructed value if no such entry exists.
480 ValueT lookup(const KeyT &Val) const {
481 BucketT *TheBucket;
482 if (LookupBucketFor(Val, TheBucket))
483 return TheBucket->second;
484 return ValueT();
485 }
486
487 // Inserts key,value pair into the map if the key isn't already in the map.
488 // If the key is already in the map, it returns false and doesn't update the
489 // value.
490 std::pair<iterator, bool> insert(const std::pair<KeyT, ValueT> &KV) {
491 BucketT *TheBucket;
492 if (LookupBucketFor(KV.first, TheBucket))
493 return std::make_pair(iterator(TheBucket, Buckets+NumBuckets),
494 false); // Already in map.
495
496 // Otherwise, insert the new element.
497 TheBucket = InsertIntoBucket(KV.first, KV.second, TheBucket);
498 return std::make_pair(iterator(TheBucket, Buckets+NumBuckets),
499 true);
500 }
501
502 /// insert - Range insertion of pairs.
503 template<typename InputIt>
504 void insert(InputIt I, InputIt E) {
505 for (; I != E; ++I)
506 insert(*I);
507 }
508
509
510 bool erase(const KeyT &Val) {
511 BucketT *TheBucket;
512 if (!LookupBucketFor(Val, TheBucket))
513 return false; // not in map.
514
515 TheBucket->second.~ValueT();
516 TheBucket->first = getTombstoneKey();
517 --NumEntries;
518 ++NumTombstones;
519 return true;
520 }
521 void erase(iterator I) {
522 BucketT *TheBucket = &*I;
523 TheBucket->second.~ValueT();
524 TheBucket->first = getTombstoneKey();
525 --NumEntries;
526 ++NumTombstones;
527 }
528
529 void swap(DenseMap& RHS) {
530 std::swap(NumBuckets, RHS.NumBuckets);
531 std::swap(Buckets, RHS.Buckets);
532 std::swap(NumEntries, RHS.NumEntries);
533 std::swap(NumTombstones, RHS.NumTombstones);
534 }
535
536 value_type& FindAndConstruct(const KeyT &Key) {
537 BucketT *TheBucket;
538 if (LookupBucketFor(Key, TheBucket))
539 return *TheBucket;
540
541 return *InsertIntoBucket(Key, ValueT(), TheBucket);
542 }
543
544 ValueT &operator[](const KeyT &Key) {
545 return FindAndConstruct(Key).second;
546 }
547
548 DenseMap& operator=(const DenseMap& other) {
549 CopyFrom(other);
550 return *this;
551 }
552
553 /// isPointerIntoBucketsArray - Return true if the specified pointer points
554 /// somewhere into the DenseMap's array of buckets (i.e. either to a key or
555 /// value in the DenseMap).
556 bool isPointerIntoBucketsArray(const void *Ptr) const {
557 return Ptr >= Buckets && Ptr < Buckets+NumBuckets;
558 }
559
560 /// getPointerIntoBucketsArray() - Return an opaque pointer into the buckets
561 /// array. In conjunction with the previous method, this can be used to
562 /// determine whether an insertion caused the DenseMap to reallocate.
563 const void *getPointerIntoBucketsArray() const { return Buckets; }
564
565 private:
566 void CopyFrom(const DenseMap& other) {
567 if (NumBuckets != 0 &&
568 (!isPodLike<KeyInfoT>::value || !isPodLike<ValueInfoT>::value)) {
569 const KeyT EmptyKey = getEmptyKey(), TombstoneKey = getTombstoneKey();
570 for (BucketT *P = Buckets, *E = Buckets+NumBuckets; P != E; ++P) {
571 if (!KeyInfoT::isEqual(P->first, EmptyKey) &&
572 !KeyInfoT::isEqual(P->first, TombstoneKey))
573 P->second.~ValueT();
574 P->first.~KeyT();
575 }
576 }
577
578 NumEntries = other.NumEntries;
579 NumTombstones = other.NumTombstones;
580
581 if (NumBuckets) {
582 #ifndef NDEBUG
583 memset(Buckets, 0x5a, sizeof(BucketT)*NumBuckets);
584 #endif
585 operator delete(Buckets);
586 }
587 Buckets = static_cast<BucketT*>(operator new(sizeof(BucketT) *
588 other.NumBuckets));
589
590 if (isPodLike<KeyInfoT>::value && isPodLike<ValueInfoT>::value)
591 memcpy(Buckets, other.Buckets, other.NumBuckets * sizeof(BucketT));
592 else
593 for (size_t i = 0; i < other.NumBuckets; ++i) {
594 new (&Buckets[i].first) KeyT(other.Buckets[i].first);
595 if (!KeyInfoT::isEqual(Buckets[i].first, getEmptyKey()) &&
596 !KeyInfoT::isEqual(Buckets[i].first, getTombstoneKey()))
597 new (&Buckets[i].second) ValueT(other.Buckets[i].second);
598 }
599 NumBuckets = other.NumBuckets;
600 }
601
602 BucketT *InsertIntoBucket(const KeyT &Key, const ValueT &Value,
603 BucketT *TheBucket) {
604 // If the load of the hash table is more than 3/4, grow the table.
605 // If fewer than 1/8 of the buckets are empty (meaning that many are
606 // filled with tombstones), rehash the table without growing.
607 //
608 // The later case is tricky. For example, if we had one empty bucket with
609 // tons of tombstones, failing lookups (e.g. for insertion) would have to
610 // probe almost the entire table until it found the empty bucket. If the
611 // table completely filled with tombstones, no lookup would ever succeed,
612 // causing infinite loops in lookup.
613 ++NumEntries;
614 if (NumEntries*4 >= NumBuckets*3) {
615 this->grow(NumBuckets * 2);
616 LookupBucketFor(Key, TheBucket);
617 }
618 else if (NumBuckets-(NumEntries+NumTombstones) < NumBuckets/8) {
619 this->grow(NumBuckets);
620 LookupBucketFor(Key, TheBucket);
621 }
622
623 // If we are writing over a tombstone or zero value, remember this.
624 if (!KeyInfoT::isEqual(TheBucket->first, getEmptyKey())) {
625 if (KeyInfoT::isEqual(TheBucket->first, getTombstoneKey())) {
626 --NumTombstones;
627 } else {
628 assert(ZeroValuesArePurgeable && TheBucket->second == 0);
629 TheBucket->second.~ValueT();
630 --NumEntries;
631 }
632 }
633
634 TheBucket->first = Key;
635 new (&TheBucket->second) ValueT(Value);
636 return TheBucket;
637 }
638
639 static unsigned getHashValue(const KeyT &Val) {
640 return KeyInfoT::getHashValue(Val);
641 }
642 static const KeyT getEmptyKey() {
643 return KeyInfoT::getEmptyKey();
644 }
645 static const KeyT getTombstoneKey() {
646 return KeyInfoT::getTombstoneKey();
647 }
648
649 /// LookupBucketFor - Lookup the appropriate bucket for Val, returning it in
650 /// FoundBucket. If the bucket contains the key and a value, this returns
651 /// true, otherwise it returns a bucket with an empty marker or tombstone
652 /// or zero value and returns false.
653 bool LookupBucketFor(const KeyT &Val, BucketT *&FoundBucket) const {
654 unsigned BucketNo = getHashValue(Val);
655 unsigned ProbeAmt = 1;
656 unsigned ProbeCount = 0;
657 BucketT *BucketsPtr = Buckets;
658
659 // FoundTombstone - Keep track of whether we find a tombstone or zero value while probing.
660 BucketT *FoundTombstone = 0;
661 const KeyT EmptyKey = getEmptyKey();
662 const KeyT TombstoneKey = getTombstoneKey();
663 assert(!KeyInfoT::isEqual(Val, EmptyKey) &&
664 !KeyInfoT::isEqual(Val, TombstoneKey) &&
665 "Empty/Tombstone value shouldn't be inserted into map!");
666
667 do {
668 BucketT *ThisBucket = BucketsPtr + (BucketNo & (NumBuckets-1));
669 // Found Val's bucket? If so, return it.
670 if (KeyInfoT::isEqual(ThisBucket->first, Val)) {
671 FoundBucket = ThisBucket;
672 return true;
673 }
674
675 // If we found an empty bucket, the key doesn't exist in the set.
676 // Insert it and return the default value.
677 if (KeyInfoT::isEqual(ThisBucket->first, EmptyKey)) {
678 // If we've already seen a tombstone while probing, fill it in instead
679 // of the empty bucket we eventually probed to.
680 if (FoundTombstone) ThisBucket = FoundTombstone;
681 FoundBucket = FoundTombstone ? FoundTombstone : ThisBucket;
682 return false;
683 }
684
685 // If this is a tombstone, remember it. If Val ends up not in the map, we
686 // prefer to return it than something that would require more probing.
687 // Ditto for zero values.
688 if (KeyInfoT::isEqual(ThisBucket->first, TombstoneKey) && !FoundTombstone)
689 FoundTombstone = ThisBucket; // Remember the first tombstone found.
690 if (ZeroValuesArePurgeable &&
691 ThisBucket->second == 0 && !FoundTombstone)
692 FoundTombstone = ThisBucket;
693
694 // Otherwise, it's a hash collision or a tombstone, continue quadratic
695 // probing.
696 BucketNo += ProbeAmt++;
697 ProbeCount++;
698 } while (ProbeCount < NumBuckets);
699 // If we get here then we did not find a bucket. This is a bug. Emit some diagnostics and abort.
700 unsigned EmptyCount = 0, TombstoneCount = 0, ZeroCount = 0, ValueCount = 0;
701 BucketsPtr = Buckets;
702 for (unsigned i=0; i<NumBuckets; i++) {
703 if (KeyInfoT::isEqual(BucketsPtr->first, EmptyKey)) EmptyCount++;
704 else if (KeyInfoT::isEqual(BucketsPtr->first, TombstoneKey)) TombstoneCount++;
705 else if (KeyInfoT::isEqual(BucketsPtr->first, 0)) ZeroCount++;
706 else ValueCount++;
707 BucketsPtr++;
708 }
709 _objc_fatal("DenseMap::LookupBucketFor() failed to find available bucket.\nNumBuckets = %d, EmptyCount = %d, TombstoneCount = %d, ZeroCount = %d, ValueCount = %d\n", NumBuckets, EmptyCount, TombstoneCount, ZeroCount, ValueCount);
710 }
711
712 void init(unsigned InitBuckets) {
713 NumEntries = 0;
714 NumTombstones = 0;
715 NumBuckets = InitBuckets;
716 assert(InitBuckets && (InitBuckets & (InitBuckets-1)) == 0 &&
717 "# initial buckets must be a power of two!");
718 Buckets = static_cast<BucketT*>(operator new(sizeof(BucketT)*InitBuckets));
719 // Initialize all the keys to EmptyKey.
720 const KeyT EmptyKey = getEmptyKey();
721 for (unsigned i = 0; i != InitBuckets; ++i)
722 new (&Buckets[i].first) KeyT(EmptyKey);
723 }
724
725 void grow(unsigned AtLeast) {
726 unsigned OldNumBuckets = NumBuckets;
727 BucketT *OldBuckets = Buckets;
728
729 // Double the number of buckets.
730 while (NumBuckets < AtLeast)
731 NumBuckets <<= 1;
732 NumTombstones = 0;
733 Buckets = static_cast<BucketT*>(operator new(sizeof(BucketT)*NumBuckets));
734
735 // Initialize all the keys to EmptyKey.
736 const KeyT EmptyKey = getEmptyKey();
737 for (unsigned i = 0, e = NumBuckets; i != e; ++i)
738 new (&Buckets[i].first) KeyT(EmptyKey);
739
740 // Insert all the old elements.
741 const KeyT TombstoneKey = getTombstoneKey();
742 for (BucketT *B = OldBuckets, *E = OldBuckets+OldNumBuckets; B != E; ++B) {
743 if (!KeyInfoT::isEqual(B->first, EmptyKey) &&
744 !KeyInfoT::isEqual(B->first, TombstoneKey))
745 {
746 // Valid key/value, or zero value
747 if (!ZeroValuesArePurgeable || B->second != 0) {
748 // Insert the key/value into the new table.
749 BucketT *DestBucket;
750 bool FoundVal = LookupBucketFor(B->first, DestBucket);
751 (void)FoundVal; // silence warning.
752 assert(!FoundVal && "Key already in new map?");
753 DestBucket->first = B->first;
754 new (&DestBucket->second) ValueT(B->second);
755 } else {
756 NumEntries--;
757 }
758
759 // Free the value.
760 B->second.~ValueT();
761 }
762 B->first.~KeyT();
763 }
764
765 #ifndef NDEBUG
766 memset(OldBuckets, 0x5a, sizeof(BucketT)*OldNumBuckets);
767 #endif
768 // Free the old table.
769 operator delete(OldBuckets);
770 }
771
772 void shrink_and_clear() {
773 unsigned OldNumBuckets = NumBuckets;
774 BucketT *OldBuckets = Buckets;
775
776 // Reduce the number of buckets.
777 NumBuckets = NumEntries > 32 ? 1 << (Log2_32_Ceil(NumEntries) + 1)
778 : 64;
779 NumTombstones = 0;
780 Buckets = static_cast<BucketT*>(operator new(sizeof(BucketT)*NumBuckets));
781
782 // Initialize all the keys to EmptyKey.
783 const KeyT EmptyKey = getEmptyKey();
784 for (unsigned i = 0, e = NumBuckets; i != e; ++i)
785 new (&Buckets[i].first) KeyT(EmptyKey);
786
787 // Free the old buckets.
788 const KeyT TombstoneKey = getTombstoneKey();
789 for (BucketT *B = OldBuckets, *E = OldBuckets+OldNumBuckets; B != E; ++B) {
790 if (!KeyInfoT::isEqual(B->first, EmptyKey) &&
791 !KeyInfoT::isEqual(B->first, TombstoneKey)) {
792 // Free the value.
793 B->second.~ValueT();
794 }
795 B->first.~KeyT();
796 }
797
798 #ifndef NDEBUG
799 memset(OldBuckets, 0x5a, sizeof(BucketT)*OldNumBuckets);
800 #endif
801 // Free the old table.
802 operator delete(OldBuckets);
803
804 NumEntries = 0;
805 }
806 };
807
808 template<typename KeyT, typename ValueT,
809 typename KeyInfoT, typename ValueInfoT, bool IsConst>
810 class DenseMapIterator {
811 typedef std::pair<KeyT, ValueT> Bucket;
812 typedef DenseMapIterator<KeyT, ValueT,
813 KeyInfoT, ValueInfoT, true> ConstIterator;
814 friend class DenseMapIterator<KeyT, ValueT, KeyInfoT, ValueInfoT, true>;
815 public:
816 typedef ptrdiff_t difference_type;
817 typedef typename conditional<IsConst, const Bucket, Bucket>::type value_type;
818 typedef value_type *pointer;
819 typedef value_type &reference;
820 typedef std::forward_iterator_tag iterator_category;
821 private:
822 pointer Ptr, End;
823 public:
824 DenseMapIterator() : Ptr(0), End(0) {}
825
826 DenseMapIterator(pointer Pos, pointer E) : Ptr(Pos), End(E) {
827 AdvancePastEmptyBuckets();
828 }
829
830 // If IsConst is true this is a converting constructor from iterator to
831 // const_iterator and the default copy constructor is used.
832 // Otherwise this is a copy constructor for iterator.
833 DenseMapIterator(const DenseMapIterator<KeyT, ValueT,
834 KeyInfoT, ValueInfoT, false>& I)
835 : Ptr(I.Ptr), End(I.End) {}
836
837 reference operator*() const {
838 return *Ptr;
839 }
840 pointer operator->() const {
841 return Ptr;
842 }
843
844 bool operator==(const ConstIterator &RHS) const {
845 return Ptr == RHS.operator->();
846 }
847 bool operator!=(const ConstIterator &RHS) const {
848 return Ptr != RHS.operator->();
849 }
850
851 inline DenseMapIterator& operator++() { // Preincrement
852 ++Ptr;
853 AdvancePastEmptyBuckets();
854 return *this;
855 }
856 DenseMapIterator operator++(int) { // Postincrement
857 DenseMapIterator tmp = *this; ++*this; return tmp;
858 }
859
860 private:
861 void AdvancePastEmptyBuckets() {
862 const KeyT Empty = KeyInfoT::getEmptyKey();
863 const KeyT Tombstone = KeyInfoT::getTombstoneKey();
864
865 while (Ptr != End &&
866 (KeyInfoT::isEqual(Ptr->first, Empty) ||
867 KeyInfoT::isEqual(Ptr->first, Tombstone)))
868 ++Ptr;
869 }
870 };
871
872 } // end namespace objc
873
874 #endif