diff options
author | Steve Block <steveblock@google.com> | 2010-02-05 14:27:46 +0000 |
---|---|---|
committer | Steve Block <steveblock@google.com> | 2010-02-15 10:49:50 +0000 |
commit | 5e2bc6953fe6923165b8a5d7679939693a1d58d6 (patch) | |
tree | 6ccb8c24bc2bf5e8f413e6cfae250b729b426631 /JavaScriptCore/runtime | |
parent | 4a00f4fccc3cb7e9996749a05631f5d7b9de756e (diff) | |
download | external_webkit-5e2bc6953fe6923165b8a5d7679939693a1d58d6.zip external_webkit-5e2bc6953fe6923165b8a5d7679939693a1d58d6.tar.gz external_webkit-5e2bc6953fe6923165b8a5d7679939693a1d58d6.tar.bz2 |
Merge webkit.org at r54340 : Initial merge by git
Change-Id: Ib489d2ff91186ea3652522e1d586e54416a2cf44
Diffstat (limited to 'JavaScriptCore/runtime')
-rw-r--r-- | JavaScriptCore/runtime/DateConstructor.cpp | 2 | ||||
-rw-r--r-- | JavaScriptCore/runtime/MathObject.cpp | 3 | ||||
-rw-r--r-- | JavaScriptCore/runtime/PropertyMapHashTable.h | 1 | ||||
-rw-r--r-- | JavaScriptCore/runtime/Structure.cpp | 56 | ||||
-rw-r--r-- | JavaScriptCore/runtime/Structure.h | 27 |
5 files changed, 49 insertions, 40 deletions
diff --git a/JavaScriptCore/runtime/DateConstructor.cpp b/JavaScriptCore/runtime/DateConstructor.cpp index 2e476b3..e9a5c29 100644 --- a/JavaScriptCore/runtime/DateConstructor.cpp +++ b/JavaScriptCore/runtime/DateConstructor.cpp @@ -177,7 +177,7 @@ static JSValue JSC_HOST_CALL dateUTC(ExecState* exec, JSObject*, JSValue, const t.minute = args.at(4).toInt32(exec); t.second = args.at(5).toInt32(exec); double ms = (n >= 7) ? args.at(6).toNumber(exec) : 0; - return jsNumber(exec, gregorianDateTimeToMS(exec, t, ms, true)); + return jsNumber(exec, timeClip(gregorianDateTimeToMS(exec, t, ms, true))); } } // namespace JSC diff --git a/JavaScriptCore/runtime/MathObject.cpp b/JavaScriptCore/runtime/MathObject.cpp index 98ff3ba..8f22fba 100644 --- a/JavaScriptCore/runtime/MathObject.cpp +++ b/JavaScriptCore/runtime/MathObject.cpp @@ -218,7 +218,8 @@ JSValue JSC_HOST_CALL mathProtoFuncRound(ExecState* exec, JSObject*, JSValue, co double arg = args.at(0).toNumber(exec); if (signbit(arg) && arg >= -0.5) return jsNumber(exec, -0.0); - return jsNumber(exec, floor(arg + 0.5)); + double integer = ceil(arg); + return jsNumber(exec, integer - (integer - arg > 0.5)); } JSValue JSC_HOST_CALL mathProtoFuncSin(ExecState* exec, JSObject*, JSValue, const ArgList& args) diff --git a/JavaScriptCore/runtime/PropertyMapHashTable.h b/JavaScriptCore/runtime/PropertyMapHashTable.h index 5b63f79..44dc2b8 100644 --- a/JavaScriptCore/runtime/PropertyMapHashTable.h +++ b/JavaScriptCore/runtime/PropertyMapHashTable.h @@ -61,7 +61,6 @@ namespace JSC { unsigned size; unsigned keyCount; unsigned deletedSentinelCount; - unsigned anonymousSlotCount; unsigned lastIndexUsed; Vector<unsigned>* deletedOffsets; unsigned entryIndices[1]; diff --git a/JavaScriptCore/runtime/Structure.cpp b/JavaScriptCore/runtime/Structure.cpp index 77330aa..546e2bf 100644 --- a/JavaScriptCore/runtime/Structure.cpp +++ b/JavaScriptCore/runtime/Structure.cpp @@ -123,7 +123,7 @@ void Structure::dumpStatistics() #endif } -Structure::Structure(JSValue prototype, const TypeInfo& typeInfo) +Structure::Structure(JSValue prototype, const TypeInfo& typeInfo, unsigned anonymousSlotCount) : m_typeInfo(typeInfo) , m_prototype(prototype) , m_specificValueInPrevious(0) @@ -135,6 +135,7 @@ Structure::Structure(JSValue prototype, const TypeInfo& typeInfo) , m_hasGetterSetterProperties(false) , m_attributesInPrevious(0) , m_specificFunctionThrashCount(0) + , m_anonymousSlotCount(anonymousSlotCount) { ASSERT(m_prototype); ASSERT(m_prototype.isObject() || m_prototype.isNull()); @@ -275,7 +276,7 @@ void Structure::materializePropertyMap() for (ptrdiff_t i = structures.size() - 2; i >= 0; --i) { structure = structures[i]; structure->m_nameInPrevious->ref(); - PropertyMapEntry entry(structure->m_nameInPrevious.get(), structure->m_offset, structure->m_attributesInPrevious, structure->m_specificValueInPrevious, ++m_propertyTable->lastIndexUsed); + PropertyMapEntry entry(structure->m_nameInPrevious.get(), m_anonymousSlotCount + structure->m_offset, structure->m_attributesInPrevious, structure->m_specificValueInPrevious, ++m_propertyTable->lastIndexUsed); insertIntoPropertyMapHashTable(entry); } } @@ -341,7 +342,9 @@ PassRefPtr<Structure> Structure::addPropertyTransitionToExistingStructure(Struct if (Structure* existingTransition = structure->table.get(make_pair(propertyName.ustring().rep(), attributes), specificValue)) { ASSERT(existingTransition->m_offset != noOffset); - offset = existingTransition->m_offset; + offset = existingTransition->m_offset + existingTransition->m_anonymousSlotCount; + ASSERT(offset >= structure->m_anonymousSlotCount); + ASSERT(structure->m_anonymousSlotCount == existingTransition->m_anonymousSlotCount); return existingTransition; } @@ -361,12 +364,14 @@ PassRefPtr<Structure> Structure::addPropertyTransition(Structure* structure, con RefPtr<Structure> transition = toCacheableDictionaryTransition(structure); ASSERT(structure != transition); offset = transition->put(propertyName, attributes, specificValue); + ASSERT(offset >= structure->m_anonymousSlotCount); + ASSERT(structure->m_anonymousSlotCount == transition->m_anonymousSlotCount); if (transition->propertyStorageSize() > transition->propertyStorageCapacity()) transition->growPropertyStorageCapacity(); return transition.release(); } - RefPtr<Structure> transition = create(structure->m_prototype, structure->typeInfo()); + RefPtr<Structure> transition = create(structure->m_prototype, structure->typeInfo(), structure->anonymousSlotCount()); transition->m_cachedPrototypeChain = structure->m_cachedPrototypeChain; transition->m_previous = structure; @@ -393,11 +398,13 @@ PassRefPtr<Structure> Structure::addPropertyTransition(Structure* structure, con } offset = transition->put(propertyName, attributes, specificValue); + ASSERT(offset >= structure->m_anonymousSlotCount); + ASSERT(structure->m_anonymousSlotCount == transition->m_anonymousSlotCount); if (transition->propertyStorageSize() > transition->propertyStorageCapacity()) transition->growPropertyStorageCapacity(); - transition->m_offset = offset; - + transition->m_offset = offset - structure->m_anonymousSlotCount; + ASSERT(structure->anonymousSlotCount() == transition->anonymousSlotCount()); structure->table.add(make_pair(propertyName.ustring().rep(), attributes), transition.get(), specificValue); return transition.release(); } @@ -409,13 +416,15 @@ PassRefPtr<Structure> Structure::removePropertyTransition(Structure* structure, RefPtr<Structure> transition = toUncacheableDictionaryTransition(structure); offset = transition->remove(propertyName); + ASSERT(offset >= structure->m_anonymousSlotCount); + ASSERT(structure->m_anonymousSlotCount == transition->m_anonymousSlotCount); return transition.release(); } PassRefPtr<Structure> Structure::changePrototypeTransition(Structure* structure, JSValue prototype) { - RefPtr<Structure> transition = create(prototype, structure->typeInfo()); + RefPtr<Structure> transition = create(prototype, structure->typeInfo(), structure->anonymousSlotCount()); transition->m_propertyStorageCapacity = structure->m_propertyStorageCapacity; transition->m_hasGetterSetterProperties = structure->m_hasGetterSetterProperties; @@ -427,14 +436,15 @@ PassRefPtr<Structure> Structure::changePrototypeTransition(Structure* structure, structure->materializePropertyMapIfNecessary(); transition->m_propertyTable = structure->copyPropertyTable(); transition->m_isPinnedPropertyTable = true; - + + ASSERT(structure->anonymousSlotCount() == transition->anonymousSlotCount()); return transition.release(); } PassRefPtr<Structure> Structure::despecifyFunctionTransition(Structure* structure, const Identifier& replaceFunction) { ASSERT(structure->m_specificFunctionThrashCount < maxSpecificFunctionThrashCount); - RefPtr<Structure> transition = create(structure->storedPrototype(), structure->typeInfo()); + RefPtr<Structure> transition = create(structure->storedPrototype(), structure->typeInfo(), structure->anonymousSlotCount()); transition->m_propertyStorageCapacity = structure->m_propertyStorageCapacity; transition->m_hasGetterSetterProperties = structure->m_hasGetterSetterProperties; @@ -453,13 +463,14 @@ PassRefPtr<Structure> Structure::despecifyFunctionTransition(Structure* structur bool removed = transition->despecifyFunction(replaceFunction); ASSERT_UNUSED(removed, removed); } - + + ASSERT(structure->anonymousSlotCount() == transition->anonymousSlotCount()); return transition.release(); } PassRefPtr<Structure> Structure::getterSetterTransition(Structure* structure) { - RefPtr<Structure> transition = create(structure->storedPrototype(), structure->typeInfo()); + RefPtr<Structure> transition = create(structure->storedPrototype(), structure->typeInfo(), structure->anonymousSlotCount()); transition->m_propertyStorageCapacity = structure->m_propertyStorageCapacity; transition->m_hasGetterSetterProperties = transition->m_hasGetterSetterProperties; transition->m_hasNonEnumerableProperties = structure->m_hasNonEnumerableProperties; @@ -470,7 +481,8 @@ PassRefPtr<Structure> Structure::getterSetterTransition(Structure* structure) structure->materializePropertyMapIfNecessary(); transition->m_propertyTable = structure->copyPropertyTable(); transition->m_isPinnedPropertyTable = true; - + + ASSERT(structure->anonymousSlotCount() == transition->anonymousSlotCount()); return transition.release(); } @@ -478,7 +490,7 @@ PassRefPtr<Structure> Structure::toDictionaryTransition(Structure* structure, Di { ASSERT(!structure->isUncacheableDictionary()); - RefPtr<Structure> transition = create(structure->m_prototype, structure->typeInfo()); + RefPtr<Structure> transition = create(structure->m_prototype, structure->typeInfo(), structure->anonymousSlotCount()); transition->m_dictionaryKind = kind; transition->m_propertyStorageCapacity = structure->m_propertyStorageCapacity; transition->m_hasGetterSetterProperties = structure->m_hasGetterSetterProperties; @@ -489,6 +501,7 @@ PassRefPtr<Structure> Structure::toDictionaryTransition(Structure* structure, Di transition->m_propertyTable = structure->copyPropertyTable(); transition->m_isPinnedPropertyTable = true; + ASSERT(structure->anonymousSlotCount() == transition->anonymousSlotCount()); return transition.release(); } @@ -522,7 +535,7 @@ PassRefPtr<Structure> Structure::flattenDictionaryStructure(JSObject* object) // in the order that they are expected to be in, but we need to // reorder the storage, so we have to copy the current values out Vector<JSValue> values(propertyCount); - unsigned anonymousSlotCount = m_propertyTable->anonymousSlotCount; + unsigned anonymousSlotCount = m_anonymousSlotCount; for (unsigned i = 0; i < propertyCount; i++) { PropertyMapEntry* entry = sortedPropertyEntries[i]; values[i] = object->getDirectOffset(entry->offset); @@ -557,6 +570,7 @@ size_t Structure::addPropertyWithoutTransition(const Identifier& propertyName, u m_isPinnedPropertyTable = true; size_t offset = put(propertyName, attributes, specificValue); + ASSERT(offset >= m_anonymousSlotCount); if (propertyStorageSize() > propertyStorageCapacity()) growPropertyStorageCapacity(); return offset; @@ -571,6 +585,7 @@ size_t Structure::removePropertyWithoutTransition(const Identifier& propertyName m_isPinnedPropertyTable = true; size_t offset = remove(propertyName); + ASSERT(offset >= m_anonymousSlotCount); return offset; } @@ -627,7 +642,6 @@ PropertyMapHashTable* Structure::copyPropertyTable() if (m_propertyTable->deletedOffsets) newTable->deletedOffsets = new Vector<unsigned>(*m_propertyTable->deletedOffsets); - newTable->anonymousSlotCount = m_propertyTable->anonymousSlotCount; return newTable; } @@ -650,6 +664,7 @@ size_t Structure::get(const UString::Rep* rep, unsigned& attributes, JSCell*& sp if (rep == m_propertyTable->entries()[entryIndex - 1].key) { attributes = m_propertyTable->entries()[entryIndex - 1].attributes; specificValue = m_propertyTable->entries()[entryIndex - 1].specificValue; + ASSERT(m_propertyTable->entries()[entryIndex - 1].offset >= m_anonymousSlotCount); return m_propertyTable->entries()[entryIndex - 1].offset; } @@ -673,6 +688,7 @@ size_t Structure::get(const UString::Rep* rep, unsigned& attributes, JSCell*& sp if (rep == m_propertyTable->entries()[entryIndex - 1].key) { attributes = m_propertyTable->entries()[entryIndex - 1].attributes; specificValue = m_propertyTable->entries()[entryIndex - 1].specificValue; + ASSERT(m_propertyTable->entries()[entryIndex - 1].offset >= m_anonymousSlotCount); return m_propertyTable->entries()[entryIndex - 1].offset; } } @@ -821,9 +837,10 @@ size_t Structure::put(const Identifier& propertyName, unsigned attributes, JSCel newOffset = m_propertyTable->deletedOffsets->last(); m_propertyTable->deletedOffsets->removeLast(); } else - newOffset = m_propertyTable->keyCount + m_propertyTable->anonymousSlotCount; + newOffset = m_propertyTable->keyCount + m_anonymousSlotCount; m_propertyTable->entries()[entryIndex - 1].offset = newOffset; - + + ASSERT(newOffset >= m_anonymousSlotCount); ++m_propertyTable->keyCount; if ((m_propertyTable->keyCount + m_propertyTable->deletedSentinelCount) * 2 >= m_propertyTable->size) @@ -887,6 +904,7 @@ size_t Structure::remove(const Identifier& propertyName) m_propertyTable->entryIndices[i & m_propertyTable->sizeMask] = deletedSentinelIndex; size_t offset = m_propertyTable->entries()[entryIndex - 1].offset; + ASSERT(offset >= m_anonymousSlotCount); key->deref(); m_propertyTable->entries()[entryIndex - 1].key = 0; @@ -912,7 +930,7 @@ size_t Structure::remove(const Identifier& propertyName) void Structure::insertIntoPropertyMapHashTable(const PropertyMapEntry& entry) { ASSERT(m_propertyTable); - + ASSERT(entry.offset >= m_anonymousSlotCount); unsigned i = entry.key->existingHash(); unsigned k = 0; @@ -991,7 +1009,6 @@ void Structure::rehashPropertyMapHashTable(unsigned newTableSize) m_propertyTable = static_cast<PropertyMapHashTable*>(fastZeroedMalloc(PropertyMapHashTable::allocationSize(newTableSize))); m_propertyTable->size = newTableSize; m_propertyTable->sizeMask = newTableSize - 1; - m_propertyTable->anonymousSlotCount = oldTable->anonymousSlotCount; unsigned lastIndexUsed = 0; unsigned entryCount = oldTable->keyCount + oldTable->deletedSentinelCount; @@ -1121,6 +1138,7 @@ void Structure::checkConsistency() for (unsigned c = 1; c <= m_propertyTable->keyCount + m_propertyTable->deletedSentinelCount; ++c) { ASSERT(m_hasNonEnumerableProperties || !(m_propertyTable->entries()[c].attributes & DontEnum)); UString::Rep* rep = m_propertyTable->entries()[c].key; + ASSERT(m_propertyTable->entries()[c].offset >= m_anonymousSlotCount); if (!rep) continue; ++nonEmptyEntryCount; diff --git a/JavaScriptCore/runtime/Structure.h b/JavaScriptCore/runtime/Structure.h index f73f9b8..1353a5a 100644 --- a/JavaScriptCore/runtime/Structure.h +++ b/JavaScriptCore/runtime/Structure.h @@ -62,15 +62,7 @@ namespace JSC { friend class StructureTransitionTable; static PassRefPtr<Structure> create(JSValue prototype, const TypeInfo& typeInfo, unsigned anonymousSlotCount) { - Structure* structure = (new Structure(prototype, typeInfo)); - if (anonymousSlotCount) { - structure->materializePropertyMap(); - structure->m_isPinnedPropertyTable = true; - structure->m_propertyTable->anonymousSlotCount = anonymousSlotCount; - // Currently we don't allow more anonymous slots than fit in the inline capacity - ASSERT(structure->propertyStorageSize() <= structure->propertyStorageCapacity()); - } - return adoptRef(structure); + return adoptRef(new Structure(prototype, typeInfo, anonymousSlotCount)); } static void startIgnoringLeaks(); @@ -109,7 +101,7 @@ namespace JSC { void growPropertyStorageCapacity(); unsigned propertyStorageCapacity() const { return m_propertyStorageCapacity; } - unsigned propertyStorageSize() const { return m_propertyTable ? m_propertyTable->keyCount + m_propertyTable->anonymousSlotCount + (m_propertyTable->deletedOffsets ? m_propertyTable->deletedOffsets->size() : 0) : m_offset + 1; } + unsigned propertyStorageSize() const { return m_anonymousSlotCount + (m_propertyTable ? m_propertyTable->keyCount + (m_propertyTable->deletedOffsets ? m_propertyTable->deletedOffsets->size() : 0) : m_offset + 1); } bool isUsingInlineStorage() const; size_t get(const Identifier& propertyName); @@ -134,8 +126,8 @@ namespace JSC { bool hasNonEnumerableProperties() const { return m_hasNonEnumerableProperties; } - bool hasAnonymousSlots() const { return m_propertyTable && m_propertyTable->anonymousSlotCount; } - unsigned anonymousSlotCount() const { return m_propertyTable ? m_propertyTable->anonymousSlotCount : 0; } + bool hasAnonymousSlots() const { return !!m_anonymousSlotCount; } + unsigned anonymousSlotCount() const { return m_anonymousSlotCount; } bool isEmpty() const { return m_propertyTable ? !m_propertyTable->keyCount : m_offset == noOffset; } @@ -147,12 +139,8 @@ namespace JSC { void getPropertyNames(PropertyNameArray&, EnumerationMode mode); private: - static PassRefPtr<Structure> create(JSValue prototype, const TypeInfo& typeInfo) - { - return adoptRef(new Structure(prototype, typeInfo)); - } - Structure(JSValue prototype, const TypeInfo&); + Structure(JSValue prototype, const TypeInfo&, unsigned anonymousSlotCount); typedef enum { NoneDictionaryKind = 0, @@ -216,6 +204,8 @@ namespace JSC { PropertyMapHashTable* m_propertyTable; uint32_t m_propertyStorageCapacity; + + // m_offset does not account for anonymous slots signed char m_offset; unsigned m_dictionaryKind : 2; @@ -231,7 +221,8 @@ namespace JSC { unsigned m_attributesInPrevious : 7; #endif unsigned m_specificFunctionThrashCount : 2; - // 10 free bits + unsigned m_anonymousSlotCount : 5; + // 5 free bits }; inline size_t Structure::get(const Identifier& propertyName) |