diff options
author | Lorry Tar Creator <lorry-tar-importer@lorry> | 2016-04-10 09:28:39 +0000 |
---|---|---|
committer | Lorry Tar Creator <lorry-tar-importer@lorry> | 2016-04-10 09:28:39 +0000 |
commit | 32761a6cee1d0dee366b885b7b9c777e67885688 (patch) | |
tree | d6bec92bebfb216f4126356e55518842c2f476a1 /Source/JavaScriptCore/runtime/JSSymbolTableObject.h | |
parent | a4e969f4965059196ca948db781e52f7cfebf19e (diff) | |
download | WebKitGtk-tarball-32761a6cee1d0dee366b885b7b9c777e67885688.tar.gz |
webkitgtk-2.4.11webkitgtk-2.4.11
Diffstat (limited to 'Source/JavaScriptCore/runtime/JSSymbolTableObject.h')
-rw-r--r-- | Source/JavaScriptCore/runtime/JSSymbolTableObject.h | 162 |
1 files changed, 52 insertions, 110 deletions
diff --git a/Source/JavaScriptCore/runtime/JSSymbolTableObject.h b/Source/JavaScriptCore/runtime/JSSymbolTableObject.h index 368cedcb8..b5b20a845 100644 --- a/Source/JavaScriptCore/runtime/JSSymbolTableObject.h +++ b/Source/JavaScriptCore/runtime/JSSymbolTableObject.h @@ -1,5 +1,5 @@ /* - * Copyright (C) 2012, 2014, 2015 Apple Inc. All rights reserved. + * Copyright (C) 2012 Apple Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -10,7 +10,7 @@ * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. - * 3. Neither the name of Apple Inc. ("Apple") nor the names of + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of * its contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * @@ -32,47 +32,37 @@ #include "JSScope.h" #include "PropertyDescriptor.h" #include "SymbolTable.h" -#include "VariableWriteFireDetail.h" namespace JSC { -class JSSymbolTableObject; - class JSSymbolTableObject : public JSScope { public: typedef JSScope Base; - static const unsigned StructureFlags = Base::StructureFlags | IsEnvironmentRecord | OverridesGetPropertyNames; SymbolTable* symbolTable() const { return m_symbolTable.get(); } JS_EXPORT_PRIVATE static bool deleteProperty(JSCell*, ExecState*, PropertyName); JS_EXPORT_PRIVATE static void getOwnNonIndexPropertyNames(JSObject*, ExecState*, PropertyNameArray&, EnumerationMode); - static ptrdiff_t offsetOfSymbolTable() { return OBJECT_OFFSETOF(JSSymbolTableObject, m_symbolTable); } - protected: - JSSymbolTableObject(VM& vm, Structure* structure, JSScope* scope) - : Base(vm, structure, scope) - { - } + static const unsigned StructureFlags = IsEnvironmentRecord | OverridesVisitChildren | OverridesGetPropertyNames | Base::StructureFlags; - JSSymbolTableObject(VM& vm, Structure* structure, JSScope* scope, SymbolTable* symbolTable) + JSSymbolTableObject(VM& vm, Structure* structure, JSScope* scope, SymbolTable* symbolTable = 0) : Base(vm, structure, scope) { - ASSERT(symbolTable); - setSymbolTable(vm, symbolTable); + if (symbolTable) + m_symbolTable.set(vm, this, symbolTable); } - - void setSymbolTable(VM& vm, SymbolTable* symbolTable) + + void finishCreation(VM& vm) { - ASSERT(!m_symbolTable); - symbolTable->singletonScope()->notifyWrite(vm, this, "Allocated a scope"); - m_symbolTable.set(vm, this, symbolTable); + Base::finishCreation(vm); + if (!m_symbolTable) + m_symbolTable.set(vm, this, SymbolTable::create(vm)); } - + static void visitChildren(JSCell*, SlotVisitor&); - -private: + WriteBarrier<SymbolTable> m_symbolTable; }; @@ -82,18 +72,12 @@ inline bool symbolTableGet( { SymbolTable& symbolTable = *object->symbolTable(); ConcurrentJITLocker locker(symbolTable.m_lock); - SymbolTable::Map::iterator iter = symbolTable.find(locker, propertyName.uid()); + SymbolTable::Map::iterator iter = symbolTable.find(locker, propertyName.publicName()); if (iter == symbolTable.end(locker)) return false; SymbolTableEntry::Fast entry = iter->value; ASSERT(!entry.isNull()); - - ScopeOffset offset = entry.scopeOffset(); - // Defend against the inspector asking for a var after it has been optimized out. - if (!object->isValidScopeOffset(offset)) - return false; - - slot.setValue(object, entry.getAttributes() | DontDelete, object->variableAt(offset).get()); + slot.setValue(object, entry.getAttributes() | DontDelete, object->registerAt(entry.getIndex()).get()); return true; } @@ -103,18 +87,13 @@ inline bool symbolTableGet( { SymbolTable& symbolTable = *object->symbolTable(); ConcurrentJITLocker locker(symbolTable.m_lock); - SymbolTable::Map::iterator iter = symbolTable.find(locker, propertyName.uid()); + SymbolTable::Map::iterator iter = symbolTable.find(locker, propertyName.publicName()); if (iter == symbolTable.end(locker)) return false; SymbolTableEntry::Fast entry = iter->value; ASSERT(!entry.isNull()); - - ScopeOffset offset = entry.scopeOffset(); - // Defend against the inspector asking for a var after it has been optimized out. - if (!object->isValidScopeOffset(offset)) - return false; - - descriptor.setDescriptor(object->variableAt(offset).get(), entry.getAttributes() | DontDelete); + descriptor.setDescriptor( + object->registerAt(entry.getIndex()).get(), entry.getAttributes() | DontDelete); return true; } @@ -125,64 +104,42 @@ inline bool symbolTableGet( { SymbolTable& symbolTable = *object->symbolTable(); ConcurrentJITLocker locker(symbolTable.m_lock); - SymbolTable::Map::iterator iter = symbolTable.find(locker, propertyName.uid()); + SymbolTable::Map::iterator iter = symbolTable.find(locker, propertyName.publicName()); if (iter == symbolTable.end(locker)) return false; SymbolTableEntry::Fast entry = iter->value; ASSERT(!entry.isNull()); - - ScopeOffset offset = entry.scopeOffset(); - // Defend against the inspector asking for a var after it has been optimized out. - if (!object->isValidScopeOffset(offset)) - return false; - - slot.setValue(object, entry.getAttributes() | DontDelete, object->variableAt(offset).get()); + slot.setValue(object, entry.getAttributes() | DontDelete, object->registerAt(entry.getIndex()).get()); slotIsWriteable = !entry.isReadOnly(); return true; } -enum class SymbolTablePutMode { - WithAttributes, - WithoutAttributes -}; - -template<SymbolTablePutMode symbolTablePutMode, typename SymbolTableObjectType> +template<typename SymbolTableObjectType> inline bool symbolTablePut( - SymbolTableObjectType* object, ExecState* exec, PropertyName propertyName, JSValue value, unsigned attributes, - bool shouldThrowReadOnlyError, bool ignoreReadOnlyErrors, WatchpointSet*& set) + SymbolTableObjectType* object, ExecState* exec, PropertyName propertyName, JSValue value, + bool shouldThrow) { - ASSERT(!Heap::heap(value) || Heap::heap(value) == Heap::heap(object)); - VM& vm = exec->vm(); - + ASSERT(!Heap::heap(value) || Heap::heap(value) == Heap::heap(object)); + WriteBarrierBase<Unknown>* reg; { SymbolTable& symbolTable = *object->symbolTable(); - // FIXME: This is very suspicious. We shouldn't need a GC-safe lock here. - // https://bugs.webkit.org/show_bug.cgi?id=134601 - GCSafeConcurrentJITLocker locker(symbolTable.m_lock, vm.heap); - SymbolTable::Map::iterator iter = symbolTable.find(locker, propertyName.uid()); + GCSafeConcurrentJITLocker locker(symbolTable.m_lock, exec->vm().heap); + SymbolTable::Map::iterator iter = symbolTable.find(locker, propertyName.publicName()); if (iter == symbolTable.end(locker)) return false; bool wasFat; SymbolTableEntry::Fast fastEntry = iter->value.getFast(wasFat); ASSERT(!fastEntry.isNull()); - if (fastEntry.isReadOnly() && !ignoreReadOnlyErrors) { - if (shouldThrowReadOnlyError) + if (fastEntry.isReadOnly()) { + if (shouldThrow) throwTypeError(exec, StrictModeReadonlyPropertyWriteError); return true; } - - ScopeOffset offset = fastEntry.scopeOffset(); - - // Defend against the inspector asking for a var after it has been optimized out. - if (!object->isValidScopeOffset(offset)) - return false; - - set = iter->value.watchpointSet(); - if (symbolTablePutMode == SymbolTablePutMode::WithAttributes) - iter->value.setAttributes(attributes); - reg = &object->variableAt(offset); + if (VariableWatchpointSet* set = iter->value.watchpointSet()) + set->notifyWrite(value); + reg = &object->registerAt(fastEntry.getIndex()); } // I'd prefer we not hold lock while executing barriers, since I prefer to reserve // the right for barriers to be able to trigger GC. And I don't want to hold VM @@ -192,43 +149,28 @@ inline bool symbolTablePut( } template<typename SymbolTableObjectType> -inline bool symbolTablePutTouchWatchpointSet( - SymbolTableObjectType* object, ExecState* exec, PropertyName propertyName, JSValue value, - bool shouldThrowReadOnlyError, bool ignoreReadOnlyErrors) -{ - WatchpointSet* set = nullptr; - unsigned attributes = 0; - bool result = symbolTablePut<SymbolTablePutMode::WithoutAttributes>(object, exec, propertyName, value, attributes, shouldThrowReadOnlyError, ignoreReadOnlyErrors, set); - if (set) - VariableWriteFireDetail::touch(set, object, propertyName); - return result; -} - -template<typename SymbolTableObjectType> -inline bool symbolTablePutInvalidateWatchpointSet( - SymbolTableObjectType* object, ExecState* exec, PropertyName propertyName, JSValue value, - bool shouldThrowReadOnlyError, bool ignoreReadOnlyErrors) -{ - WatchpointSet* set = nullptr; - unsigned attributes = 0; - bool result = symbolTablePut<SymbolTablePutMode::WithoutAttributes>(object, exec, propertyName, value, attributes, shouldThrowReadOnlyError, ignoreReadOnlyErrors, set); - if (set) - set->invalidate(VariableWriteFireDetail(object, propertyName)); // Don't mess around - if we had found this statically, we would have invalidated it. - return result; -} - -template<typename SymbolTableObjectType> -inline bool symbolTablePutWithAttributesTouchWatchpointSet( - SymbolTableObjectType* object, ExecState* exec, PropertyName propertyName, +inline bool symbolTablePutWithAttributes( + SymbolTableObjectType* object, VM& vm, PropertyName propertyName, JSValue value, unsigned attributes) { - WatchpointSet* set = nullptr; - bool shouldThrowReadOnlyError = false; - bool ignoreReadOnlyErrors = true; - bool result = symbolTablePut<SymbolTablePutMode::WithAttributes>(object, exec, propertyName, value, attributes, shouldThrowReadOnlyError, ignoreReadOnlyErrors, set); - if (set) - VariableWriteFireDetail::touch(set, object, propertyName); - return result; + ASSERT(!Heap::heap(value) || Heap::heap(value) == Heap::heap(object)); + + WriteBarrierBase<Unknown>* reg; + { + SymbolTable& symbolTable = *object->symbolTable(); + ConcurrentJITLocker locker(symbolTable.m_lock); + SymbolTable::Map::iterator iter = symbolTable.find(locker, propertyName.publicName()); + if (iter == symbolTable.end(locker)) + return false; + SymbolTableEntry& entry = iter->value; + ASSERT(!entry.isNull()); + if (VariableWatchpointSet* set = entry.watchpointSet()) + set->notifyWrite(value); + entry.setAttributes(attributes); + reg = &object->registerAt(entry.getIndex()); + } + reg->set(vm, object, value); + return true; } } // namespace JSC |