De-virtualize JSObject::defaultValue
authormhahnenberg@apple.com <mhahnenberg@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Tue, 1 Nov 2011 01:15:06 +0000 (01:15 +0000)
committermhahnenberg@apple.com <mhahnenberg@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Tue, 1 Nov 2011 01:15:06 +0000 (01:15 +0000)
https://bugs.webkit.org/show_bug.cgi?id=71146

Reviewed by Sam Weinig.

Source/JavaScriptCore:

Added defaultValue to the MethodTable.  Replaced all virtual versions of
defaultValue with static versions.  Replaced all call sites with lookups in the
MethodTable.

* JavaScriptCore.exp:
* JavaScriptCore.vcproj/JavaScriptCore/JavaScriptCore.def:
* runtime/ClassInfo.h:
* runtime/ExceptionHelpers.cpp:
(JSC::InterruptedExecutionError::defaultValue):
(JSC::TerminatedExecutionError::defaultValue):
* runtime/ExceptionHelpers.h:
* runtime/JSCell.cpp:
(JSC::JSCell::defaultValue):
* runtime/JSCell.h:
* runtime/JSNotAnObject.cpp:
(JSC::JSNotAnObject::defaultValue):
* runtime/JSNotAnObject.h:
* runtime/JSObject.cpp:
(JSC::JSObject::getPrimitiveNumber):
(JSC::JSObject::defaultValue):
* runtime/JSObject.h:
(JSC::JSObject::toPrimitive):

Source/WebCore:

No new tests.

Added defaultValue to the MethodTable.  Replaced all virtual versions of
defaultValue with static versions.  Replaced all call sites with lookups in the
MethodTable.

* WebCore.exp.in:
* bridge/objc/objc_runtime.h:
* bridge/objc/objc_runtime.mm:
(JSC::Bindings::ObjcFallbackObjectImp::defaultValue):
* bridge/runtime_object.cpp:
(JSC::Bindings::RuntimeObject::defaultValue):
* bridge/runtime_object.h:

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@98932 268f45cc-cd09-0410-ab3c-d52691b4dbfc

18 files changed:
Source/JavaScriptCore/ChangeLog
Source/JavaScriptCore/JavaScriptCore.exp
Source/JavaScriptCore/JavaScriptCore.vcproj/JavaScriptCore/JavaScriptCore.def
Source/JavaScriptCore/runtime/ClassInfo.h
Source/JavaScriptCore/runtime/ExceptionHelpers.cpp
Source/JavaScriptCore/runtime/ExceptionHelpers.h
Source/JavaScriptCore/runtime/JSCell.cpp
Source/JavaScriptCore/runtime/JSCell.h
Source/JavaScriptCore/runtime/JSNotAnObject.cpp
Source/JavaScriptCore/runtime/JSNotAnObject.h
Source/JavaScriptCore/runtime/JSObject.cpp
Source/JavaScriptCore/runtime/JSObject.h
Source/WebCore/ChangeLog
Source/WebCore/WebCore.exp.in
Source/WebCore/bridge/objc/objc_runtime.h
Source/WebCore/bridge/objc/objc_runtime.mm
Source/WebCore/bridge/runtime_object.cpp
Source/WebCore/bridge/runtime_object.h

index 827f4ef..b7a312d 100644 (file)
@@ -1,5 +1,35 @@
 2011-10-31  Mark Hahnenberg  <mhahnenberg@apple.com>
 
+        De-virtualize JSObject::defaultValue
+        https://bugs.webkit.org/show_bug.cgi?id=71146
+
+        Reviewed by Sam Weinig.
+
+        Added defaultValue to the MethodTable.  Replaced all virtual versions of 
+        defaultValue with static versions.  Replaced all call sites with lookups in the 
+        MethodTable.
+
+        * JavaScriptCore.exp:
+        * JavaScriptCore.vcproj/JavaScriptCore/JavaScriptCore.def:
+        * runtime/ClassInfo.h:
+        * runtime/ExceptionHelpers.cpp:
+        (JSC::InterruptedExecutionError::defaultValue):
+        (JSC::TerminatedExecutionError::defaultValue):
+        * runtime/ExceptionHelpers.h:
+        * runtime/JSCell.cpp:
+        (JSC::JSCell::defaultValue):
+        * runtime/JSCell.h:
+        * runtime/JSNotAnObject.cpp:
+        (JSC::JSNotAnObject::defaultValue):
+        * runtime/JSNotAnObject.h:
+        * runtime/JSObject.cpp:
+        (JSC::JSObject::getPrimitiveNumber):
+        (JSC::JSObject::defaultValue):
+        * runtime/JSObject.h:
+        (JSC::JSObject::toPrimitive):
+
+2011-10-31  Mark Hahnenberg  <mhahnenberg@apple.com>
+
         Interpreter build fix
 
         Unreviewed build fix
index ed10f67..4d2b371 100644 (file)
@@ -304,6 +304,7 @@ __ZN3JSC8DebuggerD2Ev
 __ZN3JSC8JSObject10putByIndexEPNS_6JSCellEPNS_9ExecStateEjNS_7JSValueE
 __ZN3JSC8JSObject11hasInstanceEPNS_9ExecStateENS_7JSValueES3_
 __ZN3JSC8JSObject12defineGetterEPS0_PNS_9ExecStateERKNS_10IdentifierES1_j
+__ZN3JSC8JSObject12defaultValueEPKS0_PNS_9ExecStateENS_22PreferredPrimitiveTypeE
 __ZN3JSC8JSObject12defineSetterEPNS_9ExecStateERKNS_10IdentifierEPS0_j
 __ZN3JSC8JSObject12lookupGetterEPNS_9ExecStateERKNS_10IdentifierE
 __ZN3JSC8JSObject12lookupSetterEPNS_9ExecStateERKNS_10IdentifierE
@@ -565,7 +566,6 @@ __ZNK3JSC7UString4utf8Eb
 __ZNK3JSC7UString5asciiEv
 __ZNK3JSC8JSObject11hasPropertyEPNS_9ExecStateERKNS_10IdentifierE
 __ZNK3JSC8JSObject11hasPropertyEPNS_9ExecStateEj
-__ZNK3JSC8JSObject12defaultValueEPNS_9ExecStateENS_22PreferredPrimitiveTypeE
 __ZNK3JSC8JSObject8toNumberEPNS_9ExecStateE
 __ZNK3JSC8JSObject8toStringEPNS_9ExecStateE
 __ZNK3JSC8JSObject9classNameEv
index f0ddf34..f2ca648 100644 (file)
@@ -133,7 +133,7 @@ EXPORTS
     ?dayInYear@WTF@@YAHNH@Z
     ?decrement@RefCountedLeakCounter@WTF@@QAEXXZ
     ?defaultAttributes@PropertyDescriptor@JSC@@0IA
-    ?defaultValue@JSObject@JSC@@UBE?AVJSValue@2@PAVExecState@2@W4PreferredPrimitiveType@2@@Z
+    ?defaultValue@JSObject@JSC@@SA?AVJSValue@2@PBV12@PAVExecState@2@W4PreferredPrimitiveType@2@@Z
     ?defineOwnProperty@JSObject@JSC@@UAE_NPAVExecState@2@ABVIdentifier@2@AAVPropertyDescriptor@2@_N@Z
     ?defineGetter@JSGlobalObject@JSC@@SAXPAVJSObject@2@PAVExecState@2@ABVIdentifier@2@0I@Z
     ?defineGetter@JSObject@JSC@@SAXPAV12@PAVExecState@2@ABVIdentifier@2@0I@Z
index d218687..d8e7170 100644 (file)
@@ -64,6 +64,9 @@ namespace JSC {
 
         typedef void (*DefineGetterFunctionPtr)(JSObject*, ExecState*, const Identifier&, JSObject*, unsigned);
         DefineGetterFunctionPtr defineGetter;
+
+        typedef JSValue (*DefaultValueFunctionPtr)(const JSObject*, ExecState*, PreferredPrimitiveType);
+        DefaultValueFunctionPtr defaultValue;
     };
 
 #define CREATE_MEMBER_CHECKER(member) \
@@ -97,6 +100,7 @@ struct MemberCheck##member { \
         &ClassName::getOwnPropertySlotByIndex, \
         &ClassName::toThisObject, \
         &ClassName::defineGetter, \
+        &ClassName::defaultValue, \
     }, \
     sizeof(ClassName)
 
index 16481ba..d5ace80 100644 (file)
@@ -43,7 +43,7 @@ namespace JSC {
 
 const ClassInfo InterruptedExecutionError::s_info = { "InterruptedExecutionError", &Base::s_info, 0, 0, CREATE_METHOD_TABLE(InterruptedExecutionError) };
 
-JSValue InterruptedExecutionError::defaultValue(ExecState* exec, PreferredPrimitiveType hint) const
+JSValue InterruptedExecutionError::defaultValue(const JSObject*, ExecState* exec, PreferredPrimitiveType hint)
 {
     if (hint == PreferString)
         return jsNontrivialString(exec, "JavaScript execution exceeded timeout.");
@@ -68,7 +68,7 @@ bool isInterruptedExecutionException(JSValue value)
 
 const ClassInfo TerminatedExecutionError::s_info = { "TerminatedExecutionError", &Base::s_info, 0, 0, CREATE_METHOD_TABLE(TerminatedExecutionError) };
 
-JSValue TerminatedExecutionError::defaultValue(ExecState* exec, PreferredPrimitiveType hint) const
+JSValue TerminatedExecutionError::defaultValue(const JSObject*, ExecState* exec, PreferredPrimitiveType hint)
 {
     if (hint == PreferString)
         return jsNontrivialString(exec, "JavaScript execution terminated.");
index 62a001e..c222679 100644 (file)
@@ -62,7 +62,7 @@ private:
     {
     }
 
-    virtual JSValue defaultValue(ExecState*, PreferredPrimitiveType) const;
+    static JSValue defaultValue(const JSObject*, ExecState*, PreferredPrimitiveType);
 
 public:
     typedef JSNonFinalObject Base;
@@ -89,7 +89,7 @@ private:
     {
     }
 
-    virtual JSValue defaultValue(ExecState*, PreferredPrimitiveType) const;
+    static JSValue defaultValue(const JSObject*, ExecState*, PreferredPrimitiveType);
 
 public:
     typedef JSNonFinalObject Base;
index f3f7227..ffeccfc 100644 (file)
@@ -163,4 +163,10 @@ void JSCell::defineGetter(JSObject*, ExecState*, const Identifier&, JSObject*, u
     ASSERT_NOT_REACHED();
 }
 
+JSValue JSCell::defaultValue(const JSObject*, ExecState*, PreferredPrimitiveType)
+{
+    ASSERT_NOT_REACHED();
+    return jsUndefined();
+}
+
 } // namespace JSC
index 92b1660..aa77f79 100644 (file)
@@ -135,7 +135,8 @@ namespace JSC {
 
         // Dummy implementations of override-able static functions for classes to put in their MethodTable
         static NO_RETURN_DUE_TO_ASSERT void defineGetter(JSObject*, ExecState*, const Identifier&, JSObject*, unsigned);
-        
+        static JSValue defaultValue(const JSObject*, ExecState*, PreferredPrimitiveType);
+
     private:
         WriteBarrier<Structure> m_structure;
     };
index 310548f..61f6ba3 100644 (file)
@@ -39,7 +39,7 @@ ASSERT_CLASS_FITS_IN_CELL(JSNotAnObject);
 const ClassInfo JSNotAnObject::s_info = { "Object", &Base::s_info, 0, 0, CREATE_METHOD_TABLE(JSNotAnObject) };
 
 // JSValue methods
-JSValue JSNotAnObject::defaultValue(ExecState* exec, PreferredPrimitiveType) const
+JSValue JSNotAnObject::defaultValue(const JSObject*, ExecState* exec, PreferredPrimitiveType)
 {
     ASSERT_UNUSED(exec, exec->hadException());
     return jsNumber(0);
index df4cfa4..8922f92 100644 (file)
@@ -65,7 +65,7 @@ namespace JSC {
         static const unsigned StructureFlags = OverridesGetOwnPropertySlot | OverridesGetPropertyNames | JSObject::StructureFlags;
 
         // JSValue methods
-        virtual JSValue defaultValue(ExecState*, PreferredPrimitiveType) const;
+        static JSValue defaultValue(const JSObject*, ExecState*, PreferredPrimitiveType);
 
         // JSObject methods
         static bool getOwnPropertySlot(JSCell*, ExecState*, const Identifier& propertyName, PropertySlot&);
index 5369558..7f1093c 100644 (file)
@@ -308,27 +308,27 @@ static ALWAYS_INLINE JSValue callDefaultValueFunction(ExecState* exec, const JSO
 
 bool JSObject::getPrimitiveNumber(ExecState* exec, double& number, JSValue& result) const
 {
-    result = defaultValue(exec, PreferNumber);
+    result = methodTable()->defaultValue(this, exec, PreferNumber);
     number = result.toNumber(exec);
     return !result.isString();
 }
 
 // ECMA 8.6.2.6
-JSValue JSObject::defaultValue(ExecState* exec, PreferredPrimitiveType hint) const
+JSValue JSObject::defaultValue(const JSObject* object, ExecState* exec, PreferredPrimitiveType hint)
 {
     // Must call toString first for Date objects.
-    if ((hint == PreferString) || (hint != PreferNumber && prototype() == exec->lexicalGlobalObject()->datePrototype())) {
-        JSValue value = callDefaultValueFunction(exec, this, exec->propertyNames().toString);
+    if ((hint == PreferString) || (hint != PreferNumber && object->prototype() == exec->lexicalGlobalObject()->datePrototype())) {
+        JSValue value = callDefaultValueFunction(exec, object, exec->propertyNames().toString);
         if (value)
             return value;
-        value = callDefaultValueFunction(exec, this, exec->propertyNames().valueOf);
+        value = callDefaultValueFunction(exec, object, exec->propertyNames().valueOf);
         if (value)
             return value;
     } else {
-        JSValue value = callDefaultValueFunction(exec, this, exec->propertyNames().valueOf);
+        JSValue value = callDefaultValueFunction(exec, object, exec->propertyNames().valueOf);
         if (value)
             return value;
-        value = callDefaultValueFunction(exec, this, exec->propertyNames().toString);
+        value = callDefaultValueFunction(exec, object, exec->propertyNames().toString);
         if (value)
             return value;
     }
index 2328795..d65e5ad 100644 (file)
@@ -122,7 +122,7 @@ namespace JSC {
         static bool deleteProperty(JSCell*, ExecState*, const Identifier& propertyName);
         static bool deletePropertyByIndex(JSCell*, ExecState*, unsigned propertyName);
 
-        virtual JSValue defaultValue(ExecState*, PreferredPrimitiveType) const;
+        static JSValue defaultValue(const JSObject*, ExecState*, PreferredPrimitiveType);
 
         virtual bool hasInstance(ExecState*, JSValue, JSValue prototypeProperty);
 
@@ -774,7 +774,7 @@ inline void JSObject::transitionTo(JSGlobalData& globalData, Structure* newStruc
 
 inline JSValue JSObject::toPrimitive(ExecState* exec, PreferredPrimitiveType preferredType) const
 {
-    return defaultValue(exec, preferredType);
+    return methodTable()->defaultValue(this, exec, preferredType);
 }
 
 inline JSValue JSValue::get(ExecState* exec, const Identifier& propertyName) const
index 5a71d2f..2436c39 100644 (file)
@@ -1,3 +1,24 @@
+2011-10-31  Mark Hahnenberg  <mhahnenberg@apple.com>
+
+        De-virtualize JSObject::defaultValue
+        https://bugs.webkit.org/show_bug.cgi?id=71146
+
+        Reviewed by Sam Weinig.
+
+        No new tests.
+
+        Added defaultValue to the MethodTable.  Replaced all virtual versions of 
+        defaultValue with static versions.  Replaced all call sites with lookups in the 
+        MethodTable.
+
+        * WebCore.exp.in:
+        * bridge/objc/objc_runtime.h:
+        * bridge/objc/objc_runtime.mm:
+        (JSC::Bindings::ObjcFallbackObjectImp::defaultValue):
+        * bridge/runtime_object.cpp:
+        (JSC::Bindings::RuntimeObject::defaultValue):
+        * bridge/runtime_object.h:
+
 2011-10-31  Levi Weintraub  <leviw@chromium.org>
 
         Switch RoundedRect back to integers
index b8e088f..47c9c86 100644 (file)
@@ -1702,6 +1702,7 @@ __ZN3JSC13RuntimeMethod6s_infoE
 __ZN3JSC13RuntimeMethodC2EPNS_14JSGlobalObjectEPNS_9StructureERN3WTF6VectorIPNS_8Bindings6MethodELm0EEE
 __ZN3JSC8Bindings10RootObjectD1Ev
 __ZN3JSC8Bindings13RuntimeObject11getCallDataEPNS_6JSCellERNS_8CallDataE
+__ZN3JSC8Bindings13RuntimeObject12defaultValueEPKNS_8JSObjectEPNS_9ExecStateENS_22PreferredPrimitiveTypeE
 __ZN3JSC8Bindings13RuntimeObject14deletePropertyEPNS_6JSCellEPNS_9ExecStateERKNS_10IdentifierE
 __ZN3JSC8Bindings13RuntimeObject14finishCreationEPNS_14JSGlobalObjectE
 __ZN3JSC8Bindings13RuntimeObject16getConstructDataEPNS_6JSCellERNS_13ConstructDataE
@@ -1717,7 +1718,6 @@ __ZN3JSC8Bindings8InstanceC2EN3WTF10PassRefPtrINS0_10RootObjectEEE
 __ZN3JSC8Bindings8InstanceD2Ev
 __ZN7WebCore13IdentifierRep7isValidEPS0_
 __ZN7WebCore16ScriptController16createRootObjectEPv
-__ZNK3JSC8Bindings13RuntimeObject12defaultValueEPNS_9ExecStateENS_22PreferredPrimitiveTypeE
 __ZTVN3JSC13RuntimeMethodE
 #endif
 
index 08b6732..74d19e8 100644 (file)
@@ -128,7 +128,7 @@ private:
     static void put(JSCell*, ExecState*, const Identifier& propertyName, JSValue, PutPropertySlot&);
     static CallType getCallData(JSCell*, CallData&);
     static bool deleteProperty(JSCell*, ExecState*, const Identifier& propertyName);
-    virtual JSValue defaultValue(ExecState*, PreferredPrimitiveType) const;
+    static JSValue defaultValue(const JSObject*, ExecState*, PreferredPrimitiveType);
 
     virtual bool toBoolean(ExecState*) const;
 
index c4f2c5e..0c3979b 100644 (file)
@@ -270,9 +270,10 @@ bool ObjcFallbackObjectImp::deleteProperty(JSCell*, ExecState*, const Identifier
     return false;
 }
 
-JSValue ObjcFallbackObjectImp::defaultValue(ExecState* exec, PreferredPrimitiveType) const
+JSValue ObjcFallbackObjectImp::defaultValue(const JSObject* object, ExecState* exec, PreferredPrimitiveType)
 {
-    return _instance->getValueOfUndefinedField(exec, _item);
+    const ObjcFallbackObjectImp* thisObject = static_cast<const ObjcFallbackObjectImp*>(object);
+    return thisObject->_instance->getValueOfUndefinedField(exec, thisObject->_item);
 }
 
 bool ObjcFallbackObjectImp::toBoolean(ExecState *) const
index 0dcf74d..7c9e4eb 100644 (file)
@@ -238,12 +238,13 @@ bool RuntimeObject::deleteProperty(JSCell*, ExecState*, const Identifier&)
     return false;
 }
 
-JSValue RuntimeObject::defaultValue(ExecState* exec, PreferredPrimitiveType hint) const
+JSValue RuntimeObject::defaultValue(const JSObject* object, ExecState* exec, PreferredPrimitiveType hint)
 {
-    if (!m_instance)
+    const RuntimeObject* thisObject = static_cast<const RuntimeObject*>(object);
+    if (!thisObject->m_instance)
         return throwInvalidAccessError(exec);
     
-    RefPtr<Instance> instance = m_instance;
+    RefPtr<Instance> instance = thisObject->m_instance;
 
     instance->begin();
     JSValue result = instance->defaultValue(exec, hint);
index d1f54f9..b25cd57 100644 (file)
@@ -49,7 +49,7 @@ public:
     virtual bool getOwnPropertyDescriptor(ExecState*, const Identifier& propertyName, PropertyDescriptor&);
     static void put(JSCell*, ExecState*, const Identifier& propertyName, JSValue, PutPropertySlot&);
     static bool deleteProperty(JSCell*, ExecState*, const Identifier& propertyName);
-    virtual JSValue defaultValue(ExecState*, PreferredPrimitiveType) const;
+    static JSValue defaultValue(const JSObject*, ExecState*, PreferredPrimitiveType);
     static CallType getCallData(JSCell*, CallData&);
     static ConstructType getConstructData(JSCell*, ConstructData&);