Changeset 98268 in webkit
- Timestamp:
- Oct 24, 2011 12:41:29 PM (12 years ago)
- Location:
- trunk/Source/JavaScriptCore
- Files:
-
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/JavaScriptCore/ChangeLog
r98261 r98268 1 2011-10-24 Yuqiang Xian <yuqiang.xian@intel.com> 2 3 BitVector isInline check could fail 4 https://bugs.webkit.org/show_bug.cgi?id=70691 5 6 Reviewed by Geoffrey Garen. 7 8 Current BitVector uses the highest bit of m_bitsOrPointer to indicate 9 whether it's an inlined bit set or a pointer to an outOfLine bit set. 10 This check may fail in case the pointer also has the highest bit set, 11 which is surely possible on IA32 (Linux). 12 In this case the check failure can result in unexpected behaviors, 13 for example if the BitVector is incorrectly determined as having an 14 inlined bit set, then setting a bit exceeding maxInlineBits will wrongly 15 modify the memory adjacent to the BitVector object. 16 This fix is to use the lowest bit of m_bitsOrPointer to indicate inline 17 or outofline, based on the assumption that the pointer to OutOfLineBits 18 should be 4 or 8 byte aligned. 19 We could mark the lowest bit (bit 0) with 1 for inlined bit set, 20 and bits 1~bitsInPointer are used for bit set/test. 21 In this case we need do one bit more shift for bit set/test. 22 23 * wtf/BitVector.cpp: 24 (WTF::BitVector::resizeOutOfLine): 25 * wtf/BitVector.h: 26 (WTF::BitVector::quickGet): 27 (WTF::BitVector::quickSet): 28 (WTF::BitVector::quickClear): 29 (WTF::BitVector::makeInlineBits): 30 (WTF::BitVector::isInline): 31 1 32 2011-10-24 Mark Hahnenberg <mhahnenberg@apple.com> 2 33 -
trunk/Source/JavaScriptCore/wtf/BitVector.cpp
r97197 r98268 92 92 if (isInline()) { 93 93 // Make sure that all of the bits are zero in case we do a no-op resize. 94 *newOutOfLineBits->bits() = m_bitsOrPointer & ~(static_cast<uintptr_t>(1) << maxInlineBits());94 *newOutOfLineBits->bits() = m_bitsOrPointer & ~(static_cast<uintptr_t>(1)); 95 95 } else { 96 96 if (numBits > size()) { … … 104 104 } 105 105 m_bitsOrPointer = bitwise_cast<uintptr_t>(newOutOfLineBits); 106 ASSERT(!isInline()); 106 107 } 107 108 -
trunk/Source/JavaScriptCore/wtf/BitVector.h
r97211 r98268 115 115 { 116 116 ASSERT(bit < size()); 117 return !!(bits()[bit / bitsInPointer()] & (static_cast<uintptr_t>(1) << ( bit & (bitsInPointer() - 1))));117 return !!(bits()[bit / bitsInPointer()] & (static_cast<uintptr_t>(1) << ((bit & (bitsInPointer() - 1)) + 1))); 118 118 } 119 119 … … 121 121 { 122 122 ASSERT(bit < size()); 123 bits()[bit / bitsInPointer()] |= (static_cast<uintptr_t>(1) << ( bit & (bitsInPointer() - 1)));123 bits()[bit / bitsInPointer()] |= (static_cast<uintptr_t>(1) << ((bit & (bitsInPointer() - 1)) + 1)); 124 124 } 125 125 … … 127 127 { 128 128 ASSERT(bit < size()); 129 bits()[bit / bitsInPointer()] &= ~(static_cast<uintptr_t>(1) << ( bit & (bitsInPointer() - 1)));129 bits()[bit / bitsInPointer()] &= ~(static_cast<uintptr_t>(1) << ((bit & (bitsInPointer() - 1)) + 1)); 130 130 } 131 131 … … 188 188 static uintptr_t makeInlineBits(uintptr_t bits) 189 189 { 190 ASSERT(!(bits & (static_cast<uintptr_t>(1) << maxInlineBits())));191 return bits | (static_cast<uintptr_t>(1) << maxInlineBits());190 ASSERT(!(bits & static_cast<uintptr_t>(1))); 191 return bits | static_cast<uintptr_t>(1); 192 192 } 193 193 … … 212 212 }; 213 213 214 bool isInline() const { return m_bitsOrPointer >> maxInlineBits(); }214 bool isInline() const { return m_bitsOrPointer & static_cast<uintptr_t>(1); } 215 215 216 216 const OutOfLineBits* outOfLineBits() const { return bitwise_cast<const OutOfLineBits*>(m_bitsOrPointer); } … … 233 233 return outOfLineBits()->bits(); 234 234 } 235 235 236 // The low bit of m_bitsOrPointer is a flag indicating whether this field is 237 // inline bits or a pointer to out of line bits. If the flag is set, the field 238 // is inline bits. This works because the low bit in a pointer is always unset. 236 239 uintptr_t m_bitsOrPointer; 237 240 };
Note: See TracChangeset
for help on using the changeset viewer.