SmallNumDataBits = SmallNumRawBits - SmallNumSizeBits
};
+public:
+ // Encapsulation of a single bit.
+ class reference {
+ SmallBitVector &TheVector;
+ unsigned BitPos;
+
+ public:
+ reference(SmallBitVector &b, unsigned Idx) : TheVector(b), BitPos(Idx) {}
+
+ reference& operator=(reference t) {
+ *this = bool(t);
+ return *this;
+ }
+
+ reference& operator=(bool t) {
+ if (t)
+ TheVector.set(BitPos);
+ else
+ TheVector.reset(BitPos);
+ return *this;
+ }
+
+ operator bool() const {
+ return const_cast<const SmallBitVector &>(TheVector).operator[](BitPos);
+ }
+ };
+
+private:
bool isSmall() const {
return X & uintptr_t(1);
}
void setSmallRawBits(uintptr_t NewRawBits) {
assert(isSmall());
- X = NewRawBits << 1 | uintptr_t(1);
+ X = (NewRawBits << 1) | uintptr_t(1);
}
// Return the size.
}
void setSmallBits(uintptr_t NewBits) {
- setSmallRawBits(NewBits & ~(~uintptr_t(0) << getSmallSize()) |
+ setSmallRawBits((NewBits & ~(~uintptr_t(0) << getSmallSize())) |
(getSmallSize() << SmallNumDataBits));
}
return getPointer()->any();
}
+ /// all - Returns true if all bits are set.
+ bool all() const {
+ if (isSmall())
+ return getSmallBits() == (uintptr_t(1) << getSmallSize()) - 1;
+ return getPointer()->all();
+ }
+
/// none - Returns true if none of the bits are set.
bool none() const {
if (isSmall())
int find_first() const {
if (isSmall()) {
uintptr_t Bits = getSmallBits();
- if (sizeof(uintptr_t) * CHAR_BIT == 32) {
- size_t FirstBit = CountTrailingZeros_32(Bits);
- return FirstBit == 32 ? -1 : FirstBit;
- } else if (sizeof(uintptr_t) * CHAR_BIT == 64) {
- size_t FirstBit = CountTrailingZeros_64(Bits);
- return FirstBit == 64 ? -1 : FirstBit;
- }
+ if (Bits == 0)
+ return -1;
+ if (sizeof(uintptr_t) * CHAR_BIT == 32)
+ return CountTrailingZeros_32(Bits);
+ if (sizeof(uintptr_t) * CHAR_BIT == 64)
+ return CountTrailingZeros_64(Bits);
assert(0 && "Unsupported!");
}
return getPointer()->find_first();
uintptr_t Bits = getSmallBits();
// Mask off previous bits.
Bits &= ~uintptr_t(0) << (Prev + 1);
- if (sizeof(uintptr_t) * CHAR_BIT == 32) {
- size_t FirstBit = CountTrailingZeros_32(Bits);
- return FirstBit == 32 ? -1 : FirstBit;
- } else if (sizeof(uintptr_t) * CHAR_BIT == 64) {
- size_t FirstBit = CountTrailingZeros_64(Bits);
- return FirstBit == 64 ? -1 : FirstBit;
- }
+ if (Bits == 0 || Prev + 1 >= getSmallSize())
+ return -1;
+ if (sizeof(uintptr_t) * CHAR_BIT == 32)
+ return CountTrailingZeros_32(Bits);
+ if (sizeof(uintptr_t) * CHAR_BIT == 64)
+ return CountTrailingZeros_64(Bits);
assert(0 && "Unsupported!");
}
return getPointer()->find_next(Prev);
}
// Indexing.
- // TODO: Add an index operator which returns a "reference" (proxy class).
+ reference operator[](unsigned Idx) {
+ assert(Idx < size() && "Out-of-bounds Bit access.");
+ return reference(*this, Idx);
+ }
+
bool operator[](unsigned Idx) const {
assert(Idx < size() && "Out-of-bounds Bit access.");
if (isSmall())