JIT call inline caches should cache calls to objects with getCallData/getConstructDat...
authorutatane.tea@gmail.com <utatane.tea@gmail.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Mon, 6 Nov 2017 14:40:08 +0000 (14:40 +0000)
committerutatane.tea@gmail.com <utatane.tea@gmail.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Mon, 6 Nov 2017 14:40:08 +0000 (14:40 +0000)
https://bugs.webkit.org/show_bug.cgi?id=144458

Reviewed by Saam Barati.

JSTests:

* microbenchmarks/dfg-internal-function-call.js: Added.
(target):
* microbenchmarks/dfg-internal-function-construct.js: Added.
(target):
* microbenchmarks/dfg-internal-function-not-handled-call.js: Added.
(target):
* microbenchmarks/dfg-internal-function-not-handled-construct.js: Added.
(target):
* stress/dfg-internal-function-call.js: Added.
(shouldBe):
(target):
* stress/dfg-internal-function-construct.js: Added.
(shouldBe):
(target):
* stress/internal-function-call.js: Added.
(shouldBe):
* stress/internal-function-construct.js: Added.
(shouldBe):

Source/JavaScriptCore:

Previously only JSFunction is handled by CallLinkInfo's caching mechanism. This means that
InternalFunction calls are not cached and they always go to the slow path. This is not good because

1. We need to query getCallData/getConstructData every time in the slow path.
2. CallLinkInfo tells nothing in the higher tier JITs.

This patch starts handling InternalFunction in CallLinkInfo's caching mechanism. We change InternalFunction
to hold pointers to the functions for call and construct. We have new stubs that can call/construct
InternalFunction. And we return this code pointer as a result of setup call to use CallLinkInfo mechanism.

This patch is critical to optimizing derived Array construction[1] since it starts using CallLinkInfo
for InternalFunction. Previously we did not record any information to CallLinkInfo. Except for the
case that DFGByteCodeParser figures out InternalFunction constant, we cannot attempt to emit DFG
nodes for these InternalFunctions since CallLinkInfo tells us nothing.

Attached microbenchmarks show performance improvement.

                                                   baseline                  patched

dfg-internal-function-construct                 1.6439+-0.0826     ^      1.2829+-0.0727        ^ definitely 1.2813x faster
dfg-internal-function-not-handled-construct     2.1862+-0.1361            2.0696+-0.1201          might be 1.0564x faster
dfg-internal-function-not-handled-call         20.7592+-0.9085           19.7369+-0.7921          might be 1.0518x faster
dfg-internal-function-call                      1.6856+-0.0967     ^      1.2771+-0.0744        ^ definitely 1.3198x faster

[1]: https://bugs.webkit.org/show_bug.cgi?id=178064

* API/JSCallbackFunction.cpp:
(JSC::JSCallbackFunction::JSCallbackFunction):
(JSC::JSCallbackFunction::getCallData): Deleted.
* API/JSCallbackFunction.h:
(JSC::JSCallbackFunction::createStructure):
* API/ObjCCallbackFunction.h:
(JSC::ObjCCallbackFunction::createStructure):
* API/ObjCCallbackFunction.mm:
(JSC::ObjCCallbackFunction::ObjCCallbackFunction):
(JSC::ObjCCallbackFunction::getCallData): Deleted.
(JSC::ObjCCallbackFunction::getConstructData): Deleted.
* bytecode/BytecodeDumper.cpp:
(JSC::BytecodeDumper<Block>::printCallOp):
* bytecode/BytecodeList.json:
* bytecode/CallLinkInfo.cpp:
(JSC::CallLinkInfo::setCallee):
(JSC::CallLinkInfo::callee):
(JSC::CallLinkInfo::setLastSeenCallee):
(JSC::CallLinkInfo::lastSeenCallee):
(JSC::CallLinkInfo::visitWeak):
* bytecode/CallLinkInfo.h:
* bytecode/CallLinkStatus.cpp:
(JSC::CallLinkStatus::computeFromCallLinkInfo):
* bytecode/LLIntCallLinkInfo.h:
* jit/JITOperations.cpp:
* jit/JITThunks.cpp:
(JSC::JITThunks::ctiInternalFunctionCall):
(JSC::JITThunks::ctiInternalFunctionConstruct):
* jit/JITThunks.h:
* jit/Repatch.cpp:
(JSC::linkFor):
(JSC::linkPolymorphicCall):
* jit/Repatch.h:
* jit/ThunkGenerators.cpp:
(JSC::virtualThunkFor):
(JSC::nativeForGenerator):
(JSC::nativeCallGenerator):
(JSC::nativeTailCallGenerator):
(JSC::nativeTailCallWithoutSavedTagsGenerator):
(JSC::nativeConstructGenerator):
(JSC::internalFunctionCallGenerator):
(JSC::internalFunctionConstructGenerator):
* jit/ThunkGenerators.h:
* llint/LLIntSlowPaths.cpp:
(JSC::LLInt::setUpCall):
* llint/LowLevelInterpreter.asm:
* llint/LowLevelInterpreter32_64.asm:
* llint/LowLevelInterpreter64.asm:
* runtime/ArrayConstructor.cpp:
(JSC::ArrayConstructor::ArrayConstructor):
(JSC::ArrayConstructor::getConstructData): Deleted.
(JSC::ArrayConstructor::getCallData): Deleted.
* runtime/ArrayConstructor.h:
(JSC::ArrayConstructor::createStructure):
* runtime/AsyncFunctionConstructor.cpp:
(JSC::AsyncFunctionConstructor::AsyncFunctionConstructor):
(JSC::AsyncFunctionConstructor::finishCreation):
(JSC::AsyncFunctionConstructor::getCallData): Deleted.
(JSC::AsyncFunctionConstructor::getConstructData): Deleted.
* runtime/AsyncFunctionConstructor.h:
(JSC::AsyncFunctionConstructor::createStructure):
* runtime/AsyncGeneratorFunctionConstructor.cpp:
(JSC::AsyncGeneratorFunctionConstructor::AsyncGeneratorFunctionConstructor):
(JSC::AsyncGeneratorFunctionConstructor::finishCreation):
(JSC::AsyncGeneratorFunctionConstructor::getCallData): Deleted.
(JSC::AsyncGeneratorFunctionConstructor::getConstructData): Deleted.
* runtime/AsyncGeneratorFunctionConstructor.h:
(JSC::AsyncGeneratorFunctionConstructor::createStructure):
* runtime/BooleanConstructor.cpp:
(JSC::callBooleanConstructor):
(JSC::BooleanConstructor::BooleanConstructor):
(JSC::BooleanConstructor::finishCreation):
(JSC::BooleanConstructor::getConstructData): Deleted.
(JSC::BooleanConstructor::getCallData): Deleted.
* runtime/BooleanConstructor.h:
(JSC::BooleanConstructor::createStructure):
* runtime/DateConstructor.cpp:
(JSC::DateConstructor::DateConstructor):
(JSC::DateConstructor::getConstructData): Deleted.
(JSC::DateConstructor::getCallData): Deleted.
* runtime/DateConstructor.h:
(JSC::DateConstructor::createStructure):
* runtime/Error.h:
(JSC::StrictModeTypeErrorFunction::StrictModeTypeErrorFunction):
(JSC::StrictModeTypeErrorFunction::createStructure):
(JSC::StrictModeTypeErrorFunction::getConstructData): Deleted.
(JSC::StrictModeTypeErrorFunction::getCallData): Deleted.
* runtime/ErrorConstructor.cpp:
(JSC::ErrorConstructor::ErrorConstructor):
(JSC::ErrorConstructor::getConstructData): Deleted.
(JSC::ErrorConstructor::getCallData): Deleted.
* runtime/ErrorConstructor.h:
(JSC::ErrorConstructor::createStructure):
* runtime/FunctionConstructor.cpp:
(JSC::FunctionConstructor::FunctionConstructor):
(JSC::FunctionConstructor::finishCreation):
(JSC::FunctionConstructor::getConstructData): Deleted.
(JSC::FunctionConstructor::getCallData): Deleted.
* runtime/FunctionConstructor.h:
(JSC::FunctionConstructor::createStructure):
* runtime/FunctionPrototype.cpp:
(JSC::callFunctionPrototype):
(JSC::FunctionPrototype::FunctionPrototype):
(JSC::FunctionPrototype::getCallData): Deleted.
* runtime/FunctionPrototype.h:
(JSC::FunctionPrototype::createStructure):
* runtime/GeneratorFunctionConstructor.cpp:
(JSC::GeneratorFunctionConstructor::GeneratorFunctionConstructor):
(JSC::GeneratorFunctionConstructor::finishCreation):
(JSC::GeneratorFunctionConstructor::getCallData): Deleted.
(JSC::GeneratorFunctionConstructor::getConstructData): Deleted.
* runtime/GeneratorFunctionConstructor.h:
(JSC::GeneratorFunctionConstructor::createStructure):
* runtime/InternalFunction.cpp:
(JSC::InternalFunction::InternalFunction):
(JSC::InternalFunction::finishCreation):
(JSC::InternalFunction::getCallData):
(JSC::InternalFunction::getConstructData):
* runtime/InternalFunction.h:
(JSC::InternalFunction::createStructure):
(JSC::InternalFunction::nativeFunctionFor):
(JSC::InternalFunction::offsetOfNativeFunctionFor):
* runtime/IntlCollatorConstructor.cpp:
(JSC::IntlCollatorConstructor::createStructure):
(JSC::IntlCollatorConstructor::IntlCollatorConstructor):
(JSC::IntlCollatorConstructor::getConstructData): Deleted.
(JSC::IntlCollatorConstructor::getCallData): Deleted.
* runtime/IntlCollatorConstructor.h:
* runtime/IntlDateTimeFormatConstructor.cpp:
(JSC::IntlDateTimeFormatConstructor::createStructure):
(JSC::IntlDateTimeFormatConstructor::IntlDateTimeFormatConstructor):
(JSC::IntlDateTimeFormatConstructor::getConstructData): Deleted.
(JSC::IntlDateTimeFormatConstructor::getCallData): Deleted.
* runtime/IntlDateTimeFormatConstructor.h:
* runtime/IntlNumberFormatConstructor.cpp:
(JSC::IntlNumberFormatConstructor::createStructure):
(JSC::IntlNumberFormatConstructor::IntlNumberFormatConstructor):
(JSC::IntlNumberFormatConstructor::getConstructData): Deleted.
(JSC::IntlNumberFormatConstructor::getCallData): Deleted.
* runtime/IntlNumberFormatConstructor.h:
* runtime/JSArrayBufferConstructor.cpp:
(JSC::JSArrayBufferConstructor::JSArrayBufferConstructor):
(JSC::JSArrayBufferConstructor::createStructure):
(JSC::JSArrayBufferConstructor::getConstructData): Deleted.
(JSC::JSArrayBufferConstructor::getCallData): Deleted.
* runtime/JSArrayBufferConstructor.h:
* runtime/JSGenericTypedArrayViewConstructor.h:
* runtime/JSGenericTypedArrayViewConstructorInlines.h:
(JSC::JSGenericTypedArrayViewConstructor<ViewClass>::JSGenericTypedArrayViewConstructor):
(JSC::JSGenericTypedArrayViewConstructor<ViewClass>::createStructure):
(JSC::JSGenericTypedArrayViewConstructor<ViewClass>::getConstructData): Deleted.
(JSC::JSGenericTypedArrayViewConstructor<ViewClass>::getCallData): Deleted.
* runtime/JSInternalPromiseConstructor.cpp:
(JSC::JSInternalPromiseConstructor::createStructure):
(JSC::JSInternalPromiseConstructor::JSInternalPromiseConstructor):
(JSC::JSInternalPromiseConstructor::getConstructData): Deleted.
(JSC::JSInternalPromiseConstructor::getCallData): Deleted.
* runtime/JSInternalPromiseConstructor.h:
* runtime/JSPromiseConstructor.cpp:
(JSC::JSPromiseConstructor::createStructure):
(JSC::JSPromiseConstructor::JSPromiseConstructor):
(JSC::JSPromiseConstructor::getConstructData): Deleted.
(JSC::JSPromiseConstructor::getCallData): Deleted.
* runtime/JSPromiseConstructor.h:
* runtime/JSType.h:
* runtime/JSTypedArrayViewConstructor.cpp:
(JSC::JSTypedArrayViewConstructor::JSTypedArrayViewConstructor):
(JSC::JSTypedArrayViewConstructor::createStructure):
(JSC::JSTypedArrayViewConstructor::getConstructData): Deleted.
(JSC::JSTypedArrayViewConstructor::getCallData): Deleted.
* runtime/JSTypedArrayViewConstructor.h:
* runtime/MapConstructor.cpp:
(JSC::MapConstructor::MapConstructor):
(JSC::MapConstructor::getConstructData): Deleted.
(JSC::MapConstructor::getCallData): Deleted.
* runtime/MapConstructor.h:
(JSC::MapConstructor::createStructure):
(JSC::MapConstructor::MapConstructor): Deleted.
* runtime/NativeErrorConstructor.cpp:
(JSC::NativeErrorConstructor::NativeErrorConstructor):
(JSC::NativeErrorConstructor::getConstructData): Deleted.
(JSC::NativeErrorConstructor::getCallData): Deleted.
* runtime/NativeErrorConstructor.h:
(JSC::NativeErrorConstructor::createStructure):
* runtime/NullGetterFunction.cpp:
(JSC::NullGetterFunction::NullGetterFunction):
(JSC::NullGetterFunction::getCallData): Deleted.
(JSC::NullGetterFunction::getConstructData): Deleted.
* runtime/NullGetterFunction.h:
(JSC::NullGetterFunction::createStructure):
(JSC::NullGetterFunction::NullGetterFunction): Deleted.
* runtime/NullSetterFunction.cpp:
(JSC::NullSetterFunction::NullSetterFunction):
(JSC::NullSetterFunction::getCallData): Deleted.
(JSC::NullSetterFunction::getConstructData): Deleted.
* runtime/NullSetterFunction.h:
(JSC::NullSetterFunction::createStructure):
(JSC::NullSetterFunction::NullSetterFunction): Deleted.
* runtime/NumberConstructor.cpp:
(JSC::NumberConstructor::NumberConstructor):
(JSC::constructNumberConstructor):
(JSC::constructWithNumberConstructor): Deleted.
(JSC::NumberConstructor::getConstructData): Deleted.
(JSC::NumberConstructor::getCallData): Deleted.
* runtime/NumberConstructor.h:
(JSC::NumberConstructor::createStructure):
* runtime/ObjectConstructor.cpp:
(JSC::ObjectConstructor::ObjectConstructor):
(JSC::ObjectConstructor::getConstructData): Deleted.
(JSC::ObjectConstructor::getCallData): Deleted.
* runtime/ObjectConstructor.h:
(JSC::ObjectConstructor::createStructure):
* runtime/ProxyConstructor.cpp:
(JSC::ProxyConstructor::ProxyConstructor):
(JSC::ProxyConstructor::getConstructData): Deleted.
(JSC::ProxyConstructor::getCallData): Deleted.
* runtime/ProxyConstructor.h:
(JSC::ProxyConstructor::createStructure):
* runtime/ProxyRevoke.cpp:
(JSC::ProxyRevoke::ProxyRevoke):
(JSC::ProxyRevoke::getCallData): Deleted.
* runtime/ProxyRevoke.h:
(JSC::ProxyRevoke::createStructure):
* runtime/RegExpConstructor.cpp:
(JSC::RegExpConstructor::RegExpConstructor):
(JSC::RegExpConstructor::getConstructData): Deleted.
(JSC::RegExpConstructor::getCallData): Deleted.
* runtime/RegExpConstructor.h:
(JSC::RegExpConstructor::createStructure):
* runtime/SetConstructor.cpp:
(JSC::SetConstructor::SetConstructor):
(JSC::SetConstructor::getConstructData): Deleted.
(JSC::SetConstructor::getCallData): Deleted.
* runtime/SetConstructor.h:
(JSC::SetConstructor::createStructure):
(JSC::SetConstructor::SetConstructor): Deleted.
* runtime/StringConstructor.cpp:
(JSC::StringConstructor::StringConstructor):
(JSC::StringConstructor::getConstructData): Deleted.
(JSC::StringConstructor::getCallData): Deleted.
* runtime/StringConstructor.h:
(JSC::StringConstructor::createStructure):
* runtime/SymbolConstructor.cpp:
(JSC::SymbolConstructor::SymbolConstructor):
(JSC::SymbolConstructor::getConstructData): Deleted.
(JSC::SymbolConstructor::getCallData): Deleted.
* runtime/SymbolConstructor.h:
(JSC::SymbolConstructor::createStructure):
* runtime/VM.cpp:
(JSC::VM::VM):
(JSC::VM::getCTIInternalFunctionTrampolineFor):
* runtime/VM.h:
* runtime/WeakMapConstructor.cpp:
(JSC::WeakMapConstructor::WeakMapConstructor):
(JSC::WeakMapConstructor::getConstructData): Deleted.
(JSC::WeakMapConstructor::getCallData): Deleted.
* runtime/WeakMapConstructor.h:
(JSC::WeakMapConstructor::createStructure):
(JSC::WeakMapConstructor::WeakMapConstructor): Deleted.
* runtime/WeakSetConstructor.cpp:
(JSC::WeakSetConstructor::WeakSetConstructor):
(JSC::WeakSetConstructor::getConstructData): Deleted.
(JSC::WeakSetConstructor::getCallData): Deleted.
* runtime/WeakSetConstructor.h:
(JSC::WeakSetConstructor::createStructure):
(JSC::WeakSetConstructor::WeakSetConstructor): Deleted.
* wasm/js/WebAssemblyCompileErrorConstructor.cpp:
(JSC::WebAssemblyCompileErrorConstructor::createStructure):
(JSC::WebAssemblyCompileErrorConstructor::WebAssemblyCompileErrorConstructor):
(JSC::WebAssemblyCompileErrorConstructor::getConstructData): Deleted.
(JSC::WebAssemblyCompileErrorConstructor::getCallData): Deleted.
* wasm/js/WebAssemblyCompileErrorConstructor.h:
* wasm/js/WebAssemblyInstanceConstructor.cpp:
(JSC::WebAssemblyInstanceConstructor::createStructure):
(JSC::WebAssemblyInstanceConstructor::WebAssemblyInstanceConstructor):
(JSC::WebAssemblyInstanceConstructor::getConstructData): Deleted.
(JSC::WebAssemblyInstanceConstructor::getCallData): Deleted.
* wasm/js/WebAssemblyInstanceConstructor.h:
* wasm/js/WebAssemblyLinkErrorConstructor.cpp:
(JSC::WebAssemblyLinkErrorConstructor::createStructure):
(JSC::WebAssemblyLinkErrorConstructor::WebAssemblyLinkErrorConstructor):
(JSC::WebAssemblyLinkErrorConstructor::getConstructData): Deleted.
(JSC::WebAssemblyLinkErrorConstructor::getCallData): Deleted.
* wasm/js/WebAssemblyLinkErrorConstructor.h:
* wasm/js/WebAssemblyMemoryConstructor.cpp:
(JSC::WebAssemblyMemoryConstructor::createStructure):
(JSC::WebAssemblyMemoryConstructor::WebAssemblyMemoryConstructor):
(JSC::WebAssemblyMemoryConstructor::getConstructData): Deleted.
(JSC::WebAssemblyMemoryConstructor::getCallData): Deleted.
* wasm/js/WebAssemblyMemoryConstructor.h:
* wasm/js/WebAssemblyModuleConstructor.cpp:
(JSC::WebAssemblyModuleConstructor::createStructure):
(JSC::WebAssemblyModuleConstructor::WebAssemblyModuleConstructor):
(JSC::WebAssemblyModuleConstructor::getConstructData): Deleted.
(JSC::WebAssemblyModuleConstructor::getCallData): Deleted.
* wasm/js/WebAssemblyModuleConstructor.h:
* wasm/js/WebAssemblyRuntimeErrorConstructor.cpp:
(JSC::WebAssemblyRuntimeErrorConstructor::createStructure):
(JSC::WebAssemblyRuntimeErrorConstructor::WebAssemblyRuntimeErrorConstructor):
(JSC::WebAssemblyRuntimeErrorConstructor::getConstructData): Deleted.
(JSC::WebAssemblyRuntimeErrorConstructor::getCallData): Deleted.
* wasm/js/WebAssemblyRuntimeErrorConstructor.h:
* wasm/js/WebAssemblyTableConstructor.cpp:
(JSC::WebAssemblyTableConstructor::createStructure):
(JSC::WebAssemblyTableConstructor::WebAssemblyTableConstructor):
(JSC::WebAssemblyTableConstructor::getConstructData): Deleted.
(JSC::WebAssemblyTableConstructor::getCallData): Deleted.
* wasm/js/WebAssemblyTableConstructor.h:

Source/WebCore:

* bridge/runtime_method.cpp:
(JSC::RuntimeMethod::RuntimeMethod):
(JSC::RuntimeMethod::getCallData): Deleted.
* bridge/runtime_method.h:

Source/WebKit:

* WebProcess/Plugins/Netscape/JSNPMethod.cpp:
(WebKit::JSNPMethod::JSNPMethod):
(WebKit::JSNPMethod::getCallData): Deleted.
* WebProcess/Plugins/Netscape/JSNPMethod.h:
(WebKit::JSNPMethod::createStructure):

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

122 files changed:
JSTests/ChangeLog
JSTests/microbenchmarks/dfg-internal-function-call.js [new file with mode: 0644]
JSTests/microbenchmarks/dfg-internal-function-construct.js [new file with mode: 0644]
JSTests/microbenchmarks/dfg-internal-function-not-handled-call.js [new file with mode: 0644]
JSTests/microbenchmarks/dfg-internal-function-not-handled-construct.js [new file with mode: 0644]
JSTests/stress/dfg-internal-function-call.js [new file with mode: 0644]
JSTests/stress/dfg-internal-function-construct.js [new file with mode: 0644]
JSTests/stress/internal-function-call.js [new file with mode: 0644]
JSTests/stress/internal-function-construct.js [new file with mode: 0644]
Source/JavaScriptCore/API/JSCallbackFunction.cpp
Source/JavaScriptCore/API/JSCallbackFunction.h
Source/JavaScriptCore/API/ObjCCallbackFunction.h
Source/JavaScriptCore/API/ObjCCallbackFunction.mm
Source/JavaScriptCore/ChangeLog
Source/JavaScriptCore/bytecode/BytecodeDumper.cpp
Source/JavaScriptCore/bytecode/BytecodeList.json
Source/JavaScriptCore/bytecode/CallLinkInfo.cpp
Source/JavaScriptCore/bytecode/CallLinkInfo.h
Source/JavaScriptCore/bytecode/CallLinkStatus.cpp
Source/JavaScriptCore/bytecode/LLIntCallLinkInfo.h
Source/JavaScriptCore/jit/JITOperations.cpp
Source/JavaScriptCore/jit/JITThunks.cpp
Source/JavaScriptCore/jit/JITThunks.h
Source/JavaScriptCore/jit/Repatch.cpp
Source/JavaScriptCore/jit/Repatch.h
Source/JavaScriptCore/jit/ThunkGenerators.cpp
Source/JavaScriptCore/jit/ThunkGenerators.h
Source/JavaScriptCore/llint/LLIntSlowPaths.cpp
Source/JavaScriptCore/llint/LowLevelInterpreter.asm
Source/JavaScriptCore/llint/LowLevelInterpreter32_64.asm
Source/JavaScriptCore/llint/LowLevelInterpreter64.asm
Source/JavaScriptCore/runtime/ArrayConstructor.cpp
Source/JavaScriptCore/runtime/ArrayConstructor.h
Source/JavaScriptCore/runtime/AsyncFunctionConstructor.cpp
Source/JavaScriptCore/runtime/AsyncFunctionConstructor.h
Source/JavaScriptCore/runtime/AsyncGeneratorFunctionConstructor.cpp
Source/JavaScriptCore/runtime/AsyncGeneratorFunctionConstructor.h
Source/JavaScriptCore/runtime/BooleanConstructor.cpp
Source/JavaScriptCore/runtime/BooleanConstructor.h
Source/JavaScriptCore/runtime/DateConstructor.cpp
Source/JavaScriptCore/runtime/DateConstructor.h
Source/JavaScriptCore/runtime/Error.h
Source/JavaScriptCore/runtime/ErrorConstructor.cpp
Source/JavaScriptCore/runtime/ErrorConstructor.h
Source/JavaScriptCore/runtime/FunctionConstructor.cpp
Source/JavaScriptCore/runtime/FunctionConstructor.h
Source/JavaScriptCore/runtime/FunctionPrototype.cpp
Source/JavaScriptCore/runtime/FunctionPrototype.h
Source/JavaScriptCore/runtime/GeneratorFunctionConstructor.cpp
Source/JavaScriptCore/runtime/GeneratorFunctionConstructor.h
Source/JavaScriptCore/runtime/InternalFunction.cpp
Source/JavaScriptCore/runtime/InternalFunction.h
Source/JavaScriptCore/runtime/IntlCollatorConstructor.cpp
Source/JavaScriptCore/runtime/IntlCollatorConstructor.h
Source/JavaScriptCore/runtime/IntlDateTimeFormatConstructor.cpp
Source/JavaScriptCore/runtime/IntlDateTimeFormatConstructor.h
Source/JavaScriptCore/runtime/IntlNumberFormatConstructor.cpp
Source/JavaScriptCore/runtime/IntlNumberFormatConstructor.h
Source/JavaScriptCore/runtime/JSArrayBufferConstructor.cpp
Source/JavaScriptCore/runtime/JSArrayBufferConstructor.h
Source/JavaScriptCore/runtime/JSGenericTypedArrayViewConstructor.h
Source/JavaScriptCore/runtime/JSGenericTypedArrayViewConstructorInlines.h
Source/JavaScriptCore/runtime/JSInternalPromiseConstructor.cpp
Source/JavaScriptCore/runtime/JSInternalPromiseConstructor.h
Source/JavaScriptCore/runtime/JSPromiseConstructor.cpp
Source/JavaScriptCore/runtime/JSPromiseConstructor.h
Source/JavaScriptCore/runtime/JSType.h
Source/JavaScriptCore/runtime/JSTypedArrayViewConstructor.cpp
Source/JavaScriptCore/runtime/JSTypedArrayViewConstructor.h
Source/JavaScriptCore/runtime/MapConstructor.cpp
Source/JavaScriptCore/runtime/MapConstructor.h
Source/JavaScriptCore/runtime/NativeErrorConstructor.cpp
Source/JavaScriptCore/runtime/NativeErrorConstructor.h
Source/JavaScriptCore/runtime/NullGetterFunction.cpp
Source/JavaScriptCore/runtime/NullGetterFunction.h
Source/JavaScriptCore/runtime/NullSetterFunction.cpp
Source/JavaScriptCore/runtime/NullSetterFunction.h
Source/JavaScriptCore/runtime/NumberConstructor.cpp
Source/JavaScriptCore/runtime/NumberConstructor.h
Source/JavaScriptCore/runtime/ObjectConstructor.cpp
Source/JavaScriptCore/runtime/ObjectConstructor.h
Source/JavaScriptCore/runtime/ProxyConstructor.cpp
Source/JavaScriptCore/runtime/ProxyConstructor.h
Source/JavaScriptCore/runtime/ProxyRevoke.cpp
Source/JavaScriptCore/runtime/ProxyRevoke.h
Source/JavaScriptCore/runtime/RegExpConstructor.cpp
Source/JavaScriptCore/runtime/RegExpConstructor.h
Source/JavaScriptCore/runtime/SetConstructor.cpp
Source/JavaScriptCore/runtime/SetConstructor.h
Source/JavaScriptCore/runtime/StringConstructor.cpp
Source/JavaScriptCore/runtime/StringConstructor.h
Source/JavaScriptCore/runtime/SymbolConstructor.cpp
Source/JavaScriptCore/runtime/SymbolConstructor.h
Source/JavaScriptCore/runtime/VM.cpp
Source/JavaScriptCore/runtime/VM.h
Source/JavaScriptCore/runtime/WeakMapConstructor.cpp
Source/JavaScriptCore/runtime/WeakMapConstructor.h
Source/JavaScriptCore/runtime/WeakSetConstructor.cpp
Source/JavaScriptCore/runtime/WeakSetConstructor.h
Source/JavaScriptCore/wasm/js/WebAssemblyCompileErrorConstructor.cpp
Source/JavaScriptCore/wasm/js/WebAssemblyCompileErrorConstructor.h
Source/JavaScriptCore/wasm/js/WebAssemblyInstanceConstructor.cpp
Source/JavaScriptCore/wasm/js/WebAssemblyInstanceConstructor.h
Source/JavaScriptCore/wasm/js/WebAssemblyLinkErrorConstructor.cpp
Source/JavaScriptCore/wasm/js/WebAssemblyLinkErrorConstructor.h
Source/JavaScriptCore/wasm/js/WebAssemblyMemoryConstructor.cpp
Source/JavaScriptCore/wasm/js/WebAssemblyMemoryConstructor.h
Source/JavaScriptCore/wasm/js/WebAssemblyModuleConstructor.cpp
Source/JavaScriptCore/wasm/js/WebAssemblyModuleConstructor.h
Source/JavaScriptCore/wasm/js/WebAssemblyRuntimeErrorConstructor.cpp
Source/JavaScriptCore/wasm/js/WebAssemblyRuntimeErrorConstructor.h
Source/JavaScriptCore/wasm/js/WebAssemblyTableConstructor.cpp
Source/JavaScriptCore/wasm/js/WebAssemblyTableConstructor.h
Source/WebCore/ChangeLog
Source/WebCore/bridge/c/c_instance.cpp
Source/WebCore/bridge/objc/objc_instance.mm
Source/WebCore/bridge/runtime_method.cpp
Source/WebCore/bridge/runtime_method.h
Source/WebKit/ChangeLog
Source/WebKit/WebProcess/Plugins/Netscape/JSNPMethod.cpp
Source/WebKit/WebProcess/Plugins/Netscape/JSNPMethod.h
Source/WebKitLegacy/mac/Plugins/Hosted/ProxyInstance.mm

index 5fd124a..c921790 100644 (file)
@@ -1,3 +1,29 @@
+2017-11-05  Yusuke Suzuki  <utatane.tea@gmail.com>
+
+        JIT call inline caches should cache calls to objects with getCallData/getConstructData traps
+        https://bugs.webkit.org/show_bug.cgi?id=144458
+
+        Reviewed by Saam Barati.
+
+        * microbenchmarks/dfg-internal-function-call.js: Added.
+        (target):
+        * microbenchmarks/dfg-internal-function-construct.js: Added.
+        (target):
+        * microbenchmarks/dfg-internal-function-not-handled-call.js: Added.
+        (target):
+        * microbenchmarks/dfg-internal-function-not-handled-construct.js: Added.
+        (target):
+        * stress/dfg-internal-function-call.js: Added.
+        (shouldBe):
+        (target):
+        * stress/dfg-internal-function-construct.js: Added.
+        (shouldBe):
+        (target):
+        * stress/internal-function-call.js: Added.
+        (shouldBe):
+        * stress/internal-function-construct.js: Added.
+        (shouldBe):
+
 2017-11-05  Per Arne Vollan  <pvollan@apple.com>
 
         [Win] Skip stress/regress-178385.js.
diff --git a/JSTests/microbenchmarks/dfg-internal-function-call.js b/JSTests/microbenchmarks/dfg-internal-function-call.js
new file mode 100644 (file)
index 0000000..009738b
--- /dev/null
@@ -0,0 +1,8 @@
+function target(func)
+{
+    return func();
+}
+noInline(target);
+
+for (var i = 0; i < 1e4; ++i)
+    target(Array);
diff --git a/JSTests/microbenchmarks/dfg-internal-function-construct.js b/JSTests/microbenchmarks/dfg-internal-function-construct.js
new file mode 100644 (file)
index 0000000..882a000
--- /dev/null
@@ -0,0 +1,8 @@
+function target(func)
+{
+    return new func();
+}
+noInline(target);
+
+for (var i = 0; i < 1e4; ++i)
+    target(Array);
diff --git a/JSTests/microbenchmarks/dfg-internal-function-not-handled-call.js b/JSTests/microbenchmarks/dfg-internal-function-not-handled-call.js
new file mode 100644 (file)
index 0000000..20b29b4
--- /dev/null
@@ -0,0 +1,8 @@
+function target(func)
+{
+    return func();
+}
+noInline(target);
+
+for (var i = 0; i < 1e4; ++i)
+    target(Date);
diff --git a/JSTests/microbenchmarks/dfg-internal-function-not-handled-construct.js b/JSTests/microbenchmarks/dfg-internal-function-not-handled-construct.js
new file mode 100644 (file)
index 0000000..e266bbe
--- /dev/null
@@ -0,0 +1,8 @@
+function target(func)
+{
+    return new func();
+}
+noInline(target);
+
+for (var i = 0; i < 1e4; ++i)
+    target(Date);
diff --git a/JSTests/stress/dfg-internal-function-call.js b/JSTests/stress/dfg-internal-function-call.js
new file mode 100644 (file)
index 0000000..d04852a
--- /dev/null
@@ -0,0 +1,14 @@
+function shouldBe(actual, expected) {
+    if (actual !== expected)
+        throw new Error('bad value: ' + actual);
+}
+noInline(shouldBe);
+
+function target(func)
+{
+    return func();
+}
+noInline(target);
+
+for (var i = 0; i < 1e4; ++i)
+    shouldBe(target(Array).length, 0);
diff --git a/JSTests/stress/dfg-internal-function-construct.js b/JSTests/stress/dfg-internal-function-construct.js
new file mode 100644 (file)
index 0000000..671942e
--- /dev/null
@@ -0,0 +1,14 @@
+function shouldBe(actual, expected) {
+    if (actual !== expected)
+        throw new Error('bad value: ' + actual);
+}
+noInline(shouldBe);
+
+function target(func)
+{
+    return new func();
+}
+noInline(target);
+
+for (var i = 0; i < 1e4; ++i)
+    shouldBe(target(Array).length, 0);
diff --git a/JSTests/stress/internal-function-call.js b/JSTests/stress/internal-function-call.js
new file mode 100644 (file)
index 0000000..ecbfa7b
--- /dev/null
@@ -0,0 +1,9 @@
+function shouldBe(actual, expected) {
+    if (actual !== expected)
+        throw new Error('bad value: ' + actual);
+}
+
+var func = Date;
+
+for (var i = 0; i < 1e4; ++i)
+    shouldBe(typeof func(), "string");
diff --git a/JSTests/stress/internal-function-construct.js b/JSTests/stress/internal-function-construct.js
new file mode 100644 (file)
index 0000000..9852b91
--- /dev/null
@@ -0,0 +1,12 @@
+function shouldBe(actual, expected) {
+    if (actual !== expected)
+        throw new Error('bad value: ' + actual);
+}
+
+var func = Date;
+
+for (var i = 0; i < 1e4; ++i) {
+    var date = new func();
+    shouldBe(typeof date, "object");
+    shouldBe(date instanceof Date, true);
+}
index 684ece6..78ca55b 100644 (file)
@@ -44,7 +44,7 @@ STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(JSCallbackFunction);
 const ClassInfo JSCallbackFunction::s_info = { "CallbackFunction", &InternalFunction::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(JSCallbackFunction) };
 
 JSCallbackFunction::JSCallbackFunction(VM& vm, Structure* structure, JSObjectCallAsFunctionCallback callback)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, APICallbackFunction::call<JSCallbackFunction>, nullptr)
     , m_callback(callback)
 {
 }
@@ -63,10 +63,4 @@ JSCallbackFunction* JSCallbackFunction::create(VM& vm, JSGlobalObject* globalObj
     return function;
 }
 
-CallType JSCallbackFunction::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = APICallbackFunction::call<JSCallbackFunction>;
-    return CallType::Host;
-}
-
 } // namespace JSC
index a4fdd06..4c54b80 100644 (file)
@@ -44,15 +44,13 @@ public:
     // refactor the code so this override isn't necessary
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue proto) 
     { 
-        return Structure::create(vm, globalObject, proto, TypeInfo(ObjectType, StructureFlags), info()); 
+        return Structure::create(vm, globalObject, proto, TypeInfo(InternalFunctionType, StructureFlags), info()); 
     }
 
 private:
     JSCallbackFunction(VM&, Structure*, JSObjectCallAsFunctionCallback);
     void finishCreation(VM&, const String& name);
 
-    static CallType getCallData(JSCell*, CallData&);
-
     JSObjectCallAsFunctionCallback functionCallback() { return m_callback; }
 
     JSObjectCallAsFunctionCallback m_callback;
index 4d5b736..dea6cc4 100644 (file)
@@ -54,7 +54,7 @@ public:
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
         ASSERT(globalObject);
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
     DECLARE_EXPORT_INFO;
@@ -65,9 +65,6 @@ protected:
     ObjCCallbackFunction(VM&, Structure*, JSObjectCallAsFunctionCallback, JSObjectCallAsConstructorCallback, std::unique_ptr<ObjCCallbackFunctionImpl>);
 
 private:
-    static CallType getCallData(JSCell*, CallData&);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-
     JSObjectCallAsFunctionCallback functionCallback() { return m_functionCallback; }
     JSObjectCallAsConstructorCallback constructCallback() { return m_constructCallback; }
 
index fb93a86..63f920e 100644 (file)
@@ -506,7 +506,7 @@ static JSObjectRef objCCallbackFunctionCallAsConstructor(JSContextRef callerCont
 const JSC::ClassInfo ObjCCallbackFunction::s_info = { "CallbackFunction", &Base::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(ObjCCallbackFunction) };
 
 ObjCCallbackFunction::ObjCCallbackFunction(JSC::VM& vm, JSC::Structure* structure, JSObjectCallAsFunctionCallback functionCallback, JSObjectCallAsConstructorCallback constructCallback, std::unique_ptr<ObjCCallbackFunctionImpl> impl)
-    : Base(vm, structure)
+    : Base(vm, structure, APICallbackFunction::call<ObjCCallbackFunction>, impl->isConstructible() ? APICallbackFunction::construct<ObjCCallbackFunction> : nullptr)
     , m_functionCallback(functionCallback)
     , m_constructCallback(constructCallback)
     , m_impl(WTFMove(impl))
@@ -528,22 +528,6 @@ void ObjCCallbackFunction::destroy(JSCell* cell)
     function.~ObjCCallbackFunction();
 }
 
-
-CallType ObjCCallbackFunction::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = APICallbackFunction::call<ObjCCallbackFunction>;
-    return CallType::Host;
-}
-
-ConstructType ObjCCallbackFunction::getConstructData(JSCell* cell, ConstructData& constructData)
-{
-    ObjCCallbackFunction* callback = jsCast<ObjCCallbackFunction*>(cell);
-    if (!callback->impl()->isConstructible())
-        return Base::getConstructData(cell, constructData);
-    constructData.native.function = APICallbackFunction::construct<ObjCCallbackFunction>;
-    return ConstructType::Host;
-}
-
 String ObjCCallbackFunctionImpl::name()
 {
     if (m_type == CallbackInitMethod)
index 7b79de0..7723e4c 100644 (file)
@@ -1,3 +1,345 @@
+2017-11-05  Yusuke Suzuki  <utatane.tea@gmail.com>
+
+        JIT call inline caches should cache calls to objects with getCallData/getConstructData traps
+        https://bugs.webkit.org/show_bug.cgi?id=144458
+
+        Reviewed by Saam Barati.
+
+        Previously only JSFunction is handled by CallLinkInfo's caching mechanism. This means that
+        InternalFunction calls are not cached and they always go to the slow path. This is not good because
+
+        1. We need to query getCallData/getConstructData every time in the slow path.
+        2. CallLinkInfo tells nothing in the higher tier JITs.
+
+        This patch starts handling InternalFunction in CallLinkInfo's caching mechanism. We change InternalFunction
+        to hold pointers to the functions for call and construct. We have new stubs that can call/construct
+        InternalFunction. And we return this code pointer as a result of setup call to use CallLinkInfo mechanism.
+
+        This patch is critical to optimizing derived Array construction[1] since it starts using CallLinkInfo
+        for InternalFunction. Previously we did not record any information to CallLinkInfo. Except for the
+        case that DFGByteCodeParser figures out InternalFunction constant, we cannot attempt to emit DFG
+        nodes for these InternalFunctions since CallLinkInfo tells us nothing.
+
+        Attached microbenchmarks show performance improvement.
+
+                                                           baseline                  patched
+
+        dfg-internal-function-construct                 1.6439+-0.0826     ^      1.2829+-0.0727        ^ definitely 1.2813x faster
+        dfg-internal-function-not-handled-construct     2.1862+-0.1361            2.0696+-0.1201          might be 1.0564x faster
+        dfg-internal-function-not-handled-call         20.7592+-0.9085           19.7369+-0.7921          might be 1.0518x faster
+        dfg-internal-function-call                      1.6856+-0.0967     ^      1.2771+-0.0744        ^ definitely 1.3198x faster
+
+        [1]: https://bugs.webkit.org/show_bug.cgi?id=178064
+
+        * API/JSCallbackFunction.cpp:
+        (JSC::JSCallbackFunction::JSCallbackFunction):
+        (JSC::JSCallbackFunction::getCallData): Deleted.
+        * API/JSCallbackFunction.h:
+        (JSC::JSCallbackFunction::createStructure):
+        * API/ObjCCallbackFunction.h:
+        (JSC::ObjCCallbackFunction::createStructure):
+        * API/ObjCCallbackFunction.mm:
+        (JSC::ObjCCallbackFunction::ObjCCallbackFunction):
+        (JSC::ObjCCallbackFunction::getCallData): Deleted.
+        (JSC::ObjCCallbackFunction::getConstructData): Deleted.
+        * bytecode/BytecodeDumper.cpp:
+        (JSC::BytecodeDumper<Block>::printCallOp):
+        * bytecode/BytecodeList.json:
+        * bytecode/CallLinkInfo.cpp:
+        (JSC::CallLinkInfo::setCallee):
+        (JSC::CallLinkInfo::callee):
+        (JSC::CallLinkInfo::setLastSeenCallee):
+        (JSC::CallLinkInfo::lastSeenCallee):
+        (JSC::CallLinkInfo::visitWeak):
+        * bytecode/CallLinkInfo.h:
+        * bytecode/CallLinkStatus.cpp:
+        (JSC::CallLinkStatus::computeFromCallLinkInfo):
+        * bytecode/LLIntCallLinkInfo.h:
+        * jit/JITOperations.cpp:
+        * jit/JITThunks.cpp:
+        (JSC::JITThunks::ctiInternalFunctionCall):
+        (JSC::JITThunks::ctiInternalFunctionConstruct):
+        * jit/JITThunks.h:
+        * jit/Repatch.cpp:
+        (JSC::linkFor):
+        (JSC::linkPolymorphicCall):
+        * jit/Repatch.h:
+        * jit/ThunkGenerators.cpp:
+        (JSC::virtualThunkFor):
+        (JSC::nativeForGenerator):
+        (JSC::nativeCallGenerator):
+        (JSC::nativeTailCallGenerator):
+        (JSC::nativeTailCallWithoutSavedTagsGenerator):
+        (JSC::nativeConstructGenerator):
+        (JSC::internalFunctionCallGenerator):
+        (JSC::internalFunctionConstructGenerator):
+        * jit/ThunkGenerators.h:
+        * llint/LLIntSlowPaths.cpp:
+        (JSC::LLInt::setUpCall):
+        * llint/LowLevelInterpreter.asm:
+        * llint/LowLevelInterpreter32_64.asm:
+        * llint/LowLevelInterpreter64.asm:
+        * runtime/ArrayConstructor.cpp:
+        (JSC::ArrayConstructor::ArrayConstructor):
+        (JSC::ArrayConstructor::getConstructData): Deleted.
+        (JSC::ArrayConstructor::getCallData): Deleted.
+        * runtime/ArrayConstructor.h:
+        (JSC::ArrayConstructor::createStructure):
+        * runtime/AsyncFunctionConstructor.cpp:
+        (JSC::AsyncFunctionConstructor::AsyncFunctionConstructor):
+        (JSC::AsyncFunctionConstructor::finishCreation):
+        (JSC::AsyncFunctionConstructor::getCallData): Deleted.
+        (JSC::AsyncFunctionConstructor::getConstructData): Deleted.
+        * runtime/AsyncFunctionConstructor.h:
+        (JSC::AsyncFunctionConstructor::createStructure):
+        * runtime/AsyncGeneratorFunctionConstructor.cpp:
+        (JSC::AsyncGeneratorFunctionConstructor::AsyncGeneratorFunctionConstructor):
+        (JSC::AsyncGeneratorFunctionConstructor::finishCreation):
+        (JSC::AsyncGeneratorFunctionConstructor::getCallData): Deleted.
+        (JSC::AsyncGeneratorFunctionConstructor::getConstructData): Deleted.
+        * runtime/AsyncGeneratorFunctionConstructor.h:
+        (JSC::AsyncGeneratorFunctionConstructor::createStructure):
+        * runtime/BooleanConstructor.cpp:
+        (JSC::callBooleanConstructor):
+        (JSC::BooleanConstructor::BooleanConstructor):
+        (JSC::BooleanConstructor::finishCreation):
+        (JSC::BooleanConstructor::getConstructData): Deleted.
+        (JSC::BooleanConstructor::getCallData): Deleted.
+        * runtime/BooleanConstructor.h:
+        (JSC::BooleanConstructor::createStructure):
+        * runtime/DateConstructor.cpp:
+        (JSC::DateConstructor::DateConstructor):
+        (JSC::DateConstructor::getConstructData): Deleted.
+        (JSC::DateConstructor::getCallData): Deleted.
+        * runtime/DateConstructor.h:
+        (JSC::DateConstructor::createStructure):
+        * runtime/Error.h:
+        (JSC::StrictModeTypeErrorFunction::StrictModeTypeErrorFunction):
+        (JSC::StrictModeTypeErrorFunction::createStructure):
+        (JSC::StrictModeTypeErrorFunction::getConstructData): Deleted.
+        (JSC::StrictModeTypeErrorFunction::getCallData): Deleted.
+        * runtime/ErrorConstructor.cpp:
+        (JSC::ErrorConstructor::ErrorConstructor):
+        (JSC::ErrorConstructor::getConstructData): Deleted.
+        (JSC::ErrorConstructor::getCallData): Deleted.
+        * runtime/ErrorConstructor.h:
+        (JSC::ErrorConstructor::createStructure):
+        * runtime/FunctionConstructor.cpp:
+        (JSC::FunctionConstructor::FunctionConstructor):
+        (JSC::FunctionConstructor::finishCreation):
+        (JSC::FunctionConstructor::getConstructData): Deleted.
+        (JSC::FunctionConstructor::getCallData): Deleted.
+        * runtime/FunctionConstructor.h:
+        (JSC::FunctionConstructor::createStructure):
+        * runtime/FunctionPrototype.cpp:
+        (JSC::callFunctionPrototype):
+        (JSC::FunctionPrototype::FunctionPrototype):
+        (JSC::FunctionPrototype::getCallData): Deleted.
+        * runtime/FunctionPrototype.h:
+        (JSC::FunctionPrototype::createStructure):
+        * runtime/GeneratorFunctionConstructor.cpp:
+        (JSC::GeneratorFunctionConstructor::GeneratorFunctionConstructor):
+        (JSC::GeneratorFunctionConstructor::finishCreation):
+        (JSC::GeneratorFunctionConstructor::getCallData): Deleted.
+        (JSC::GeneratorFunctionConstructor::getConstructData): Deleted.
+        * runtime/GeneratorFunctionConstructor.h:
+        (JSC::GeneratorFunctionConstructor::createStructure):
+        * runtime/InternalFunction.cpp:
+        (JSC::InternalFunction::InternalFunction):
+        (JSC::InternalFunction::finishCreation):
+        (JSC::InternalFunction::getCallData):
+        (JSC::InternalFunction::getConstructData):
+        * runtime/InternalFunction.h:
+        (JSC::InternalFunction::createStructure):
+        (JSC::InternalFunction::nativeFunctionFor):
+        (JSC::InternalFunction::offsetOfNativeFunctionFor):
+        * runtime/IntlCollatorConstructor.cpp:
+        (JSC::IntlCollatorConstructor::createStructure):
+        (JSC::IntlCollatorConstructor::IntlCollatorConstructor):
+        (JSC::IntlCollatorConstructor::getConstructData): Deleted.
+        (JSC::IntlCollatorConstructor::getCallData): Deleted.
+        * runtime/IntlCollatorConstructor.h:
+        * runtime/IntlDateTimeFormatConstructor.cpp:
+        (JSC::IntlDateTimeFormatConstructor::createStructure):
+        (JSC::IntlDateTimeFormatConstructor::IntlDateTimeFormatConstructor):
+        (JSC::IntlDateTimeFormatConstructor::getConstructData): Deleted.
+        (JSC::IntlDateTimeFormatConstructor::getCallData): Deleted.
+        * runtime/IntlDateTimeFormatConstructor.h:
+        * runtime/IntlNumberFormatConstructor.cpp:
+        (JSC::IntlNumberFormatConstructor::createStructure):
+        (JSC::IntlNumberFormatConstructor::IntlNumberFormatConstructor):
+        (JSC::IntlNumberFormatConstructor::getConstructData): Deleted.
+        (JSC::IntlNumberFormatConstructor::getCallData): Deleted.
+        * runtime/IntlNumberFormatConstructor.h:
+        * runtime/JSArrayBufferConstructor.cpp:
+        (JSC::JSArrayBufferConstructor::JSArrayBufferConstructor):
+        (JSC::JSArrayBufferConstructor::createStructure):
+        (JSC::JSArrayBufferConstructor::getConstructData): Deleted.
+        (JSC::JSArrayBufferConstructor::getCallData): Deleted.
+        * runtime/JSArrayBufferConstructor.h:
+        * runtime/JSGenericTypedArrayViewConstructor.h:
+        * runtime/JSGenericTypedArrayViewConstructorInlines.h:
+        (JSC::JSGenericTypedArrayViewConstructor<ViewClass>::JSGenericTypedArrayViewConstructor):
+        (JSC::JSGenericTypedArrayViewConstructor<ViewClass>::createStructure):
+        (JSC::JSGenericTypedArrayViewConstructor<ViewClass>::getConstructData): Deleted.
+        (JSC::JSGenericTypedArrayViewConstructor<ViewClass>::getCallData): Deleted.
+        * runtime/JSInternalPromiseConstructor.cpp:
+        (JSC::JSInternalPromiseConstructor::createStructure):
+        (JSC::JSInternalPromiseConstructor::JSInternalPromiseConstructor):
+        (JSC::JSInternalPromiseConstructor::getConstructData): Deleted.
+        (JSC::JSInternalPromiseConstructor::getCallData): Deleted.
+        * runtime/JSInternalPromiseConstructor.h:
+        * runtime/JSPromiseConstructor.cpp:
+        (JSC::JSPromiseConstructor::createStructure):
+        (JSC::JSPromiseConstructor::JSPromiseConstructor):
+        (JSC::JSPromiseConstructor::getConstructData): Deleted.
+        (JSC::JSPromiseConstructor::getCallData): Deleted.
+        * runtime/JSPromiseConstructor.h:
+        * runtime/JSType.h:
+        * runtime/JSTypedArrayViewConstructor.cpp:
+        (JSC::JSTypedArrayViewConstructor::JSTypedArrayViewConstructor):
+        (JSC::JSTypedArrayViewConstructor::createStructure):
+        (JSC::JSTypedArrayViewConstructor::getConstructData): Deleted.
+        (JSC::JSTypedArrayViewConstructor::getCallData): Deleted.
+        * runtime/JSTypedArrayViewConstructor.h:
+        * runtime/MapConstructor.cpp:
+        (JSC::MapConstructor::MapConstructor):
+        (JSC::MapConstructor::getConstructData): Deleted.
+        (JSC::MapConstructor::getCallData): Deleted.
+        * runtime/MapConstructor.h:
+        (JSC::MapConstructor::createStructure):
+        (JSC::MapConstructor::MapConstructor): Deleted.
+        * runtime/NativeErrorConstructor.cpp:
+        (JSC::NativeErrorConstructor::NativeErrorConstructor):
+        (JSC::NativeErrorConstructor::getConstructData): Deleted.
+        (JSC::NativeErrorConstructor::getCallData): Deleted.
+        * runtime/NativeErrorConstructor.h:
+        (JSC::NativeErrorConstructor::createStructure):
+        * runtime/NullGetterFunction.cpp:
+        (JSC::NullGetterFunction::NullGetterFunction):
+        (JSC::NullGetterFunction::getCallData): Deleted.
+        (JSC::NullGetterFunction::getConstructData): Deleted.
+        * runtime/NullGetterFunction.h:
+        (JSC::NullGetterFunction::createStructure):
+        (JSC::NullGetterFunction::NullGetterFunction): Deleted.
+        * runtime/NullSetterFunction.cpp:
+        (JSC::NullSetterFunction::NullSetterFunction):
+        (JSC::NullSetterFunction::getCallData): Deleted.
+        (JSC::NullSetterFunction::getConstructData): Deleted.
+        * runtime/NullSetterFunction.h:
+        (JSC::NullSetterFunction::createStructure):
+        (JSC::NullSetterFunction::NullSetterFunction): Deleted.
+        * runtime/NumberConstructor.cpp:
+        (JSC::NumberConstructor::NumberConstructor):
+        (JSC::constructNumberConstructor):
+        (JSC::constructWithNumberConstructor): Deleted.
+        (JSC::NumberConstructor::getConstructData): Deleted.
+        (JSC::NumberConstructor::getCallData): Deleted.
+        * runtime/NumberConstructor.h:
+        (JSC::NumberConstructor::createStructure):
+        * runtime/ObjectConstructor.cpp:
+        (JSC::ObjectConstructor::ObjectConstructor):
+        (JSC::ObjectConstructor::getConstructData): Deleted.
+        (JSC::ObjectConstructor::getCallData): Deleted.
+        * runtime/ObjectConstructor.h:
+        (JSC::ObjectConstructor::createStructure):
+        * runtime/ProxyConstructor.cpp:
+        (JSC::ProxyConstructor::ProxyConstructor):
+        (JSC::ProxyConstructor::getConstructData): Deleted.
+        (JSC::ProxyConstructor::getCallData): Deleted.
+        * runtime/ProxyConstructor.h:
+        (JSC::ProxyConstructor::createStructure):
+        * runtime/ProxyRevoke.cpp:
+        (JSC::ProxyRevoke::ProxyRevoke):
+        (JSC::ProxyRevoke::getCallData): Deleted.
+        * runtime/ProxyRevoke.h:
+        (JSC::ProxyRevoke::createStructure):
+        * runtime/RegExpConstructor.cpp:
+        (JSC::RegExpConstructor::RegExpConstructor):
+        (JSC::RegExpConstructor::getConstructData): Deleted.
+        (JSC::RegExpConstructor::getCallData): Deleted.
+        * runtime/RegExpConstructor.h:
+        (JSC::RegExpConstructor::createStructure):
+        * runtime/SetConstructor.cpp:
+        (JSC::SetConstructor::SetConstructor):
+        (JSC::SetConstructor::getConstructData): Deleted.
+        (JSC::SetConstructor::getCallData): Deleted.
+        * runtime/SetConstructor.h:
+        (JSC::SetConstructor::createStructure):
+        (JSC::SetConstructor::SetConstructor): Deleted.
+        * runtime/StringConstructor.cpp:
+        (JSC::StringConstructor::StringConstructor):
+        (JSC::StringConstructor::getConstructData): Deleted.
+        (JSC::StringConstructor::getCallData): Deleted.
+        * runtime/StringConstructor.h:
+        (JSC::StringConstructor::createStructure):
+        * runtime/SymbolConstructor.cpp:
+        (JSC::SymbolConstructor::SymbolConstructor):
+        (JSC::SymbolConstructor::getConstructData): Deleted.
+        (JSC::SymbolConstructor::getCallData): Deleted.
+        * runtime/SymbolConstructor.h:
+        (JSC::SymbolConstructor::createStructure):
+        * runtime/VM.cpp:
+        (JSC::VM::VM):
+        (JSC::VM::getCTIInternalFunctionTrampolineFor):
+        * runtime/VM.h:
+        * runtime/WeakMapConstructor.cpp:
+        (JSC::WeakMapConstructor::WeakMapConstructor):
+        (JSC::WeakMapConstructor::getConstructData): Deleted.
+        (JSC::WeakMapConstructor::getCallData): Deleted.
+        * runtime/WeakMapConstructor.h:
+        (JSC::WeakMapConstructor::createStructure):
+        (JSC::WeakMapConstructor::WeakMapConstructor): Deleted.
+        * runtime/WeakSetConstructor.cpp:
+        (JSC::WeakSetConstructor::WeakSetConstructor):
+        (JSC::WeakSetConstructor::getConstructData): Deleted.
+        (JSC::WeakSetConstructor::getCallData): Deleted.
+        * runtime/WeakSetConstructor.h:
+        (JSC::WeakSetConstructor::createStructure):
+        (JSC::WeakSetConstructor::WeakSetConstructor): Deleted.
+        * wasm/js/WebAssemblyCompileErrorConstructor.cpp:
+        (JSC::WebAssemblyCompileErrorConstructor::createStructure):
+        (JSC::WebAssemblyCompileErrorConstructor::WebAssemblyCompileErrorConstructor):
+        (JSC::WebAssemblyCompileErrorConstructor::getConstructData): Deleted.
+        (JSC::WebAssemblyCompileErrorConstructor::getCallData): Deleted.
+        * wasm/js/WebAssemblyCompileErrorConstructor.h:
+        * wasm/js/WebAssemblyInstanceConstructor.cpp:
+        (JSC::WebAssemblyInstanceConstructor::createStructure):
+        (JSC::WebAssemblyInstanceConstructor::WebAssemblyInstanceConstructor):
+        (JSC::WebAssemblyInstanceConstructor::getConstructData): Deleted.
+        (JSC::WebAssemblyInstanceConstructor::getCallData): Deleted.
+        * wasm/js/WebAssemblyInstanceConstructor.h:
+        * wasm/js/WebAssemblyLinkErrorConstructor.cpp:
+        (JSC::WebAssemblyLinkErrorConstructor::createStructure):
+        (JSC::WebAssemblyLinkErrorConstructor::WebAssemblyLinkErrorConstructor):
+        (JSC::WebAssemblyLinkErrorConstructor::getConstructData): Deleted.
+        (JSC::WebAssemblyLinkErrorConstructor::getCallData): Deleted.
+        * wasm/js/WebAssemblyLinkErrorConstructor.h:
+        * wasm/js/WebAssemblyMemoryConstructor.cpp:
+        (JSC::WebAssemblyMemoryConstructor::createStructure):
+        (JSC::WebAssemblyMemoryConstructor::WebAssemblyMemoryConstructor):
+        (JSC::WebAssemblyMemoryConstructor::getConstructData): Deleted.
+        (JSC::WebAssemblyMemoryConstructor::getCallData): Deleted.
+        * wasm/js/WebAssemblyMemoryConstructor.h:
+        * wasm/js/WebAssemblyModuleConstructor.cpp:
+        (JSC::WebAssemblyModuleConstructor::createStructure):
+        (JSC::WebAssemblyModuleConstructor::WebAssemblyModuleConstructor):
+        (JSC::WebAssemblyModuleConstructor::getConstructData): Deleted.
+        (JSC::WebAssemblyModuleConstructor::getCallData): Deleted.
+        * wasm/js/WebAssemblyModuleConstructor.h:
+        * wasm/js/WebAssemblyRuntimeErrorConstructor.cpp:
+        (JSC::WebAssemblyRuntimeErrorConstructor::createStructure):
+        (JSC::WebAssemblyRuntimeErrorConstructor::WebAssemblyRuntimeErrorConstructor):
+        (JSC::WebAssemblyRuntimeErrorConstructor::getConstructData): Deleted.
+        (JSC::WebAssemblyRuntimeErrorConstructor::getCallData): Deleted.
+        * wasm/js/WebAssemblyRuntimeErrorConstructor.h:
+        * wasm/js/WebAssemblyTableConstructor.cpp:
+        (JSC::WebAssemblyTableConstructor::createStructure):
+        (JSC::WebAssemblyTableConstructor::WebAssemblyTableConstructor):
+        (JSC::WebAssemblyTableConstructor::getConstructData): Deleted.
+        (JSC::WebAssemblyTableConstructor::getCallData): Deleted.
+        * wasm/js/WebAssemblyTableConstructor.h:
+
 2017-11-03  Michael Saboff  <msaboff@apple.com>
 
         The Abstract Interpreter needs to change similar to clobberize() in r224366
index 9c6f5d3..4f9834e 100644 (file)
@@ -578,16 +578,19 @@ void BytecodeDumper<Block>::printCallOp(PrintStream& out, int location, const ty
     if (cacheDumpMode == DumpCaches) {
         LLIntCallLinkInfo* callLinkInfo = getCallLinkInfo(it[1]);
         if (callLinkInfo->lastSeenCallee) {
-            out.printf(
-                " llint(%p, exec %p)",
-                callLinkInfo->lastSeenCallee.get(),
-                callLinkInfo->lastSeenCallee->executable());
+            JSObject* object = callLinkInfo->lastSeenCallee.get();
+            if (auto* function = jsDynamicCast<JSFunction*>(*vm(), object))
+                out.printf(" llint(%p, exec %p)", function, function->executable());
+            else
+                out.printf(" llint(%p)", object);
         }
 #if ENABLE(JIT)
         if (CallLinkInfo* info = map.get(CodeOrigin(location))) {
-            JSFunction* target = info->lastSeenCallee();
-            if (target)
-                out.printf(" jit(%p, exec %p)", target, target->executable());
+            JSObject* object = info->lastSeenCallee();
+            if (auto* function = jsDynamicCast<JSFunction*>(*vm(), object))
+                out.printf(" jit(%p, exec %p)", function, function->executable());
+            else
+                out.printf(" jit(%p)", object);
         }
 
         dumpCallLinkStatus(out, location, map);
index 36cf57e..09005ea 100644 (file)
             { "name" : "llint_throw_during_call_trampoline" },
             { "name" : "llint_native_call_trampoline" },
             { "name" : "llint_native_construct_trampoline" },
+            { "name" : "llint_internal_function_call_trampoline" },
+            { "name" : "llint_internal_function_construct_trampoline" },
             { "name" : "handleUncaughtException" }
         ]
     }
index 3acc5fb..f236014 100644 (file)
@@ -121,7 +121,7 @@ CodeLocationLabel CallLinkInfo::slowPathStart()
     return m_hotPathBeginOrSlowPathStart;
 }
 
-void CallLinkInfo::setCallee(VM& vm, JSCell* owner, JSFunction* callee)
+void CallLinkInfo::setCallee(VM& vm, JSCell* owner, JSObject* callee)
 {
     RELEASE_ASSERT(!isDirect());
     MacroAssembler::repatchPointer(hotPathBegin(), callee);
@@ -137,10 +137,10 @@ void CallLinkInfo::clearCallee()
     m_isLinked = false;
 }
 
-JSFunction* CallLinkInfo::callee()
+JSObject* CallLinkInfo::callee()
 {
     RELEASE_ASSERT(!isDirect());
-    return jsCast<JSFunction*>(m_calleeOrCodeBlock.get());
+    return jsCast<JSObject*>(m_calleeOrCodeBlock.get());
 }
 
 void CallLinkInfo::setCodeBlock(VM& vm, JSCell* owner, FunctionCodeBlock* codeBlock)
@@ -163,7 +163,7 @@ FunctionCodeBlock* CallLinkInfo::codeBlock()
     return jsCast<FunctionCodeBlock*>(m_calleeOrCodeBlock.get());
 }
 
-void CallLinkInfo::setLastSeenCallee(VM& vm, const JSCell* owner, JSFunction* callee)
+void CallLinkInfo::setLastSeenCallee(VM& vm, const JSCell* owner, JSObject* callee)
 {
     RELEASE_ASSERT(!isDirect());
     m_lastSeenCalleeOrExecutable.set(vm, owner, callee);
@@ -175,10 +175,10 @@ void CallLinkInfo::clearLastSeenCallee()
     m_lastSeenCalleeOrExecutable.clear();
 }
 
-JSFunction* CallLinkInfo::lastSeenCallee()
+JSObject* CallLinkInfo::lastSeenCallee()
 {
     RELEASE_ASSERT(!isDirect());
-    return jsCast<JSFunction*>(m_lastSeenCalleeOrExecutable.get());
+    return jsCast<JSObject*>(m_lastSeenCalleeOrExecutable.get());
 }
 
 bool CallLinkInfo::haveLastSeenCallee()
@@ -235,14 +235,20 @@ void CallLinkInfo::visitWeak(VM& vm)
                         pointerDump(codeBlock()), ").\n");
                 }
             } else {
-                if (Options::verboseOSR()) {
-                    dataLog(
-                        "Clearing call to ",
-                        RawPointer(callee()), " (",
-                        callee()->executable()->hashFor(specializationKind()),
-                        ").\n");
+                if (callee()->type() == JSFunctionType) {
+                    if (Options::verboseOSR()) {
+                        dataLog(
+                            "Clearing call to ",
+                            RawPointer(callee()), " (",
+                            static_cast<JSFunction*>(callee())->executable()->hashFor(specializationKind()),
+                            ").\n");
+                    }
+                    handleSpecificCallee(static_cast<JSFunction*>(callee()));
+                } else {
+                    if (Options::verboseOSR())
+                        dataLog("Clearing call to ", RawPointer(callee()), ".\n");
+                    m_clearedByGC = true;
                 }
-                handleSpecificCallee(callee());
             }
             unlink(vm);
         } else if (isDirect() && !Heap::isMarked(m_lastSeenCalleeOrExecutable.get())) {
@@ -258,7 +264,10 @@ void CallLinkInfo::visitWeak(VM& vm)
         }
     }
     if (!isDirect() && haveLastSeenCallee() && !Heap::isMarked(lastSeenCallee())) {
-        handleSpecificCallee(lastSeenCallee());
+        if (lastSeenCallee()->type() == JSFunctionType)
+            handleSpecificCallee(jsCast<JSFunction*>(lastSeenCallee()));
+        else
+            m_clearedByGC = true;
         clearLastSeenCallee();
     }
 }
index 91d3dd8..5bc2c44 100644 (file)
@@ -191,17 +191,17 @@ public:
         return m_hotPathOther;
     }
 
-    void setCallee(VM&, JSCell*, JSFunction* callee);
+    void setCallee(VM&, JSCell*, JSObject* callee);
     void clearCallee();
-    JSFunction* callee();
+    JSObject* callee();
 
     void setCodeBlock(VM&, JSCell*, FunctionCodeBlock*);
     void clearCodeBlock();
     FunctionCodeBlock* codeBlock();
 
-    void setLastSeenCallee(VM& vm, const JSCell* owner, JSFunction* callee);
+    void setLastSeenCallee(VM&, const JSCell* owner, JSObject* callee);
     void clearLastSeenCallee();
-    JSFunction* lastSeenCallee();
+    JSObject* lastSeenCallee();
     bool haveLastSeenCallee();
     
     void setExecutableDuringCompilation(ExecutableBase*);
index 53b84d9..f284e30 100644 (file)
@@ -215,7 +215,7 @@ CallLinkStatus CallLinkStatus::computeFromCallLinkInfo(
     
     CallLinkStatus result;
     
-    if (JSFunction* target = callLinkInfo.lastSeenCallee()) {
+    if (JSObject* target = callLinkInfo.lastSeenCallee()) {
         CallVariant variant(target);
         if (callLinkInfo.hasSeenClosure())
             variant = variant.despecifiedClosure();
index c2cf4d1..8d0b860 100644 (file)
@@ -54,8 +54,8 @@ struct LLIntCallLinkInfo : public BasicRawSentinelNode<LLIntCallLinkInfo> {
             remove();
     }
     
-    WriteBarrier<JSFunction> callee;
-    WriteBarrier<JSFunction> lastSeenCallee;
+    WriteBarrier<JSObject> callee;
+    WriteBarrier<JSObject> lastSeenCallee;
     MacroAssemblerCodePtr machineCodeTarget;
 };
 
index 7359856..acd23e8 100644 (file)
@@ -939,9 +939,17 @@ SlowPathReturnType JIT_OPERATION operationLinkCall(ExecState* execCallee, CallLi
     JSValue calleeAsValue = execCallee->guaranteedJSValueCallee();
     JSCell* calleeAsFunctionCell = getJSFunction(calleeAsValue);
     if (!calleeAsFunctionCell) {
-        // FIXME: We should cache these kinds of calls. They can be common and currently they are
-        // expensive.
-        // https://bugs.webkit.org/show_bug.cgi?id=144458
+        if (calleeAsValue.isCell() && calleeAsValue.asCell()->type() == InternalFunctionType) {
+            MacroAssemblerCodePtr codePtr = vm->getCTIInternalFunctionTrampolineFor(kind);
+            RELEASE_ASSERT(!!codePtr);
+
+            if (!callLinkInfo->seenOnce())
+                callLinkInfo->setSeen();
+            else
+                linkFor(execCallee, *callLinkInfo, nullptr, asObject(calleeAsValue), codePtr);
+
+            return encodeResult(codePtr.executableAddress(), reinterpret_cast<void*>(callLinkInfo->callMode() == CallMode::Tail ? ReuseTheFrame : KeepTheFrame));
+        }
         throwScope.release();
         return handleHostCall(execCallee, calleeAsValue, callLinkInfo);
     }
@@ -951,7 +959,7 @@ SlowPathReturnType JIT_OPERATION operationLinkCall(ExecState* execCallee, CallLi
     ExecutableBase* executable = callee->executable();
 
     MacroAssemblerCodePtr codePtr;
-    CodeBlock* codeBlock = 0;
+    CodeBlock* codeBlock = nullptr;
     if (executable->isHostFunction()) {
         codePtr = executable->entrypointFor(kind, MustCheckArity);
     } else {
@@ -1053,6 +1061,11 @@ inline SlowPathReturnType virtualForWithFunction(
     JSValue calleeAsValue = execCallee->guaranteedJSValueCallee();
     calleeAsFunctionCell = getJSFunction(calleeAsValue);
     if (UNLIKELY(!calleeAsFunctionCell)) {
+        if (calleeAsValue.isCell() && calleeAsValue.asCell()->type() == InternalFunctionType) {
+            MacroAssemblerCodePtr codePtr = vm->getCTIInternalFunctionTrampolineFor(kind);
+            ASSERT(!!codePtr);
+            return encodeResult(codePtr.executableAddress(), reinterpret_cast<void*>(callLinkInfo->callMode() == CallMode::Tail ? ReuseTheFrame : KeepTheFrame));
+        }
         throwScope.release();
         return handleHostCall(execCallee, calleeAsValue, callLinkInfo);
     }
index dffd802..03ded6c 100644 (file)
@@ -71,6 +71,20 @@ MacroAssemblerCodePtr JITThunks::ctiNativeTailCallWithoutSavedTags(VM* vm)
     return ctiStub(vm, nativeTailCallWithoutSavedTagsGenerator).code();
 }
 
+MacroAssemblerCodePtr JITThunks::ctiInternalFunctionCall(VM* vm)
+{
+    if (!vm->canUseJIT())
+        return MacroAssemblerCodePtr::createLLIntCodePtr(llint_internal_function_call_trampoline);
+    return ctiStub(vm, internalFunctionCallGenerator).code();
+}
+
+MacroAssemblerCodePtr JITThunks::ctiInternalFunctionConstruct(VM* vm)
+{
+    if (!vm->canUseJIT())
+        return MacroAssemblerCodePtr::createLLIntCodePtr(llint_internal_function_construct_trampoline);
+    return ctiStub(vm, internalFunctionConstructGenerator).code();
+}
+
 MacroAssemblerCodeRef JITThunks::ctiStub(VM* vm, ThunkGenerator generator)
 {
     LockHolder locker(m_lock);
index 4e7337a..3142728 100644 (file)
@@ -55,6 +55,8 @@ public:
     MacroAssemblerCodePtr ctiNativeConstruct(VM*);
     MacroAssemblerCodePtr ctiNativeTailCall(VM*);    
     MacroAssemblerCodePtr ctiNativeTailCallWithoutSavedTags(VM*);    
+    MacroAssemblerCodePtr ctiInternalFunctionCall(VM*);
+    MacroAssemblerCodePtr ctiInternalFunctionConstruct(VM*);
 
     MacroAssemblerCodeRef ctiStub(VM*, ThunkGenerator);
     MacroAssemblerCodeRef existingCTIStub(ThunkGenerator);
index d79ac6d..e92321c 100644 (file)
@@ -692,7 +692,7 @@ static JSCell* webAssemblyOwner(JSCell* callee)
 
 void linkFor(
     ExecState* exec, CallLinkInfo& callLinkInfo, CodeBlock* calleeCodeBlock,
-    JSFunction* callee, MacroAssemblerCodePtr codePtr)
+    JSObject* callee, MacroAssemblerCodePtr codePtr)
 {
     ASSERT(!callLinkInfo.stub());
 
@@ -815,9 +815,7 @@ void linkPolymorphicCall(
 {
     RELEASE_ASSERT(callLinkInfo.allowStubs());
     
-    // Currently we can't do anything for non-function callees.
-    // https://bugs.webkit.org/show_bug.cgi?id=140685
-    if (!newVariant || !newVariant.executable()) {
+    if (!newVariant) {
         linkVirtualFor(exec, callLinkInfo);
         return;
     }
@@ -839,7 +837,7 @@ void linkPolymorphicCall(
     CallVariantList list;
     if (PolymorphicCallStubRoutine* stub = callLinkInfo.stub())
         list = stub->variants();
-    else if (JSFunction* oldCallee = callLinkInfo.callee())
+    else if (JSObject* oldCallee = callLinkInfo.callee())
         list = CallVariantList{ CallVariant(oldCallee) };
     
     list = variantListWithVariant(list, newVariant);
@@ -863,10 +861,8 @@ void linkPolymorphicCall(
     
     // Figure out what our cases are.
     for (CallVariant variant : list) {
-        CodeBlock* codeBlock;
-        if (variant.executable()->isHostFunction())
-            codeBlock = nullptr;
-        else {
+        CodeBlock* codeBlock = nullptr;
+        if (variant.executable() && !variant.executable()->isHostFunction()) {
             ExecutableBase* executable = variant.executable();
             codeBlock = jsCast<FunctionExecutable*>(executable)->codeBlockForCall();
             // If we cannot handle a callee, either because we don't have a CodeBlock or because arity mismatch,
@@ -926,7 +922,8 @@ void linkPolymorphicCall(
 #else
         // We would have already checked that the callee is a cell.
 #endif
-    
+
+        // FIXME: We could add a fast path for InternalFunction with closure call.
         slowPath.append(
             stubJit.branch8(
                 CCallHelpers::NotEqual,
@@ -953,11 +950,19 @@ void linkPolymorphicCall(
             fastCounts[i] = 0;
         
         CallVariant variant = callCases[i].variant();
-        int64_t newCaseValue;
-        if (isClosureCall)
+        int64_t newCaseValue = 0;
+        if (isClosureCall) {
             newCaseValue = bitwise_cast<intptr_t>(variant.executable());
-        else
-            newCaseValue = bitwise_cast<intptr_t>(variant.function());
+            // FIXME: We could add a fast path for InternalFunction with closure call.
+            // https://bugs.webkit.org/show_bug.cgi?id=179311
+            if (!newCaseValue)
+                continue;
+        } else {
+            if (auto* function = variant.function())
+                newCaseValue = bitwise_cast<intptr_t>(function);
+            else
+                newCaseValue = bitwise_cast<intptr_t>(variant.internalFunction());
+        }
         
         if (!ASSERT_DISABLED) {
             for (size_t j = 0; j < i; ++j) {
@@ -996,9 +1001,14 @@ void linkPolymorphicCall(
         
         CallVariant variant = callCases[caseIndex].variant();
         
-        ASSERT(variant.executable()->hasJITCodeForCall());
-        MacroAssemblerCodePtr codePtr =
-            variant.executable()->generatedJITCodeForCall()->addressForCall(ArityCheckNotRequired);
+        MacroAssemblerCodePtr codePtr;
+        if (variant.executable()) {
+            ASSERT(variant.executable()->hasJITCodeForCall());
+            codePtr = variant.executable()->generatedJITCodeForCall()->addressForCall(ArityCheckNotRequired);
+        } else {
+            ASSERT(variant.internalFunction());
+            codePtr = vm.getCTIInternalFunctionTrampolineFor(CodeForCall);
+        }
         
         if (fastCounts) {
             stubJit.add32(
index e2975b9..19b1f5f 100644 (file)
@@ -44,7 +44,7 @@ void buildGetByIDProtoList(ExecState*, JSValue, const Identifier&, const Propert
 void repatchPutByID(ExecState*, JSValue, Structure*, const Identifier&, const PutPropertySlot&, StructureStubInfo&, PutKind);
 void buildPutByIdList(ExecState*, JSValue, Structure*, const Identifier&, const PutPropertySlot&, StructureStubInfo&, PutKind);
 void repatchIn(ExecState*, JSCell*, const Identifier&, bool wasFound, const PropertySlot&, StructureStubInfo&);
-void linkFor(ExecState*, CallLinkInfo&, CodeBlock*, JSFunction* callee, MacroAssemblerCodePtr);
+void linkFor(ExecState*, CallLinkInfo&, CodeBlock*, JSObject* callee, MacroAssemblerCodePtr);
 void linkDirectFor(ExecState*, CallLinkInfo&, CodeBlock*, MacroAssemblerCodePtr);
 void linkSlowFor(ExecState*, CallLinkInfo&);
 void unlinkFor(VM&, CallLinkInfo&);
index f1dde76..f9ea5a3 100644 (file)
@@ -197,7 +197,7 @@ MacroAssemblerCodeRef virtualThunkFor(VM* vm, CallLinkInfo& callLinkInfo)
             CCallHelpers::NotEqual, GPRInfo::regT1,
             CCallHelpers::TrustedImm32(JSValue::CellTag)));
 #endif
-    slowCase.append(jit.branchIfNotType(GPRInfo::regT0, JSFunctionType));
+    auto notJSFunction = jit.branchIfNotType(GPRInfo::regT0, JSFunctionType);
     
     // Now we know we have a JSFunction.
     
@@ -215,6 +215,7 @@ MacroAssemblerCodeRef virtualThunkFor(VM* vm, CallLinkInfo& callLinkInfo)
     // call.
     
     // Make a tail call. This will return back to JIT code.
+    JSInterfaceJIT::Label callCode(jit.label());
     emitPointerValidation(jit, GPRInfo::regT4);
     if (callLinkInfo.isTailCall()) {
         jit.preserveReturnAddressAfterCall(GPRInfo::regT0);
@@ -222,6 +223,11 @@ MacroAssemblerCodeRef virtualThunkFor(VM* vm, CallLinkInfo& callLinkInfo)
     }
     jit.jump(GPRInfo::regT4);
 
+    notJSFunction.link(&jit);
+    slowCase.append(jit.branchIfNotType(GPRInfo::regT0, InternalFunctionType));
+    jit.move(CCallHelpers::TrustedImmPtr(vm->getCTIInternalFunctionTrampolineFor(callLinkInfo.specializationKind()).executableAddress()), GPRInfo::regT4);
+    jit.jump().linkTo(callCode, &jit);
+
     slowCase.link(&jit);
     
     // Here we don't know anything, so revert to the full slow path.
@@ -236,8 +242,9 @@ MacroAssemblerCodeRef virtualThunkFor(VM* vm, CallLinkInfo& callLinkInfo)
 }
 
 enum ThunkEntryType { EnterViaCall, EnterViaJumpWithSavedTags, EnterViaJumpWithoutSavedTags };
+enum class ThunkFunctionType { JSFunction, InternalFunction };
 
-static MacroAssemblerCodeRef nativeForGenerator(VM* vm, CodeSpecializationKind kind, ThunkEntryType entryType = EnterViaCall)
+static MacroAssemblerCodeRef nativeForGenerator(VM* vm, ThunkFunctionType thunkFunctionType, CodeSpecializationKind kind, ThunkEntryType entryType = EnterViaCall)
 {
     // FIXME: This should be able to log ShadowChicken prologue packets.
     // https://bugs.webkit.org/show_bug.cgi?id=155689
@@ -279,8 +286,11 @@ static MacroAssemblerCodeRef nativeForGenerator(VM* vm, CodeSpecializationKind k
 
     // call the function
     jit.emitGetFromCallFrameHeaderPtr(CallFrameSlot::callee, JSInterfaceJIT::regT1);
-    jit.loadPtr(JSInterfaceJIT::Address(JSInterfaceJIT::regT1, JSFunction::offsetOfExecutable()), JSInterfaceJIT::regT1);
-    jit.call(JSInterfaceJIT::Address(JSInterfaceJIT::regT1, executableOffsetToFunction));
+    if (thunkFunctionType == ThunkFunctionType::JSFunction) {
+        jit.loadPtr(JSInterfaceJIT::Address(JSInterfaceJIT::regT1, JSFunction::offsetOfExecutable()), JSInterfaceJIT::regT1);
+        jit.call(JSInterfaceJIT::Address(JSInterfaceJIT::regT1, executableOffsetToFunction));
+    } else
+        jit.call(JSInterfaceJIT::Address(JSInterfaceJIT::regT1, InternalFunction::offsetOfNativeFunctionFor(kind)));
 
     jit.addPtr(JSInterfaceJIT::TrustedImm32(8), JSInterfaceJIT::stackPointerRegister);
 
@@ -291,8 +301,11 @@ static MacroAssemblerCodeRef nativeForGenerator(VM* vm, CodeSpecializationKind k
     jit.move(JSInterfaceJIT::callFrameRegister, X86Registers::edi);
 
     jit.emitGetFromCallFrameHeaderPtr(CallFrameSlot::callee, X86Registers::esi);
-    jit.loadPtr(JSInterfaceJIT::Address(X86Registers::esi, JSFunction::offsetOfExecutable()), X86Registers::r9);
-    jit.call(JSInterfaceJIT::Address(X86Registers::r9, executableOffsetToFunction));
+    if (thunkFunctionType == ThunkFunctionType::JSFunction) {
+        jit.loadPtr(JSInterfaceJIT::Address(X86Registers::esi, JSFunction::offsetOfExecutable()), X86Registers::r9);
+        jit.call(JSInterfaceJIT::Address(X86Registers::r9, executableOffsetToFunction));
+    } else
+        jit.call(JSInterfaceJIT::Address(X86Registers::esi, InternalFunction::offsetOfNativeFunctionFor(kind)));
 
 #else
     // Calling convention:      f(ecx, edx, r8, r9, ...);
@@ -304,8 +317,11 @@ static MacroAssemblerCodeRef nativeForGenerator(VM* vm, CodeSpecializationKind k
     jit.subPtr(JSInterfaceJIT::TrustedImm32(4 * sizeof(int64_t)), JSInterfaceJIT::stackPointerRegister);
 
     jit.emitGetFromCallFrameHeaderPtr(CallFrameSlot::callee, X86Registers::edx);
-    jit.loadPtr(JSInterfaceJIT::Address(X86Registers::edx, JSFunction::offsetOfExecutable()), X86Registers::r9);
-    jit.call(JSInterfaceJIT::Address(X86Registers::r9, executableOffsetToFunction));
+    if (thunkFunctionType == ThunkFunctionType::JSFunction) {
+        jit.loadPtr(JSInterfaceJIT::Address(X86Registers::edx, JSFunction::offsetOfExecutable()), X86Registers::r9);
+        jit.call(JSInterfaceJIT::Address(X86Registers::r9, executableOffsetToFunction));
+    } else
+        jit.call(JSInterfaceJIT::Address(X86Registers::edx, InternalFunction::offsetOfNativeFunctionFor(kind)));
 
     jit.addPtr(JSInterfaceJIT::TrustedImm32(4 * sizeof(int64_t)), JSInterfaceJIT::stackPointerRegister);
 #endif
@@ -319,8 +335,11 @@ static MacroAssemblerCodeRef nativeForGenerator(VM* vm, CodeSpecializationKind k
     jit.move(JSInterfaceJIT::callFrameRegister, ARM64Registers::x0);
 
     jit.emitGetFromCallFrameHeaderPtr(CallFrameSlot::callee, ARM64Registers::x1);
-    jit.loadPtr(JSInterfaceJIT::Address(ARM64Registers::x1, JSFunction::offsetOfExecutable()), ARM64Registers::x2);
-    jit.call(JSInterfaceJIT::Address(ARM64Registers::x2, executableOffsetToFunction));
+    if (thunkFunctionType == ThunkFunctionType::JSFunction) {
+        jit.loadPtr(JSInterfaceJIT::Address(ARM64Registers::x1, JSFunction::offsetOfExecutable()), ARM64Registers::x2);
+        jit.call(JSInterfaceJIT::Address(ARM64Registers::x2, executableOffsetToFunction));
+    } else
+        jit.call(JSInterfaceJIT::Address(ARM64Registers::x1, InternalFunction::offsetOfNativeFunctionFor(kind)));
 #elif CPU(ARM) || CPU(MIPS)
 #if CPU(MIPS)
     // Allocate stack space for (unused) 16 bytes (8-byte aligned) for 4 arguments.
@@ -332,8 +351,11 @@ static MacroAssemblerCodeRef nativeForGenerator(VM* vm, CodeSpecializationKind k
     jit.move(JSInterfaceJIT::callFrameRegister, JSInterfaceJIT::argumentGPR0);
 
     jit.emitGetFromCallFrameHeaderPtr(CallFrameSlot::callee, JSInterfaceJIT::argumentGPR1);
-    jit.loadPtr(JSInterfaceJIT::Address(JSInterfaceJIT::argumentGPR1, JSFunction::offsetOfExecutable()), JSInterfaceJIT::regT2);
-    jit.call(JSInterfaceJIT::Address(JSInterfaceJIT::regT2, executableOffsetToFunction));
+    if (thunkFunctionType == ThunkFunctionType::JSFunction) {
+        jit.loadPtr(JSInterfaceJIT::Address(JSInterfaceJIT::argumentGPR1, JSFunction::offsetOfExecutable()), JSInterfaceJIT::regT2);
+        jit.call(JSInterfaceJIT::Address(JSInterfaceJIT::regT2, executableOffsetToFunction));
+    } else
+        jit.call(JSInterfaceJIT::Address(JSInterfaceJIT::argumentGPR1, InternalFunction::offsetOfNativeFunctionFor(kind)));
 
 #if CPU(MIPS)
     // Restore stack space
@@ -388,27 +410,37 @@ static MacroAssemblerCodeRef nativeForGenerator(VM* vm, CodeSpecializationKind k
     jit.jumpToExceptionHandler(*vm);
 
     LinkBuffer patchBuffer(jit, GLOBAL_THUNK_ID);
-    return FINALIZE_CODE(patchBuffer, ("native %s%s trampoline", entryType == EnterViaJumpWithSavedTags ? "Tail With Saved Tags " : entryType == EnterViaJumpWithoutSavedTags ? "Tail Without Saved Tags " : "", toCString(kind).data()));
+    return FINALIZE_CODE(patchBuffer, ("%s %s%s trampoline", thunkFunctionType == ThunkFunctionType::JSFunction ? "native" : "internal", entryType == EnterViaJumpWithSavedTags ? "Tail With Saved Tags " : entryType == EnterViaJumpWithoutSavedTags ? "Tail Without Saved Tags " : "", toCString(kind).data()));
 }
 
 MacroAssemblerCodeRef nativeCallGenerator(VM* vm)
 {
-    return nativeForGenerator(vm, CodeForCall);
+    return nativeForGenerator(vm, ThunkFunctionType::JSFunction, CodeForCall);
 }
 
 MacroAssemblerCodeRef nativeTailCallGenerator(VM* vm)
 {
-    return nativeForGenerator(vm, CodeForCall, EnterViaJumpWithSavedTags);
+    return nativeForGenerator(vm, ThunkFunctionType::JSFunction, CodeForCall, EnterViaJumpWithSavedTags);
 }
 
 MacroAssemblerCodeRef nativeTailCallWithoutSavedTagsGenerator(VM* vm)
 {
-    return nativeForGenerator(vm, CodeForCall, EnterViaJumpWithoutSavedTags);
+    return nativeForGenerator(vm, ThunkFunctionType::JSFunction, CodeForCall, EnterViaJumpWithoutSavedTags);
 }
 
 MacroAssemblerCodeRef nativeConstructGenerator(VM* vm)
 {
-    return nativeForGenerator(vm, CodeForConstruct);
+    return nativeForGenerator(vm, ThunkFunctionType::JSFunction, CodeForConstruct);
+}
+
+MacroAssemblerCodeRef internalFunctionCallGenerator(VM* vm)
+{
+    return nativeForGenerator(vm, ThunkFunctionType::InternalFunction, CodeForCall);
+}
+
+MacroAssemblerCodeRef internalFunctionConstructGenerator(VM* vm)
+{
+    return nativeForGenerator(vm, ThunkFunctionType::InternalFunction, CodeForConstruct);
 }
 
 MacroAssemblerCodeRef arityFixupGenerator(VM* vm)
index c043d41..618fee0 100644 (file)
@@ -46,6 +46,8 @@ MacroAssemblerCodeRef nativeCallGenerator(VM*);
 MacroAssemblerCodeRef nativeConstructGenerator(VM*);
 MacroAssemblerCodeRef nativeTailCallGenerator(VM*);
 MacroAssemblerCodeRef nativeTailCallWithoutSavedTagsGenerator(VM*);
+MacroAssemblerCodeRef internalFunctionCallGenerator(VM*);
+MacroAssemblerCodeRef internalFunctionConstructGenerator(VM*);
 MacroAssemblerCodeRef arityFixupGenerator(VM*);
 MacroAssemblerCodeRef unreachableGenerator(VM*);
 
index 8a0e1ac..297b6c1 100644 (file)
@@ -1350,6 +1350,25 @@ inline SlowPathReturnType setUpCall(ExecState* execCallee, Instruction* pc, Code
     
     JSCell* calleeAsFunctionCell = getJSFunction(calleeAsValue);
     if (!calleeAsFunctionCell) {
+        if (calleeAsValue.isCell() && calleeAsValue.asCell()->type() == InternalFunctionType) {
+            auto* internalFunction = jsCast<InternalFunction*>(calleeAsValue.asCell());
+            MacroAssemblerCodePtr codePtr = vm.getCTIInternalFunctionTrampolineFor(kind);
+            ASSERT(!!codePtr);
+
+            if (!LLINT_ALWAYS_ACCESS_SLOW && callLinkInfo) {
+                CodeBlock* callerCodeBlock = exec->codeBlock();
+
+                ConcurrentJSLocker locker(callerCodeBlock->m_lock);
+
+                if (callLinkInfo->isOnList())
+                    callLinkInfo->remove();
+                callLinkInfo->callee.set(vm, callerCodeBlock, internalFunction);
+                callLinkInfo->lastSeenCallee.set(vm, callerCodeBlock, internalFunction);
+                callLinkInfo->machineCodeTarget = codePtr;
+            }
+
+            LLINT_CALL_RETURN(exec, execCallee, codePtr.executableAddress());
+        }
         throwScope.release();
         return handleHostCall(execCallee, pc, calleeAsValue, kind);
     }
index 5dad116..6c054fa 100644 (file)
@@ -1834,6 +1834,15 @@ _llint_native_call_trampoline:
 _llint_native_construct_trampoline:
     nativeCallTrampoline(NativeExecutable::m_constructor)
 
+
+_llint_internal_function_call_trampoline:
+    internalFunctionCallTrampoline(InternalFunction::m_functionForCall)
+
+
+_llint_internal_function_construct_trampoline:
+    internalFunctionCallTrampoline(InternalFunction::m_functionForConstruct)
+
+
 _llint_op_get_enumerable_length:
     traceExecution()
     callOpcodeSlowPath(_slow_path_get_enumerable_length)
index dfd17b5..7d6269c 100644 (file)
@@ -2115,6 +2115,58 @@ macro nativeCallTrampoline(executableOffsetToFunction)
 end
 
 
+macro internalFunctionCallTrampoline(offsetOfFunction)
+    functionPrologue()
+    storep 0, CodeBlock[cfr]
+    loadi Callee + PayloadOffset[cfr], t1
+    // Callee is still in t1 for code below
+    if X86 or X86_WIN
+        subp 8, sp # align stack pointer
+        andp MarkedBlockMask, t1
+        loadp MarkedBlock::m_vm[t1], t3
+        storep cfr, VM::topCallFrame[t3]
+        move cfr, a0  # a0 = ecx
+        storep a0, [sp]
+        loadi Callee + PayloadOffset[cfr], t1
+        checkStackPointerAlignment(t3, 0xdead0001)
+        call offsetOfFunction[t1]
+        loadp Callee + PayloadOffset[cfr], t3
+        andp MarkedBlockMask, t3
+        loadp MarkedBlock::m_vm[t3], t3
+        addp 8, sp
+    elsif ARM or ARMv7 or ARMv7_TRADITIONAL or C_LOOP or MIPS
+        subp 8, sp # align stack pointer
+        # t1 already contains the Callee.
+        andp MarkedBlockMask, t1
+        loadp MarkedBlock::m_vm[t1], t1
+        storep cfr, VM::topCallFrame[t1]
+        move cfr, a0
+        loadi Callee + PayloadOffset[cfr], t1
+        checkStackPointerAlignment(t3, 0xdead0001)
+        if C_LOOP
+            cloopCallNative offsetOfFunction[t1]
+        else
+            call offsetOfFunction[t1]
+        end
+        loadp Callee + PayloadOffset[cfr], t3
+        andp MarkedBlockMask, t3
+        loadp MarkedBlock::m_vm[t3], t3
+        addp 8, sp
+    else
+        error
+    end
+
+    btinz VM::m_exception[t3], .handleException
+
+    functionEpilogue()
+    ret
+
+.handleException:
+    storep cfr, VM::topCallFrame[t3]
+    jmp _llint_throw_from_slow_path_trampoline
+end
+
+
 macro getConstantScope(dst)
     loadpFromInstruction(6, t0)
     loadisFromInstruction(dst, t1)
index c57ebc3..46f72e0 100644 (file)
@@ -2094,6 +2094,45 @@ macro nativeCallTrampoline(executableOffsetToFunction)
     jmp _llint_throw_from_slow_path_trampoline
 end
 
+macro internalFunctionCallTrampoline(offsetOfFunction)
+    functionPrologue()
+    storep 0, CodeBlock[cfr]
+    loadp Callee[cfr], t0
+    andp MarkedBlockMask, t0, t1
+    loadp MarkedBlock::m_vm[t1], t1
+    storep cfr, VM::topCallFrame[t1]
+    if ARM64 or C_LOOP
+        storep lr, ReturnPC[cfr]
+    end
+    move cfr, a0
+    loadp Callee[cfr], t1
+    checkStackPointerAlignment(t3, 0xdead0001)
+    if C_LOOP
+        cloopCallNative offsetOfFunction[t1]
+    else
+        if X86_64_WIN
+            subp 32, sp
+        end
+        call offsetOfFunction[t1]
+        if X86_64_WIN
+            addp 32, sp
+        end
+    end
+
+    loadp Callee[cfr], t3
+    andp MarkedBlockMask, t3
+    loadp MarkedBlock::m_vm[t3], t3
+
+    btqnz VM::m_exception[t3], .handleException
+
+    functionEpilogue()
+    ret
+
+.handleException:
+    storep cfr, VM::topCallFrame[t3]
+    jmp _llint_throw_from_slow_path_trampoline
+end
+
 macro getConstantScope(dst)
     loadpFromInstruction(6, t0)
     loadisFromInstruction(dst, t1)
index 8233683..4d89aca 100644 (file)
@@ -50,8 +50,11 @@ const ClassInfo ArrayConstructor::s_info = { "Function", &InternalFunction::s_in
 @end
 */
 
+static EncodedJSValue JSC_HOST_CALL callArrayConstructor(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructWithArrayConstructor(ExecState*);
+
 ArrayConstructor::ArrayConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, callArrayConstructor, constructWithArrayConstructor)
 {
 }
 
@@ -100,25 +103,12 @@ static EncodedJSValue JSC_HOST_CALL constructWithArrayConstructor(ExecState* exe
     return JSValue::encode(constructArrayWithSizeQuirk(exec, args, exec->newTarget()));
 }
 
-ConstructType ArrayConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructWithArrayConstructor;
-    return ConstructType::Host;
-}
-
 static EncodedJSValue JSC_HOST_CALL callArrayConstructor(ExecState* exec)
 {
     ArgList args(exec);
     return JSValue::encode(constructArrayWithSizeQuirk(exec, args, JSValue()));
 }
 
-CallType ArrayConstructor::getCallData(JSCell*, CallData& callData)
-{
-    // equivalent to 'new Array(....)'
-    callData.native.function = callArrayConstructor;
-    return CallType::Host;
-}
-
 static ALWAYS_INLINE bool isArraySlowInline(ExecState* exec, ProxyObject* proxy)
 {
     VM& vm = exec->vm();
index 1584885..61652aa 100644 (file)
@@ -46,7 +46,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 protected:
@@ -54,9 +54,6 @@ protected:
 
 private:
     ArrayConstructor(VM&, Structure*);
-
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 JSValue constructArrayWithSizeQuirk(ExecState*, ArrayAllocationProfile*, JSGlobalObject*, JSValue length, JSValue prototype = JSValue());
index 52728f9..d0e9bd7 100644 (file)
@@ -36,18 +36,6 @@ STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(AsyncFunctionConstructor);
 
 const ClassInfo AsyncFunctionConstructor::s_info = { "AsyncFunction", &Base::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(AsyncFunctionConstructor) };
 
-AsyncFunctionConstructor::AsyncFunctionConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
-{
-}
-
-void AsyncFunctionConstructor::finishCreation(VM& vm, AsyncFunctionPrototype* prototype)
-{
-    Base::finishCreation(vm, "AsyncFunction");
-    putDirectWithoutTransition(vm, vm.propertyNames->prototype, prototype, PropertyAttribute::DontEnum | PropertyAttribute::DontDelete | PropertyAttribute::ReadOnly);
-    putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(1), PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
-}
-
 static EncodedJSValue JSC_HOST_CALL callAsyncFunctionConstructor(ExecState* exec)
 {
     ArgList args(exec);
@@ -60,16 +48,16 @@ static EncodedJSValue JSC_HOST_CALL constructAsyncFunctionConstructor(ExecState*
     return JSValue::encode(constructFunction(exec, asInternalFunction(exec->jsCallee())->globalObject(), args, FunctionConstructionMode::Async));
 }
 
-CallType AsyncFunctionConstructor::getCallData(JSCell*, CallData& callData)
+AsyncFunctionConstructor::AsyncFunctionConstructor(VM& vm, Structure* structure)
+    : InternalFunction(vm, structure, callAsyncFunctionConstructor, constructAsyncFunctionConstructor)
 {
-    callData.native.function = callAsyncFunctionConstructor;
-    return CallType::Host;
 }
 
-ConstructType AsyncFunctionConstructor::getConstructData(JSCell*, ConstructData& constructData)
+void AsyncFunctionConstructor::finishCreation(VM& vm, AsyncFunctionPrototype* prototype)
 {
-    constructData.native.function = constructAsyncFunctionConstructor;
-    return ConstructType::Host;
+    Base::finishCreation(vm, "AsyncFunction");
+    putDirectWithoutTransition(vm, vm.propertyNames->prototype, prototype, PropertyAttribute::DontEnum | PropertyAttribute::DontDelete | PropertyAttribute::ReadOnly);
+    putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(1), PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
 }
 
 } // namespace JSC
index 035a2c1..03efdba 100644 (file)
@@ -46,14 +46,12 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 private:
     AsyncFunctionConstructor(VM&, Structure*);
     void finishCreation(VM&, AsyncFunctionPrototype*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index aaa6a1f..c534190 100644 (file)
@@ -36,20 +36,6 @@ STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(AsyncGeneratorFunctionConstructor);
 
 const ClassInfo AsyncGeneratorFunctionConstructor::s_info = { "AsyncGeneratorFunction", &Base::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(AsyncGeneratorFunctionConstructor) };
 
-AsyncGeneratorFunctionConstructor::AsyncGeneratorFunctionConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
-{
-}
-
-void AsyncGeneratorFunctionConstructor::finishCreation(VM& vm, AsyncGeneratorFunctionPrototype* prototype)
-{
-    Base::finishCreation(vm, "AsyncGeneratorFunction");
-    putDirectWithoutTransition(vm, vm.propertyNames->prototype, prototype, PropertyAttribute::DontEnum | PropertyAttribute::DontDelete | PropertyAttribute::ReadOnly);
-
-    // Number of arguments for constructor
-    putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(1), PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
-}
-
 static EncodedJSValue JSC_HOST_CALL callAsyncGeneratorFunctionConstructor(ExecState* exec)
 {
     ArgList args(exec);
@@ -62,16 +48,18 @@ static EncodedJSValue JSC_HOST_CALL constructAsyncGeneratorFunctionConstructor(E
     return JSValue::encode(constructFunction(exec, asInternalFunction(exec->jsCallee())->globalObject(), args, FunctionConstructionMode::AsyncGenerator));
 }
 
-CallType AsyncGeneratorFunctionConstructor::getCallData(JSCell*, CallData& callData)
+AsyncGeneratorFunctionConstructor::AsyncGeneratorFunctionConstructor(VM& vm, Structure* structure)
+    : InternalFunction(vm, structure, callAsyncGeneratorFunctionConstructor, constructAsyncGeneratorFunctionConstructor)
 {
-    callData.native.function = callAsyncGeneratorFunctionConstructor;
-    return CallType::Host;
 }
 
-ConstructType AsyncGeneratorFunctionConstructor::getConstructData(JSCell*, ConstructData& constructData)
+void AsyncGeneratorFunctionConstructor::finishCreation(VM& vm, AsyncGeneratorFunctionPrototype* prototype)
 {
-    constructData.native.function = constructAsyncGeneratorFunctionConstructor;
-    return ConstructType::Host;
+    Base::finishCreation(vm, "AsyncGeneratorFunction");
+    putDirectWithoutTransition(vm, vm.propertyNames->prototype, prototype, PropertyAttribute::DontEnum | PropertyAttribute::DontDelete | PropertyAttribute::ReadOnly);
+
+    // Number of arguments for constructor
+    putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(1), PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
 }
 
 } // namespace JSC
index b8f150b..bc44ac6 100644 (file)
@@ -46,14 +46,12 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 private:
     AsyncGeneratorFunctionConstructor(VM&, Structure*);
     void finishCreation(VM&, AsyncGeneratorFunctionPrototype*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index 67a015a..f0ab042 100644 (file)
@@ -31,16 +31,10 @@ STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(BooleanConstructor);
 
 const ClassInfo BooleanConstructor::s_info = { "Function", &Base::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(BooleanConstructor) };
 
-BooleanConstructor::BooleanConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
-{
-}
-
-void BooleanConstructor::finishCreation(VM& vm, BooleanPrototype* booleanPrototype)
+// ECMA 15.6.1
+static EncodedJSValue JSC_HOST_CALL callBooleanConstructor(ExecState* exec)
 {
-    Base::finishCreation(vm, booleanPrototype->classInfo()->className);
-    putDirectWithoutTransition(vm, vm.propertyNames->prototype, booleanPrototype, PropertyAttribute::DontEnum | PropertyAttribute::DontDelete | PropertyAttribute::ReadOnly);
-    putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(1), PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
+    return JSValue::encode(jsBoolean(exec->argument(0).toBoolean(exec)));
 }
 
 // ECMA 15.6.2
@@ -56,22 +50,16 @@ static EncodedJSValue JSC_HOST_CALL constructWithBooleanConstructor(ExecState* e
     return JSValue::encode(obj);
 }
 
-ConstructType BooleanConstructor::getConstructData(JSCell*, ConstructData& constructData)
+BooleanConstructor::BooleanConstructor(VM& vm, Structure* structure)
+    : InternalFunction(vm, structure, callBooleanConstructor, constructWithBooleanConstructor)
 {
-    constructData.native.function = constructWithBooleanConstructor;
-    return ConstructType::Host;
 }
 
-// ECMA 15.6.1
-static EncodedJSValue JSC_HOST_CALL callBooleanConstructor(ExecState* exec)
-{
-    return JSValue::encode(jsBoolean(exec->argument(0).toBoolean(exec)));
-}
-
-CallType BooleanConstructor::getCallData(JSCell*, CallData& callData)
+void BooleanConstructor::finishCreation(VM& vm, BooleanPrototype* booleanPrototype)
 {
-    callData.native.function = callBooleanConstructor;
-    return CallType::Host;
+    Base::finishCreation(vm, booleanPrototype->classInfo()->className);
+    putDirectWithoutTransition(vm, vm.propertyNames->prototype, booleanPrototype, PropertyAttribute::DontEnum | PropertyAttribute::DontDelete | PropertyAttribute::ReadOnly);
+    putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(1), PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
 }
 
 JSObject* constructBooleanFromImmediateBoolean(ExecState* exec, JSGlobalObject* globalObject, JSValue immediateBooleanValue)
index bb8c5df..36ecc9f 100644 (file)
@@ -42,7 +42,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype) 
     { 
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info()); 
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info()); 
     }
 
 protected:
@@ -50,8 +50,6 @@ protected:
 
 private:
     BooleanConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 JSObject* constructBooleanFromImmediateBoolean(ExecState*, JSGlobalObject*, JSValue);
index b2f29cf..679965c 100644 (file)
@@ -68,8 +68,11 @@ const ClassInfo DateConstructor::s_info = { "Function", &InternalFunction::s_inf
 
 STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(DateConstructor);
 
+static EncodedJSValue JSC_HOST_CALL callDate(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructWithDateConstructor(ExecState*);
+
 DateConstructor::DateConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, callDate, constructWithDateConstructor)
 {
 }
 
@@ -153,12 +156,6 @@ static EncodedJSValue JSC_HOST_CALL constructWithDateConstructor(ExecState* exec
     return JSValue::encode(constructDate(exec, asInternalFunction(exec->jsCallee())->globalObject(), exec->newTarget(), args));
 }
 
-ConstructType DateConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructWithDateConstructor;
-    return ConstructType::Host;
-}
-
 // ECMA 15.9.2
 static EncodedJSValue JSC_HOST_CALL callDate(ExecState* exec)
 {
@@ -168,12 +165,6 @@ static EncodedJSValue JSC_HOST_CALL callDate(ExecState* exec)
     return JSValue::encode(jsNontrivialString(&vm, formatDateTime(ts, DateTimeFormatDateAndTime, false)));
 }
 
-CallType DateConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callDate;
-    return CallType::Host;
-}
-
 EncodedJSValue JSC_HOST_CALL dateParse(ExecState* exec)
 {
     VM& vm = exec->vm();
index fcea55f..307c6d5 100644 (file)
@@ -43,7 +43,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 protected:
@@ -51,8 +51,6 @@ protected:
 
 private:
     DateConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 JSObject* constructDate(ExecState*, JSGlobalObject*, JSValue newTarget, const ArgList&);
index 90671d5..4faed37 100644 (file)
@@ -106,7 +106,7 @@ inline EncodedJSValue throwVMDOMAttributeGetterTypeError(ExecState* state, Throw
 class StrictModeTypeErrorFunction : public InternalFunction {
 private:
     StrictModeTypeErrorFunction(VM& vm, Structure* structure, const String& message)
-        : InternalFunction(vm, structure)
+        : InternalFunction(vm, structure, callThrowTypeError, constructThrowTypeError)
         , m_message(message)
     {
     }
@@ -131,12 +131,6 @@ public:
         return JSValue::encode(jsNull());
     }
 
-    static ConstructType getConstructData(JSCell*, ConstructData& constructData)
-    {
-        constructData.native.function = constructThrowTypeError;
-        return ConstructType::Host;
-    }
-
     static EncodedJSValue JSC_HOST_CALL callThrowTypeError(ExecState* exec)
     {
         VM& vm = exec->vm();
@@ -145,17 +139,11 @@ public:
         return JSValue::encode(jsNull());
     }
 
-    static CallType getCallData(JSCell*, CallData& callData)
-    {
-        callData.native.function = callThrowTypeError;
-        return CallType::Host;
-    }
-
     DECLARE_INFO;
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype) 
     { 
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info()); 
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info()); 
     }
 
 private:
index daa7a90..b044c8d 100644 (file)
@@ -34,7 +34,7 @@ STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(ErrorConstructor);
 const ClassInfo ErrorConstructor::s_info = { "Function", &Base::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(ErrorConstructor) };
 
 ErrorConstructor::ErrorConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, Interpreter::callErrorConstructor, Interpreter::constructWithErrorConstructor)
 {
 }
 
@@ -63,12 +63,6 @@ EncodedJSValue JSC_HOST_CALL Interpreter::constructWithErrorConstructor(ExecStat
     return JSValue::encode(ErrorInstance::create(exec, errorStructure, message, nullptr, TypeNothing, false));
 }
 
-ConstructType ErrorConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = Interpreter::constructWithErrorConstructor;
-    return ConstructType::Host;
-}
-
 EncodedJSValue JSC_HOST_CALL Interpreter::callErrorConstructor(ExecState* exec)
 {
     JSValue message = exec->argument(0);
@@ -76,12 +70,6 @@ EncodedJSValue JSC_HOST_CALL Interpreter::callErrorConstructor(ExecState* exec)
     return JSValue::encode(ErrorInstance::create(exec, errorStructure, message, nullptr, TypeNothing, false));
 }
 
-CallType ErrorConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = Interpreter::callErrorConstructor;
-    return CallType::Host;
-}
-
 bool ErrorConstructor::put(JSCell* cell, ExecState* exec, PropertyName propertyName, JSValue value, PutPropertySlot& slot)
 {
     VM& vm = exec->vm();
index 63096bd..a0dd1b0 100644 (file)
@@ -42,7 +42,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype) 
     { 
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info()); 
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info()); 
     }
 
     std::optional<unsigned> stackTraceLimit() const { return m_stackTraceLimit; }
@@ -55,8 +55,6 @@ protected:
 
 private:
     ErrorConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 
     std::optional<unsigned> m_stackTraceLimit;
 };
index fa67cd5..d803616 100644 (file)
@@ -38,41 +38,29 @@ STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(FunctionConstructor);
 
 const ClassInfo FunctionConstructor::s_info = { "Function", &Base::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(FunctionConstructor) };
 
-FunctionConstructor::FunctionConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
-{
-}
-
-void FunctionConstructor::finishCreation(VM& vm, FunctionPrototype* functionPrototype)
-{
-    Base::finishCreation(vm, functionPrototype->classInfo()->className);
-    putDirectWithoutTransition(vm, vm.propertyNames->prototype, functionPrototype, PropertyAttribute::DontEnum | PropertyAttribute::DontDelete | PropertyAttribute::ReadOnly);
-    putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(1), PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
-}
-
 static EncodedJSValue JSC_HOST_CALL constructWithFunctionConstructor(ExecState* exec)
 {
     ArgList args(exec);
     return JSValue::encode(constructFunction(exec, asInternalFunction(exec->jsCallee())->globalObject(), args, FunctionConstructionMode::Function, exec->newTarget()));
 }
 
-ConstructType FunctionConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructWithFunctionConstructor;
-    return ConstructType::Host;
-}
-
+// ECMA 15.3.1 The Function Constructor Called as a Function
 static EncodedJSValue JSC_HOST_CALL callFunctionConstructor(ExecState* exec)
 {
     ArgList args(exec);
     return JSValue::encode(constructFunction(exec, asInternalFunction(exec->jsCallee())->globalObject(), args));
 }
 
-// ECMA 15.3.1 The Function Constructor Called as a Function
-CallType FunctionConstructor::getCallData(JSCell*, CallData& callData)
+FunctionConstructor::FunctionConstructor(VM& vm, Structure* structure)
+    : InternalFunction(vm, structure, callFunctionConstructor, constructWithFunctionConstructor)
+{
+}
+
+void FunctionConstructor::finishCreation(VM& vm, FunctionPrototype* functionPrototype)
 {
-    callData.native.function = callFunctionConstructor;
-    return CallType::Host;
+    Base::finishCreation(vm, functionPrototype->classInfo()->className);
+    putDirectWithoutTransition(vm, vm.propertyNames->prototype, functionPrototype, PropertyAttribute::DontEnum | PropertyAttribute::DontDelete | PropertyAttribute::ReadOnly);
+    putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(1), PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
 }
 
 // ECMA 15.3.2 The Function Constructor
index 13c37fd..7ce3f48 100644 (file)
@@ -45,14 +45,12 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype) 
     { 
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info()); 
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info()); 
     }
 
 private:
     FunctionConstructor(VM&, Structure*);
     void finishCreation(VM&, FunctionPrototype*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 enum class FunctionConstructionMode {
index 18f8b5e..4080e39 100644 (file)
@@ -43,8 +43,14 @@ const ClassInfo FunctionPrototype::s_info = { "Function", &Base::s_info, nullptr
 
 static EncodedJSValue JSC_HOST_CALL functionProtoFuncToString(ExecState*);
 
+// ECMA 15.3.4
+static EncodedJSValue JSC_HOST_CALL callFunctionPrototype(ExecState*)
+{
+    return JSValue::encode(jsUndefined());
+}
+
 FunctionPrototype::FunctionPrototype(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, callFunctionPrototype, nullptr)
 {
 }
 
@@ -77,18 +83,6 @@ void FunctionPrototype::initRestrictedProperties(ExecState* exec, JSGlobalObject
     putDirectAccessor(exec, vm.propertyNames->arguments, errorGetterSetter, PropertyAttribute::DontEnum | PropertyAttribute::Accessor);
 }
 
-static EncodedJSValue JSC_HOST_CALL callFunctionPrototype(ExecState*)
-{
-    return JSValue::encode(jsUndefined());
-}
-
-// ECMA 15.3.4
-CallType FunctionPrototype::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callFunctionPrototype;
-    return CallType::Host;
-}
-
 EncodedJSValue JSC_HOST_CALL functionProtoFuncToString(ExecState* exec)
 {
     VM& vm = exec->vm();
index baf7ccb..9388870 100644 (file)
@@ -41,7 +41,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue proto)
     {
-        return Structure::create(vm, globalObject, proto, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, proto, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
     DECLARE_INFO;
@@ -51,7 +51,6 @@ protected:
 
 private:
     FunctionPrototype(VM&, Structure*);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index e54e63f..3743c6a 100644 (file)
@@ -36,18 +36,6 @@ STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(GeneratorFunctionConstructor);
 
 const ClassInfo GeneratorFunctionConstructor::s_info = { "GeneratorFunction", &Base::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(GeneratorFunctionConstructor) };
 
-GeneratorFunctionConstructor::GeneratorFunctionConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
-{
-}
-
-void GeneratorFunctionConstructor::finishCreation(VM& vm, GeneratorFunctionPrototype* generatorFunctionPrototype)
-{
-    Base::finishCreation(vm, "GeneratorFunction");
-    putDirectWithoutTransition(vm, vm.propertyNames->prototype, generatorFunctionPrototype, PropertyAttribute::DontEnum | PropertyAttribute::DontDelete | PropertyAttribute::ReadOnly);
-    putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(1), PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
-}
-
 static EncodedJSValue JSC_HOST_CALL callGeneratorFunctionConstructor(ExecState* exec)
 {
     ArgList args(exec);
@@ -60,16 +48,16 @@ static EncodedJSValue JSC_HOST_CALL constructGeneratorFunctionConstructor(ExecSt
     return JSValue::encode(constructFunction(exec, asInternalFunction(exec->jsCallee())->globalObject(), args, FunctionConstructionMode::Generator, exec->newTarget()));
 }
 
-CallType GeneratorFunctionConstructor::getCallData(JSCell*, CallData& callData)
+GeneratorFunctionConstructor::GeneratorFunctionConstructor(VM& vm, Structure* structure)
+    : InternalFunction(vm, structure, callGeneratorFunctionConstructor, constructGeneratorFunctionConstructor)
 {
-    callData.native.function = callGeneratorFunctionConstructor;
-    return CallType::Host;
 }
 
-ConstructType GeneratorFunctionConstructor::getConstructData(JSCell*, ConstructData& constructData)
+void GeneratorFunctionConstructor::finishCreation(VM& vm, GeneratorFunctionPrototype* generatorFunctionPrototype)
 {
-    constructData.native.function = constructGeneratorFunctionConstructor;
-    return ConstructType::Host;
+    Base::finishCreation(vm, "GeneratorFunction");
+    putDirectWithoutTransition(vm, vm.propertyNames->prototype, generatorFunctionPrototype, PropertyAttribute::DontEnum | PropertyAttribute::DontDelete | PropertyAttribute::ReadOnly);
+    putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(1), PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
 }
 
 } // namespace JSC
index f28c71c..f46d8c5 100644 (file)
@@ -52,14 +52,12 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 private:
     GeneratorFunctionConstructor(VM&, Structure*);
     void finishCreation(VM&, GeneratorFunctionPrototype*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index 3d3fd1a..7b66438 100644 (file)
@@ -34,18 +34,24 @@ STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(InternalFunction);
 
 const ClassInfo InternalFunction::s_info = { "Function", &Base::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(InternalFunction) };
 
-InternalFunction::InternalFunction(VM& vm, Structure* structure)
+InternalFunction::InternalFunction(VM& vm, Structure* structure, NativeFunction functionForCall, NativeFunction functionForConstruct)
     : JSDestructibleObject(vm, structure)
+    , m_functionForCall(functionForCall)
+    , m_functionForConstruct(functionForConstruct ? functionForConstruct : callHostFunctionAsConstructor)
 {
     // exec->vm() wants callees to not be large allocations.
     RELEASE_ASSERT(!isLargeAllocation());
+    ASSERT_WITH_MESSAGE(m_functionForCall, "[[Call]] must be implemented");
+    ASSERT(m_functionForConstruct);
 }
 
 void InternalFunction::finishCreation(VM& vm, const String& name, NameVisibility nameVisibility)
 {
     Base::finishCreation(vm);
     ASSERT(inherits(vm, info()));
-    ASSERT(methodTable(vm)->getCallData != InternalFunction::info()->methodTable.getCallData);
+    ASSERT(methodTable(vm)->getCallData == InternalFunction::info()->methodTable.getCallData);
+    ASSERT(methodTable(vm)->getConstructData == InternalFunction::info()->methodTable.getConstructData);
+    ASSERT(type() == InternalFunctionType);
     JSString* nameString = jsString(&vm, name);
     m_originalName.set(vm, this, nameString);
     if (nameVisibility == NameVisibility::Visible)
@@ -78,10 +84,21 @@ const String InternalFunction::displayName(VM& vm)
     return String();
 }
 
-CallType InternalFunction::getCallData(JSCell*, CallData&)
+CallType InternalFunction::getCallData(JSCell* cell, CallData& callData)
 {
-    RELEASE_ASSERT_NOT_REACHED();
-    return CallType::None;
+    auto* function = jsCast<InternalFunction*>(cell);
+    ASSERT(function->m_functionForCall);
+    callData.native.function = function->m_functionForCall;
+    return CallType::Host;
+}
+
+ConstructType InternalFunction::getConstructData(JSCell* cell, ConstructData& constructData)
+{
+    auto* function = jsCast<InternalFunction*>(cell);
+    if (function->m_functionForConstruct == callHostFunctionAsConstructor)
+        return ConstructType::None;
+    constructData.native.function = function->m_functionForConstruct;
+    return ConstructType::Host;
 }
 
 const String InternalFunction::calculatedDisplayName(VM& vm)
index 3a8f22e..ec42bb8 100644 (file)
@@ -23,6 +23,7 @@
 
 #pragma once
 
+#include "CodeSpecializationKind.h"
 #include "JSDestructibleObject.h"
 
 namespace JSC {
@@ -30,6 +31,8 @@ namespace JSC {
 class FunctionPrototype;
 
 class InternalFunction : public JSDestructibleObject {
+    friend class JIT;
+    friend class LLIntOffsetsExtractor;
 public:
     typedef JSDestructibleObject Base;
     static const unsigned StructureFlags = Base::StructureFlags | ImplementsHasInstance | ImplementsDefaultHasInstance | TypeOfShouldCallGetCallData;
@@ -44,20 +47,40 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue proto)
     { 
-        return Structure::create(vm, globalObject, proto, TypeInfo(ObjectType, StructureFlags), info()); 
+        return Structure::create(vm, globalObject, proto, TypeInfo(InternalFunctionType, StructureFlags), info()); 
     }
 
     static Structure* createSubclassStructure(ExecState*, JSValue newTarget, Structure*);
 
+    NativeFunction nativeFunctionFor(CodeSpecializationKind kind)
+    {
+        if (kind == CodeForCall)
+            return m_functionForCall;
+        ASSERT(kind == CodeForConstruct);
+        return m_functionForConstruct;
+    }
+
+    static ptrdiff_t offsetOfNativeFunctionFor(CodeSpecializationKind kind)
+    {
+        if (kind == CodeForCall)
+            return OBJECT_OFFSETOF(InternalFunction, m_functionForCall);
+        ASSERT(kind == CodeForConstruct);
+        return OBJECT_OFFSETOF(InternalFunction, m_functionForConstruct);
+    }
+
 protected:
-    JS_EXPORT_PRIVATE InternalFunction(VM&, Structure*);
+    JS_EXPORT_PRIVATE InternalFunction(VM&, Structure*, NativeFunction functionForCall, NativeFunction functionForConstruct);
 
     enum class NameVisibility { Visible, Anonymous };
     JS_EXPORT_PRIVATE void finishCreation(VM&, const String& name, NameVisibility = NameVisibility::Visible);
 
     JS_EXPORT_PRIVATE static Structure* createSubclassStructureSlow(ExecState*, JSValue newTarget, Structure*);
 
-    static CallType getCallData(JSCell*, CallData&);
+    JS_EXPORT_PRIVATE static ConstructType getConstructData(JSCell*, ConstructData&);
+    JS_EXPORT_PRIVATE static CallType getCallData(JSCell*, CallData&);
+
+    NativeFunction m_functionForCall;
+    NativeFunction m_functionForConstruct;
     WriteBarrier<JSString> m_originalName;
 };
 
index d1a184f..03b87b0 100644 (file)
@@ -49,6 +49,9 @@ static EncodedJSValue JSC_HOST_CALL IntlCollatorConstructorFuncSupportedLocalesO
 
 namespace JSC {
 
+static EncodedJSValue JSC_HOST_CALL callIntlCollator(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructIntlCollator(ExecState*);
+
 const ClassInfo IntlCollatorConstructor::s_info = { "Function", &InternalFunction::s_info, &collatorConstructorTable, nullptr, CREATE_METHOD_TABLE(IntlCollatorConstructor) };
 
 /* Source for IntlCollatorConstructor.lut.h
@@ -66,11 +69,11 @@ IntlCollatorConstructor* IntlCollatorConstructor::create(VM& vm, Structure* stru
 
 Structure* IntlCollatorConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 IntlCollatorConstructor::IntlCollatorConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, callIntlCollator, constructIntlCollator)
 {
 }
 
@@ -123,18 +126,6 @@ static EncodedJSValue JSC_HOST_CALL callIntlCollator(ExecState* state)
     return JSValue::encode(collator);
 }
 
-ConstructType IntlCollatorConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructIntlCollator;
-    return ConstructType::Host;
-}
-
-CallType IntlCollatorConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callIntlCollator;
-    return CallType::Host;
-}
-
 EncodedJSValue JSC_HOST_CALL IntlCollatorConstructorFuncSupportedLocalesOf(ExecState* state)
 {
     VM& vm = state->vm();
index cf3468f..0db86c7 100644 (file)
@@ -51,8 +51,6 @@ protected:
 
 private:
     IntlCollatorConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
     static void visitChildren(JSCell*, SlotVisitor&);
     
     WriteBarrier<Structure> m_collatorStructure;
index 5010e17..5af82ab 100644 (file)
@@ -66,11 +66,14 @@ IntlDateTimeFormatConstructor* IntlDateTimeFormatConstructor::create(VM& vm, Str
 
 Structure* IntlDateTimeFormatConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
+static EncodedJSValue JSC_HOST_CALL callIntlDateTimeFormat(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructIntlDateTimeFormat(ExecState*);
+
 IntlDateTimeFormatConstructor::IntlDateTimeFormatConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, callIntlDateTimeFormat, constructIntlDateTimeFormat)
 {
 }
 
@@ -123,18 +126,6 @@ static EncodedJSValue JSC_HOST_CALL callIntlDateTimeFormat(ExecState* state)
     }));
 }
 
-ConstructType IntlDateTimeFormatConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructIntlDateTimeFormat;
-    return ConstructType::Host;
-}
-
-CallType IntlDateTimeFormatConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callIntlDateTimeFormat;
-    return CallType::Host;
-}
-
 EncodedJSValue JSC_HOST_CALL IntlDateTimeFormatConstructorFuncSupportedLocalesOf(ExecState* state)
 {
     VM& vm = state->vm();
index f1ba267..8e61065 100644 (file)
@@ -51,8 +51,6 @@ protected:
 
 private:
     IntlDateTimeFormatConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
     static void visitChildren(JSCell*, SlotVisitor&);
     
     WriteBarrier<Structure> m_dateTimeFormatStructure;
index 2f6eadf..297210c 100644 (file)
@@ -66,11 +66,14 @@ IntlNumberFormatConstructor* IntlNumberFormatConstructor::create(VM& vm, Structu
 
 Structure* IntlNumberFormatConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
+static EncodedJSValue JSC_HOST_CALL callIntlNumberFormat(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructIntlNumberFormat(ExecState*);
+
 IntlNumberFormatConstructor::IntlNumberFormatConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, callIntlNumberFormat, constructIntlNumberFormat)
 {
 }
 
@@ -123,18 +126,6 @@ static EncodedJSValue JSC_HOST_CALL callIntlNumberFormat(ExecState* state)
     }));
 }
 
-ConstructType IntlNumberFormatConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructIntlNumberFormat;
-    return ConstructType::Host;
-}
-
-CallType IntlNumberFormatConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callIntlNumberFormat;
-    return CallType::Host;
-}
-
 EncodedJSValue JSC_HOST_CALL IntlNumberFormatConstructorFuncSupportedLocalesOf(ExecState* state)
 {
     VM& vm = state->vm();
index d762161..e43dea3 100644 (file)
@@ -51,8 +51,6 @@ protected:
 
 private:
     IntlNumberFormatConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
     static void visitChildren(JSCell*, SlotVisitor&);
     
     WriteBarrier<Structure> m_numberFormatStructure;
index dbb373c..bf2e917 100644 (file)
@@ -44,8 +44,11 @@ const ClassInfo JSArrayBufferConstructor::s_info = {
     CREATE_METHOD_TABLE(JSArrayBufferConstructor)
 };
 
+static EncodedJSValue JSC_HOST_CALL callArrayBuffer(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructArrayBuffer(ExecState*);
+
 JSArrayBufferConstructor::JSArrayBufferConstructor(VM& vm, Structure* structure, ArrayBufferSharingMode sharingMode)
-    : Base(vm, structure)
+    : Base(vm, structure, callArrayBuffer, constructArrayBuffer)
     , m_sharingMode(sharingMode)
 {
 }
@@ -77,7 +80,7 @@ Structure* JSArrayBufferConstructor::createStructure(
     VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
     return Structure::create(
-        vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 static EncodedJSValue JSC_HOST_CALL constructArrayBuffer(ExecState* exec)
@@ -121,19 +124,6 @@ static EncodedJSValue JSC_HOST_CALL callArrayBuffer(ExecState* exec)
     return JSValue::encode(throwConstructorCannotBeCalledAsFunctionTypeError(exec, scope, "ArrayBuffer"));
 }
 
-ConstructType JSArrayBufferConstructor::getConstructData(
-    JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructArrayBuffer;
-    return ConstructType::Host;
-}
-
-CallType JSArrayBufferConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callArrayBuffer;
-    return CallType::Host;
-}
-
 // ------------------------------ Functions --------------------------------
 
 // ECMA 24.1.3.1
index 9c75324..794ff86 100644 (file)
@@ -50,10 +50,6 @@ public:
     
     ArrayBufferSharingMode sharingMode() const { return m_sharingMode; }
 
-protected:
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
-
 private:
     ArrayBufferSharingMode m_sharingMode;
 };
index 3f18e0e..7b6dfd4 100644 (file)
@@ -57,10 +57,6 @@ public:
 #endif
     
     static Structure* createStructure(VM&, JSGlobalObject*, JSValue prototype);
-
-protected:
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index 46039fa..858336f 100644 (file)
 namespace JSC {
 
 template<typename ViewClass>
+static EncodedJSValue JSC_HOST_CALL callGenericTypedArrayView(ExecState*);
+
+template<typename ViewClass>
+EncodedJSValue JSC_HOST_CALL constructGenericTypedArrayView(ExecState*);
+
+template<typename ViewClass>
 JSGenericTypedArrayViewConstructor<ViewClass>::JSGenericTypedArrayViewConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, callGenericTypedArrayView<ViewClass>, constructGenericTypedArrayView<ViewClass>)
 {
 }
 
@@ -73,7 +79,7 @@ Structure* JSGenericTypedArrayViewConstructor<ViewClass>::createStructure(
     VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
     return Structure::create(
-        vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 template<typename ViewClass>
@@ -199,9 +205,6 @@ inline JSObject* constructGenericTypedArrayViewWithArguments(ExecState* exec, St
 }
 
 template<typename ViewClass>
-EncodedJSValue JSC_HOST_CALL constructGenericTypedArrayView(ExecState*);
-
-template<typename ViewClass>
 EncodedJSValue JSC_HOST_CALL constructGenericTypedArrayView(ExecState* exec)
 {
     VM& vm = exec->vm();
@@ -249,13 +252,6 @@ EncodedJSValue JSC_HOST_CALL constructGenericTypedArrayView(ExecState* exec)
 }
 
 template<typename ViewClass>
-ConstructType JSGenericTypedArrayViewConstructor<ViewClass>::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructGenericTypedArrayView<ViewClass>;
-    return ConstructType::Host;
-}
-
-template<typename ViewClass>
 static EncodedJSValue JSC_HOST_CALL callGenericTypedArrayView(ExecState* exec)
 {
     VM& vm = exec->vm();
@@ -263,11 +259,4 @@ static EncodedJSValue JSC_HOST_CALL callGenericTypedArrayView(ExecState* exec)
     return JSValue::encode(throwConstructorCannotBeCalledAsFunctionTypeError(exec, scope, ViewClass::info()->className));
 }
 
-template<typename ViewClass>
-CallType JSGenericTypedArrayViewConstructor<ViewClass>::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callGenericTypedArrayView<ViewClass>;
-    return CallType::Host;
-}
-
 } // namespace JSC
index 17fed89..da3f813 100644 (file)
@@ -54,12 +54,7 @@ JSInternalPromiseConstructor* JSInternalPromiseConstructor::create(VM& vm, Struc
 
 Structure* JSInternalPromiseConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
-}
-
-JSInternalPromiseConstructor::JSInternalPromiseConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
-{
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 static EncodedJSValue JSC_HOST_CALL constructPromise(ExecState* exec)
@@ -71,16 +66,9 @@ static EncodedJSValue JSC_HOST_CALL constructPromise(ExecState* exec)
     return JSValue::encode(promise);
 }
 
-ConstructType JSInternalPromiseConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructPromise;
-    return ConstructType::Host;
-}
-
-CallType JSInternalPromiseConstructor::getCallData(JSCell*, CallData& callData)
+JSInternalPromiseConstructor::JSInternalPromiseConstructor(VM& vm, Structure* structure)
+    : Base(vm, structure, constructPromise, constructPromise)
 {
-    callData.native.function = constructPromise;
-    return CallType::Host;
 }
 
 } // namespace JSC
index 81bd2b8..098a385 100644 (file)
@@ -44,8 +44,6 @@ public:
 
 private:
     JSInternalPromiseConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index d216111..d47b8d4 100644 (file)
@@ -70,11 +70,20 @@ JSPromiseConstructor* JSPromiseConstructor::create(VM& vm, Structure* structure,
 
 Structure* JSPromiseConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
+
+static EncodedJSValue JSC_HOST_CALL callPromise(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructPromise(ExecState*);
+
 JSPromiseConstructor::JSPromiseConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, callPromise, constructPromise)
+{
+}
+
+JSPromiseConstructor::JSPromiseConstructor(VM& vm, Structure* structure, NativeFunction functionForCall, NativeFunction functionForConstruct)
+    : Base(vm, structure, functionForCall, functionForConstruct)
 {
 }
 
@@ -118,20 +127,4 @@ static EncodedJSValue JSC_HOST_CALL callPromise(ExecState* exec)
     return JSValue::encode(throwConstructorCannotBeCalledAsFunctionTypeError(exec, scope, "Promise"));
 }
 
-ConstructType JSPromiseConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructPromise;
-    return ConstructType::Host;
-}
-
-CallType JSPromiseConstructor::getCallData(JSCell*, CallData& callData)
-{
-    // FIXME: This is workaround. Since JSC does not expose @isConstructor to JS builtins,
-    // we use typeof function === "function" now. And since typeof constructorWithoutCallability
-    // returns "object", we need to define [[Call]] for now.
-    // https://bugs.webkit.org/show_bug.cgi?id=144093
-    callData.native.function = callPromise;
-    return CallType::Host;
-}
-
 } // namespace JSC
index 0beca04..ebdf571 100644 (file)
@@ -45,12 +45,10 @@ public:
 
 protected:
     JSPromiseConstructor(VM&, Structure*);
+    JSPromiseConstructor(VM&, Structure*, NativeFunction, NativeFunction);
     void finishCreation(VM&, JSPromisePrototype*, GetterSetter*);
 
 private:
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
-
     void addOwnInternalSlots(VM&, JSGlobalObject*);
 };
 
index c017023..85356d3 100644 (file)
@@ -59,6 +59,7 @@ enum JSType : uint8_t {
     FinalObjectType,
     JSCalleeType,
     JSFunctionType,
+    InternalFunctionType,
     NumberObjectType,
     ErrorInstanceType,
     PureForwardingProxyType,
index 7b46e64..2c805f5 100644 (file)
 
 namespace JSC {
 
+static EncodedJSValue JSC_HOST_CALL constructTypedArrayView(ExecState*);
+
 JSTypedArrayViewConstructor::JSTypedArrayViewConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, constructTypedArrayView, constructTypedArrayView)
 {
 }
 
@@ -58,7 +60,7 @@ void JSTypedArrayViewConstructor::finishCreation(VM& vm, JSGlobalObject* globalO
 Structure* JSTypedArrayViewConstructor::createStructure(
     VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 
@@ -70,16 +72,4 @@ static EncodedJSValue JSC_HOST_CALL constructTypedArrayView(ExecState* exec)
     return throwVMTypeError(exec, scope, ASCIILiteral("%TypedArray% should not be called directly"));
 }
 
-ConstructType JSTypedArrayViewConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructTypedArrayView;
-    return ConstructType::Host;
-}
-
-CallType JSTypedArrayViewConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = constructTypedArrayView;
-    return CallType::Host;
-}
-
 } // namespace JSC
index d7817e2..4145ccc 100644 (file)
@@ -51,9 +51,6 @@ public:
     DECLARE_INFO;
 
     static Structure* createStructure(VM&, JSGlobalObject*, JSValue prototype);
-protected:
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
     
 } // namespace JSC
index 960ee8b..3914f2c 100644 (file)
@@ -47,6 +47,14 @@ void MapConstructor::finishCreation(VM& vm, MapPrototype* mapPrototype, GetterSe
     putDirectNonIndexAccessor(vm, vm.propertyNames->speciesSymbol, speciesSymbol, PropertyAttribute::Accessor | PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
 }
 
+static EncodedJSValue JSC_HOST_CALL callMap(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructMap(ExecState*);
+
+MapConstructor::MapConstructor(VM& vm, Structure* structure)
+    : Base(vm, structure, callMap, constructMap)
+{
+}
+
 static EncodedJSValue JSC_HOST_CALL callMap(ExecState* exec)
 {
     VM& vm = exec->vm();
@@ -113,18 +121,6 @@ static EncodedJSValue JSC_HOST_CALL constructMap(ExecState* exec)
     return JSValue::encode(map);
 }
 
-ConstructType MapConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructMap;
-    return ConstructType::Host;
-}
-
-CallType MapConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callMap;
-    return CallType::Host;
-}
-
 EncodedJSValue JSC_HOST_CALL mapPrivateFuncMapBucketHead(ExecState* exec)
 {
     ASSERT(isJSMap(exec->argument(0)));
index c48a35a..64571c7 100644 (file)
@@ -47,17 +47,13 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 private:
-    MapConstructor(VM& vm, Structure* structure)
-        : Base(vm, structure)
-    {
-    }
+    MapConstructor(VM&, Structure*);
+
     void finishCreation(VM&, MapPrototype*, GetterSetter* speciesSymbol);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 EncodedJSValue JSC_HOST_CALL mapPrivateFuncMapBucketHead(ExecState*);
index 57fc1c4..5fd3a67 100644 (file)
@@ -35,7 +35,7 @@ STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(NativeErrorConstructor);
 const ClassInfo NativeErrorConstructor::s_info = { "Function", &InternalFunction::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(NativeErrorConstructor) };
 
 NativeErrorConstructor::NativeErrorConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, Interpreter::callNativeErrorConstructor, Interpreter::constructWithNativeErrorConstructor)
 {
 }
 
@@ -73,12 +73,6 @@ EncodedJSValue JSC_HOST_CALL Interpreter::constructWithNativeErrorConstructor(Ex
     return JSValue::encode(ErrorInstance::create(exec, errorStructure, message, nullptr, TypeNothing, false));
 }
 
-ConstructType NativeErrorConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = Interpreter::constructWithNativeErrorConstructor;
-    return ConstructType::Host;
-}
-    
 EncodedJSValue JSC_HOST_CALL Interpreter::callNativeErrorConstructor(ExecState* exec)
 {
     JSValue message = exec->argument(0);
@@ -86,10 +80,4 @@ EncodedJSValue JSC_HOST_CALL Interpreter::callNativeErrorConstructor(ExecState*
     return JSValue::encode(ErrorInstance::create(exec, errorStructure, message, nullptr, TypeNothing, false));
 }
 
-CallType NativeErrorConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = Interpreter::callNativeErrorConstructor;
-    return CallType::Host;
-}
-
 } // namespace JSC
index 16e772d..d2b8097 100644 (file)
@@ -44,7 +44,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
     Structure* errorStructure() { return m_errorStructure.get(); }
@@ -54,8 +54,6 @@ protected:
 
 private:
     NativeErrorConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
     static void visitChildren(JSCell*, SlotVisitor&);
 
     WriteBarrier<Structure> m_errorStructure;
index ba46b30..a56cab3 100644 (file)
@@ -40,15 +40,9 @@ static EncodedJSValue JSC_HOST_CALL callReturnUndefined(ExecState*)
 }
 }
 
-CallType NullGetterFunction::getCallData(JSCell*, CallData& callData)
+NullGetterFunction::NullGetterFunction(VM& vm, Structure* structure)
+    : Base(vm, structure, NullGetterFunctionInternal::callReturnUndefined, nullptr)
 {
-    callData.native.function = NullGetterFunctionInternal::callReturnUndefined;
-    return CallType::Host;
-}
-
-ConstructType NullGetterFunction::getConstructData(JSCell*, ConstructData&)
-{
-    return ConstructType::None;
 }
 
 }
index 6339773..1f307d7 100644 (file)
@@ -44,16 +44,11 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 private:
-    NullGetterFunction(VM& vm, Structure* structure)
-        : Base(vm, structure)
-    {
-    }
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
+    NullGetterFunction(VM&, Structure*);
 };
 
 } // namespace JSC
index 6af0d1a..cdd112e 100644 (file)
@@ -82,15 +82,9 @@ static EncodedJSValue JSC_HOST_CALL callReturnUndefined(ExecState* exec)
 }
 }
 
-CallType NullSetterFunction::getCallData(JSCell*, CallData& callData)
+NullSetterFunction::NullSetterFunction(VM& vm, Structure* structure)
+    : Base(vm, structure, NullSetterFunctionInternal::callReturnUndefined, nullptr)
 {
-    callData.native.function = NullSetterFunctionInternal::callReturnUndefined;
-    return CallType::Host;
-}
-
-ConstructType NullSetterFunction::getConstructData(JSCell*, ConstructData&)
-{
-    return ConstructType::None;
 }
 
 }
index 7c4d964..051503d 100644 (file)
@@ -44,16 +44,11 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 private:
-    NullSetterFunction(VM& vm, Structure* structure)
-        : Base(vm, structure)
-    {
-    }
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
+    NullSetterFunction(VM&, Structure*);
 };
 
 } // namespace JSC
index b311427..e3cc1eb 100644 (file)
@@ -53,8 +53,11 @@ const ClassInfo NumberConstructor::s_info = { "Function", &InternalFunction::s_i
 @end
 */
 
+static EncodedJSValue JSC_HOST_CALL callNumberConstructor(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructNumberConstructor(ExecState*);
+
 NumberConstructor::NumberConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, callNumberConstructor, constructNumberConstructor)
 {
 }
 
@@ -80,7 +83,7 @@ void NumberConstructor::finishCreation(VM& vm, NumberPrototype* numberPrototype)
 }
 
 // ECMA 15.7.1
-static EncodedJSValue JSC_HOST_CALL constructWithNumberConstructor(ExecState* exec)
+static EncodedJSValue JSC_HOST_CALL constructNumberConstructor(ExecState* exec)
 {
     VM& vm = exec->vm();
     auto scope = DECLARE_THROW_SCOPE(vm);
@@ -94,24 +97,12 @@ static EncodedJSValue JSC_HOST_CALL constructWithNumberConstructor(ExecState* ex
     return JSValue::encode(object);
 }
 
-ConstructType NumberConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructWithNumberConstructor;
-    return ConstructType::Host;
-}
-
 // ECMA 15.7.2
 static EncodedJSValue JSC_HOST_CALL callNumberConstructor(ExecState* exec)
 {
     return JSValue::encode(jsNumber(!exec->argumentCount() ? 0 : exec->uncheckedArgument(0).toNumber(exec)));
 }
 
-CallType NumberConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callNumberConstructor;
-    return CallType::Host;
-}
-
 // ECMA-262 20.1.2.3
 static EncodedJSValue JSC_HOST_CALL numberConstructorFuncIsInteger(ExecState* exec)
 {
index 51e4fa3..10f58a2 100644 (file)
@@ -43,7 +43,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue proto) 
     { 
-        return Structure::create(vm, globalObject, proto, TypeInfo(ObjectType, StructureFlags), info()); 
+        return Structure::create(vm, globalObject, proto, TypeInfo(InternalFunctionType, StructureFlags), info()); 
     }
 
 protected:
@@ -51,8 +51,6 @@ protected:
 
 private:
     NumberConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index 0ee9665..a873a81 100644 (file)
@@ -90,8 +90,12 @@ const ClassInfo ObjectConstructor::s_info = { "Function", &InternalFunction::s_i
 @end
 */
 
+
+static EncodedJSValue JSC_HOST_CALL callObjectConstructor(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructWithObjectConstructor(ExecState*);
+
 ObjectConstructor::ObjectConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, callObjectConstructor, constructWithObjectConstructor)
 {
 }
 
@@ -143,23 +147,11 @@ static EncodedJSValue JSC_HOST_CALL constructWithObjectConstructor(ExecState* ex
     return JSValue::encode(constructObject(exec, exec->newTarget()));
 }
 
-ConstructType ObjectConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructWithObjectConstructor;
-    return ConstructType::Host;
-}
-
 static EncodedJSValue JSC_HOST_CALL callObjectConstructor(ExecState* exec)
 {
     return JSValue::encode(constructObject(exec, JSValue()));
 }
 
-CallType ObjectConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callObjectConstructor;
-    return CallType::Host;
-}
-
 EncodedJSValue JSC_HOST_CALL objectConstructorGetPrototypeOf(ExecState* exec)
 {
     VM& vm = exec->vm();
index 10f92d2..3bd030a 100644 (file)
@@ -50,7 +50,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 protected:
@@ -58,8 +58,6 @@ protected:
 
 private:
     ObjectConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 inline JSObject* constructEmptyObject(ExecState* exec, Structure* structure)
index 1f3c426..58e1242 100644 (file)
@@ -48,8 +48,11 @@ ProxyConstructor* ProxyConstructor::create(VM& vm, Structure* structure)
     return constructor;
 }
 
+static EncodedJSValue JSC_HOST_CALL callProxy(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructProxyObject(ExecState*);
+
 ProxyConstructor::ProxyConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, callProxy, constructProxyObject)
 {
 }
 
@@ -103,22 +106,10 @@ static EncodedJSValue JSC_HOST_CALL constructProxyObject(ExecState* exec)
     return JSValue::encode(ProxyObject::create(exec, exec->lexicalGlobalObject(), target, handler));
 }
 
-ConstructType ProxyConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructProxyObject;
-    return ConstructType::Host;
-}
-
 static EncodedJSValue JSC_HOST_CALL callProxy(ExecState* exec)
 {
     auto scope = DECLARE_THROW_SCOPE(exec->vm());
     return JSValue::encode(throwConstructorCannotBeCalledAsFunctionTypeError(exec, scope, "Proxy"));
 }
 
-CallType ProxyConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callProxy;
-    return CallType::Host;
-}
-
 } // namespace JSC
index 48f53c8..bac60d2 100644 (file)
@@ -40,15 +40,13 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype) 
     { 
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info()); 
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info()); 
     }
 
     void finishCreation(VM&, const char* name, JSGlobalObject*);
 
 private:
     ProxyConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 
     static EncodedJSValue getGetter(ExecState*, EncodedJSValue thisValue, PropertyName);
 };
index a5fca78..f875f65 100644 (file)
@@ -42,8 +42,10 @@ ProxyRevoke* ProxyRevoke::create(VM& vm, Structure* structure, ProxyObject* prox
     return revoke;
 }
 
+static EncodedJSValue JSC_HOST_CALL performProxyRevoke(ExecState*);
+
 ProxyRevoke::ProxyRevoke(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, performProxyRevoke, nullptr)
 {
 }
 
@@ -69,12 +71,6 @@ static EncodedJSValue JSC_HOST_CALL performProxyRevoke(ExecState* exec)
     return JSValue::encode(jsUndefined());
 }
 
-CallType ProxyRevoke::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = performProxyRevoke;
-    return CallType::Host;
-}
-
 void ProxyRevoke::visitChildren(JSCell* cell, SlotVisitor& visitor)
 {
     ProxyRevoke* thisObject = jsCast<ProxyRevoke*>(cell);
index e028a7d..126876e 100644 (file)
@@ -42,7 +42,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype) 
     { 
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info()); 
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info()); 
     }
 
     void finishCreation(VM&, const char* name, ProxyObject*);
@@ -52,7 +52,6 @@ public:
 
 private:
     ProxyRevoke(VM&, Structure*);
-    static CallType getCallData(JSCell*, CallData&);
 
     WriteBarrier<Unknown> m_proxy;
 };
index 1c67dc5..0f52aa2 100644 (file)
@@ -76,8 +76,12 @@ const ClassInfo RegExpConstructor::s_info = { "Function", &InternalFunction::s_i
 @end
 */
 
+
+static EncodedJSValue JSC_HOST_CALL callRegExpConstructor(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructWithRegExpConstructor(ExecState*);
+
 RegExpConstructor::RegExpConstructor(VM& vm, Structure* structure, RegExpPrototype* regExpPrototype)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, callRegExpConstructor, constructWithRegExpConstructor)
     , m_cachedResult(vm, this, regExpPrototype->emptyRegExp())
     , m_multiline(false)
 {
@@ -310,22 +314,10 @@ static EncodedJSValue JSC_HOST_CALL constructWithRegExpConstructor(ExecState* ex
     return JSValue::encode(constructRegExp(exec, asInternalFunction(exec->jsCallee())->globalObject(), args, exec->jsCallee(), exec->newTarget()));
 }
 
-ConstructType RegExpConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructWithRegExpConstructor;
-    return ConstructType::Host;
-}
-
 static EncodedJSValue JSC_HOST_CALL callRegExpConstructor(ExecState* exec)
 {
     ArgList args(exec);
     return JSValue::encode(constructRegExp(exec, asInternalFunction(exec->jsCallee())->globalObject(), args, exec->jsCallee()));
 }
 
-CallType RegExpConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callRegExpConstructor;
-    return CallType::Host;
-}
-
 } // namespace JSC
index 6d74627..da760ec 100644 (file)
@@ -44,7 +44,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
     DECLARE_INFO;
@@ -74,8 +74,6 @@ protected:
 private:
     RegExpConstructor(VM&, Structure*, RegExpPrototype*);
     static void destroy(JSCell*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 
     RegExpCachedResult m_cachedResult;
     bool m_multiline;
index f189d2f..e7b3dc2 100644 (file)
@@ -47,6 +47,14 @@ void SetConstructor::finishCreation(VM& vm, SetPrototype* setPrototype, GetterSe
     putDirectNonIndexAccessor(vm, vm.propertyNames->speciesSymbol, speciesSymbol, PropertyAttribute::Accessor | PropertyAttribute::ReadOnly | PropertyAttribute::DontEnum);
 }
 
+static EncodedJSValue JSC_HOST_CALL callSet(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructSet(ExecState*);
+
+SetConstructor::SetConstructor(VM& vm, Structure* structure)
+    : Base(vm, structure, callSet, constructSet)
+{
+}
+
 static EncodedJSValue JSC_HOST_CALL callSet(ExecState* exec)
 {
     VM& vm = exec->vm();
@@ -99,18 +107,6 @@ static EncodedJSValue JSC_HOST_CALL constructSet(ExecState* exec)
     return JSValue::encode(set);
 }
 
-ConstructType SetConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructSet;
-    return ConstructType::Host;
-}
-
-CallType SetConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callSet;
-    return CallType::Host;
-}
-
 EncodedJSValue JSC_HOST_CALL setPrivateFuncSetBucketHead(ExecState* exec)
 {
     ASSERT(isJSSet(exec->argument(0)));
index 45f0130..dd4a4d1 100644 (file)
@@ -47,17 +47,12 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 private:
-    SetConstructor(VM& vm, Structure* structure)
-        : Base(vm, structure)
-    {
-    }
+    SetConstructor(VM&, Structure*);
     void finishCreation(VM&, SetPrototype*, GetterSetter* speciesSymbol);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 EncodedJSValue JSC_HOST_CALL setPrivateFuncSetBucketHead(ExecState*);
index 37996a8..1069efe 100644 (file)
@@ -52,8 +52,12 @@ const ClassInfo StringConstructor::s_info = { "Function", &InternalFunction::s_i
 
 STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(StringConstructor);
 
+
+static EncodedJSValue JSC_HOST_CALL callStringConstructor(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructWithStringConstructor(ExecState*);
+
 StringConstructor::StringConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, callStringConstructor, constructWithStringConstructor)
 {
 }
 
@@ -134,12 +138,6 @@ static EncodedJSValue JSC_HOST_CALL constructWithStringConstructor(ExecState* ex
     return JSValue::encode(StringObject::create(vm, structure, str));
 }
 
-ConstructType StringConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructWithStringConstructor;
-    return ConstructType::Host;
-}
-
 JSCell* stringConstructor(ExecState* exec, JSValue argument)
 {
     if (argument.isSymbol())
@@ -154,10 +152,4 @@ static EncodedJSValue JSC_HOST_CALL callStringConstructor(ExecState* exec)
     return JSValue::encode(stringConstructor(exec, exec->uncheckedArgument(0)));
 }
 
-CallType StringConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callStringConstructor;
-    return CallType::Host;
-}
-
 } // namespace JSC
index 1bd1e21..99aafe8 100644 (file)
@@ -43,14 +43,12 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 private:
     StringConstructor(VM&, Structure*);
     void finishCreation(VM&, StringPrototype*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 JSCell* JSC_HOST_CALL stringFromCharCode(ExecState*, int32_t);
index a761f41..b515259 100644 (file)
@@ -56,8 +56,10 @@ const ClassInfo SymbolConstructor::s_info = { "Function", &Base::s_info, &symbol
 @end
 */
 
+static EncodedJSValue JSC_HOST_CALL callSymbol(ExecState*);
+
 SymbolConstructor::SymbolConstructor(VM& vm, Structure* structure)
-    : InternalFunction(vm, structure)
+    : InternalFunction(vm, structure, callSymbol, nullptr)
 {
 }
 
@@ -83,17 +85,6 @@ static EncodedJSValue JSC_HOST_CALL callSymbol(ExecState* exec)
     return JSValue::encode(Symbol::create(exec, description.toString(exec)));
 }
 
-ConstructType SymbolConstructor::getConstructData(JSCell*, ConstructData&)
-{
-    return ConstructType::None;
-}
-
-CallType SymbolConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callSymbol;
-    return CallType::Host;
-}
-
 EncodedJSValue JSC_HOST_CALL symbolConstructorFor(ExecState* exec)
 {
     VM& vm = exec->vm();
index 58c3518..5bd0594 100644 (file)
@@ -49,7 +49,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 protected:
@@ -57,8 +57,6 @@ protected:
 
 private:
     SymbolConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index bbbd708..b200857 100644 (file)
@@ -351,6 +351,10 @@ VM::VM(VMType vmType, HeapType heapType)
         watchdog.setTimeLimit(timeoutMillis);
     }
 
+    // Make sure that any stubs that the JIT is going to use are initialized in non-compilation threads.
+    getCTIInternalFunctionTrampolineFor(CodeForCall);
+    getCTIInternalFunctionTrampolineFor(CodeForConstruct);
+
     VMInspector::instance().add(this);
 }
 
@@ -578,6 +582,19 @@ NativeExecutable* VM::getHostFunction(NativeFunction function, Intrinsic intrins
         NoIntrinsic, signature, name);
 }
 
+MacroAssemblerCodePtr VM::getCTIInternalFunctionTrampolineFor(CodeSpecializationKind kind)
+{
+#if ENABLE(JIT)
+    if (kind == CodeForCall)
+        return jitStubs->ctiInternalFunctionCall(this);
+    return jitStubs->ctiInternalFunctionConstruct(this);
+#else
+    if (kind == CodeForCall)
+        return MacroAssemblerCodePtr::createLLIntCodePtr(llint_internal_function_call_trampoline);
+    return MacroAssemblerCodePtr::createLLIntCodePtr(llint_internal_function_construct_trampoline);
+#endif
+}
+
 VM::ClientData::~ClientData()
 {
 }
index 62202bc..b554b35 100644 (file)
@@ -29,6 +29,7 @@
 #pragma once
 
 #include "CallData.h"
+#include "CodeSpecializationKind.h"
 #include "ConcurrentJSLock.h"
 #include "ControlFlowProfiler.h"
 #include "DateInstanceCache.h"
@@ -483,6 +484,8 @@ public:
     NativeExecutable* getHostFunction(NativeFunction, NativeFunction constructor, const String& name);
     NativeExecutable* getHostFunction(NativeFunction, Intrinsic, NativeFunction constructor, const DOMJIT::Signature*, const String& name);
 
+    MacroAssemblerCodePtr getCTIInternalFunctionTrampolineFor(CodeSpecializationKind);
+
     static ptrdiff_t exceptionOffset()
     {
         return OBJECT_OFFSETOF(VM, m_exception);
index a51e844..c0d9ce1 100644 (file)
@@ -45,6 +45,14 @@ void WeakMapConstructor::finishCreation(VM& vm, WeakMapPrototype* prototype)
     putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(0), PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly);
 }
 
+static EncodedJSValue JSC_HOST_CALL callWeakMap(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructWeakMap(ExecState*);
+
+WeakMapConstructor::WeakMapConstructor(VM& vm, Structure* structure)
+    : Base(vm, structure, callWeakMap, constructWeakMap)
+{
+}
+
 static EncodedJSValue JSC_HOST_CALL callWeakMap(ExecState* exec)
 {
     VM& vm = exec->vm();
@@ -98,16 +106,4 @@ static EncodedJSValue JSC_HOST_CALL constructWeakMap(ExecState* exec)
     return JSValue::encode(weakMap);
 }
 
-ConstructType WeakMapConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructWeakMap;
-    return ConstructType::Host;
-}
-
-CallType WeakMapConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callWeakMap;
-    return CallType::Host;
-}
-
 }
index 59f2caa..c93e412 100644 (file)
@@ -47,17 +47,12 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 private:
-    WeakMapConstructor(VM& vm, Structure* structure)
-        : Base(vm, structure)
-    {
-    }
+    WeakMapConstructor(VM&, Structure*);
     void finishCreation(VM&, WeakMapPrototype*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index 3b4efe6..40d9cc5 100644 (file)
@@ -45,6 +45,14 @@ void WeakSetConstructor::finishCreation(VM& vm, WeakSetPrototype* prototype)
     putDirectWithoutTransition(vm, vm.propertyNames->length, jsNumber(0), PropertyAttribute::DontEnum | PropertyAttribute::ReadOnly);
 }
 
+static EncodedJSValue JSC_HOST_CALL callWeakSet(ExecState*);
+static EncodedJSValue JSC_HOST_CALL constructWeakSet(ExecState*);
+
+WeakSetConstructor::WeakSetConstructor(VM& vm, Structure* structure)
+    : Base(vm, structure, callWeakSet, constructWeakSet)
+{
+}
+
 static EncodedJSValue JSC_HOST_CALL callWeakSet(ExecState* exec)
 {
     VM& vm = exec->vm();
@@ -84,16 +92,4 @@ static EncodedJSValue JSC_HOST_CALL constructWeakSet(ExecState* exec)
     return JSValue::encode(weakSet);
 }
 
-ConstructType WeakSetConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructWeakSet;
-    return ConstructType::Host;
-}
-
-CallType WeakSetConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callWeakSet;
-    return CallType::Host;
-}
-
 }
index 693c10b..5e6fb82 100644 (file)
@@ -47,17 +47,12 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 private:
-    WeakSetConstructor(VM& vm, Structure* structure)
-        : Base(vm, structure)
-    {
-    }
+    WeakSetConstructor(VM&, Structure*);
     void finishCreation(VM&, WeakSetPrototype*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index 982df7f..ac4d8fc 100644 (file)
@@ -70,7 +70,7 @@ WebAssemblyCompileErrorConstructor* WebAssemblyCompileErrorConstructor::create(V
 
 Structure* WebAssemblyCompileErrorConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 void WebAssemblyCompileErrorConstructor::finishCreation(VM& vm, WebAssemblyCompileErrorPrototype* prototype)
@@ -81,22 +81,10 @@ void WebAssemblyCompileErrorConstructor::finishCreation(VM& vm, WebAssemblyCompi
 }
 
 WebAssemblyCompileErrorConstructor::WebAssemblyCompileErrorConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, callJSWebAssemblyCompileError, constructJSWebAssemblyCompileError)
 {
 }
 
-ConstructType WebAssemblyCompileErrorConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructJSWebAssemblyCompileError;
-    return ConstructType::Host;
-}
-
-CallType WebAssemblyCompileErrorConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callJSWebAssemblyCompileError;
-    return CallType::Host;
-}
-
 } // namespace JSC
 
 #endif // ENABLE(WEBASSEMBLY)
index 34a0e78..5b75bc8 100644 (file)
@@ -49,8 +49,6 @@ protected:
 
 private:
     WebAssemblyCompileErrorConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index 5de4d92..59124b9 100644 (file)
@@ -101,7 +101,7 @@ WebAssemblyInstanceConstructor* WebAssemblyInstanceConstructor::create(VM& vm, S
 
 Structure* WebAssemblyInstanceConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 void WebAssemblyInstanceConstructor::finishCreation(VM& vm, WebAssemblyInstancePrototype* prototype)
@@ -112,22 +112,10 @@ void WebAssemblyInstanceConstructor::finishCreation(VM& vm, WebAssemblyInstanceP
 }
 
 WebAssemblyInstanceConstructor::WebAssemblyInstanceConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, callJSWebAssemblyInstance, constructJSWebAssemblyInstance)
 {
 }
 
-ConstructType WebAssemblyInstanceConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructJSWebAssemblyInstance;
-    return ConstructType::Host;
-}
-
-CallType WebAssemblyInstanceConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callJSWebAssemblyInstance;
-    return CallType::Host;
-}
-
 } // namespace JSC
 
 #endif // ENABLE(WEBASSEMBLY)
index 6d9ed3c..a21d91a 100644 (file)
@@ -53,8 +53,6 @@ protected:
 
 private:
     WebAssemblyInstanceConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index b17d58a..af0917a 100644 (file)
@@ -70,7 +70,7 @@ WebAssemblyLinkErrorConstructor* WebAssemblyLinkErrorConstructor::create(VM& vm,
 
 Structure* WebAssemblyLinkErrorConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 void WebAssemblyLinkErrorConstructor::finishCreation(VM& vm, WebAssemblyLinkErrorPrototype* prototype)
@@ -81,22 +81,10 @@ void WebAssemblyLinkErrorConstructor::finishCreation(VM& vm, WebAssemblyLinkErro
 }
 
 WebAssemblyLinkErrorConstructor::WebAssemblyLinkErrorConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, callJSWebAssemblyLinkError, constructJSWebAssemblyLinkError)
 {
 }
 
-ConstructType WebAssemblyLinkErrorConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructJSWebAssemblyLinkError;
-    return ConstructType::Host;
-}
-
-CallType WebAssemblyLinkErrorConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callJSWebAssemblyLinkError;
-    return CallType::Host;
-}
-
 } // namespace JSC
 
 #endif // ENABLE(WEBASSEMBLY)
index c700c63..e291297 100644 (file)
@@ -49,8 +49,6 @@ protected:
 
 private:
     WebAssemblyLinkErrorConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index d0435af..c55698c 100644 (file)
@@ -127,7 +127,7 @@ WebAssemblyMemoryConstructor* WebAssemblyMemoryConstructor::create(VM& vm, Struc
 
 Structure* WebAssemblyMemoryConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 void WebAssemblyMemoryConstructor::finishCreation(VM& vm, WebAssemblyMemoryPrototype* prototype)
@@ -138,22 +138,10 @@ void WebAssemblyMemoryConstructor::finishCreation(VM& vm, WebAssemblyMemoryProto
 }
 
 WebAssemblyMemoryConstructor::WebAssemblyMemoryConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, callJSWebAssemblyMemory, constructJSWebAssemblyMemory)
 {
 }
 
-ConstructType WebAssemblyMemoryConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructJSWebAssemblyMemory;
-    return ConstructType::Host;
-}
-
-CallType WebAssemblyMemoryConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callJSWebAssemblyMemory;
-    return CallType::Host;
-}
-
 } // namespace JSC
 
 #endif // ENABLE(WEBASSEMBLY)
index 2061e24..ea6460b 100644 (file)
@@ -49,8 +49,6 @@ protected:
 
 private:
     WebAssemblyMemoryConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index 75b5b62..fa31c59 100644 (file)
@@ -198,7 +198,7 @@ WebAssemblyModuleConstructor* WebAssemblyModuleConstructor::create(VM& vm, Struc
 
 Structure* WebAssemblyModuleConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 void WebAssemblyModuleConstructor::finishCreation(VM& vm, WebAssemblyModulePrototype* prototype)
@@ -209,22 +209,10 @@ void WebAssemblyModuleConstructor::finishCreation(VM& vm, WebAssemblyModuleProto
 }
 
 WebAssemblyModuleConstructor::WebAssemblyModuleConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, callJSWebAssemblyModule, constructJSWebAssemblyModule)
 {
 }
 
-ConstructType WebAssemblyModuleConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructJSWebAssemblyModule;
-    return ConstructType::Host;
-}
-
-CallType WebAssemblyModuleConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callJSWebAssemblyModule;
-    return CallType::Host;
-}
-
 } // namespace JSC
 
 #endif // ENABLE(WEBASSEMBLY)
index 13aca3f..f74b666 100644 (file)
@@ -54,8 +54,6 @@ protected:
 
 private:
     WebAssemblyModuleConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index 645f967..155315f 100644 (file)
@@ -70,7 +70,7 @@ WebAssemblyRuntimeErrorConstructor* WebAssemblyRuntimeErrorConstructor::create(V
 
 Structure* WebAssemblyRuntimeErrorConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 void WebAssemblyRuntimeErrorConstructor::finishCreation(VM& vm, WebAssemblyRuntimeErrorPrototype* prototype)
@@ -81,22 +81,10 @@ void WebAssemblyRuntimeErrorConstructor::finishCreation(VM& vm, WebAssemblyRunti
 }
 
 WebAssemblyRuntimeErrorConstructor::WebAssemblyRuntimeErrorConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, callJSWebAssemblyRuntimeError, constructJSWebAssemblyRuntimeError)
 {
 }
 
-ConstructType WebAssemblyRuntimeErrorConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructJSWebAssemblyRuntimeError;
-    return ConstructType::Host;
-}
-
-CallType WebAssemblyRuntimeErrorConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callJSWebAssemblyRuntimeError;
-    return CallType::Host;
-}
-
 } // namespace JSC
 
 #endif // ENABLE(WEBASSEMBLY)
index 77fb6e4..94ae6b9 100644 (file)
@@ -49,8 +49,6 @@ protected:
 
 private:
     WebAssemblyRuntimeErrorConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index 2c5bc70..5844c9e 100644 (file)
@@ -117,7 +117,7 @@ WebAssemblyTableConstructor* WebAssemblyTableConstructor::create(VM& vm, Structu
 
 Structure* WebAssemblyTableConstructor::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
 }
 
 void WebAssemblyTableConstructor::finishCreation(VM& vm, WebAssemblyTablePrototype* prototype)
@@ -128,22 +128,10 @@ void WebAssemblyTableConstructor::finishCreation(VM& vm, WebAssemblyTablePrototy
 }
 
 WebAssemblyTableConstructor::WebAssemblyTableConstructor(VM& vm, Structure* structure)
-    : Base(vm, structure)
+    : Base(vm, structure, callJSWebAssemblyTable, constructJSWebAssemblyTable)
 {
 }
 
-ConstructType WebAssemblyTableConstructor::getConstructData(JSCell*, ConstructData& constructData)
-{
-    constructData.native.function = constructJSWebAssemblyTable;
-    return ConstructType::Host;
-}
-
-CallType WebAssemblyTableConstructor::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callJSWebAssemblyTable;
-    return CallType::Host;
-}
-
 } // namespace JSC
 
 #endif // ENABLE(WEBASSEMBLY)
index 5adebb3..36468d0 100644 (file)
@@ -49,8 +49,6 @@ protected:
 
 private:
     WebAssemblyTableConstructor(VM&, Structure*);
-    static ConstructType getConstructData(JSCell*, ConstructData&);
-    static CallType getCallData(JSCell*, CallData&);
 };
 
 } // namespace JSC
index 209938b..b87fd55 100644 (file)
@@ -1,3 +1,15 @@
+2017-11-05  Yusuke Suzuki  <utatane.tea@gmail.com>
+
+        JIT call inline caches should cache calls to objects with getCallData/getConstructData traps
+        https://bugs.webkit.org/show_bug.cgi?id=144458
+
+        Reviewed by Saam Barati.
+
+        * bridge/runtime_method.cpp:
+        (JSC::RuntimeMethod::RuntimeMethod):
+        (JSC::RuntimeMethod::getCallData): Deleted.
+        * bridge/runtime_method.h:
+
 2017-11-06  Maciej Stachowiak  <mjs@apple.com>
 
         Canonical name of EUC-KR encoding should be EUC-KR, not windows-949
index 8407dd9..9692e5b 100644 (file)
@@ -128,7 +128,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
     DECLARE_INFO;
index fb92dcf..ead7f22 100644 (file)
@@ -179,7 +179,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSC::JSGlobalObject* globalObject, JSC::JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), &s_info);
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), &s_info);
     }
 
     DECLARE_INFO;
index 910a702..255d841 100644 (file)
@@ -41,9 +41,11 @@ using namespace Bindings;
 
 WEBCORE_EXPORT const ClassInfo RuntimeMethod::s_info = { "RuntimeMethod", &InternalFunction::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(RuntimeMethod) };
 
+static EncodedJSValue JSC_HOST_CALL callRuntimeMethod(ExecState*);
+
 RuntimeMethod::RuntimeMethod(JSGlobalObject* globalObject, Structure* structure, Method* method)
     // Callers will need to pass in the right global object corresponding to this native object "method".
-    : InternalFunction(globalObject->vm(), structure)
+    : InternalFunction(globalObject->vm(), structure, callRuntimeMethod, nullptr)
     , m_method(method)
 {
 }
@@ -110,10 +112,4 @@ static EncodedJSValue JSC_HOST_CALL callRuntimeMethod(ExecState* exec)
     return JSValue::encode(result);
 }
 
-CallType RuntimeMethod::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callRuntimeMethod;
-    return CallType::Host;
-}
-
 }
index 7c275ac..4df4355 100644 (file)
@@ -56,13 +56,12 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), info());
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), info());
     }
 
 protected:
     RuntimeMethod(JSGlobalObject*, Structure*, Bindings::Method*);
     void finishCreation(VM&, const String&);
-    static CallType getCallData(JSCell*, CallData&);
 
     static bool getOwnPropertySlot(JSObject*, ExecState*, PropertyName, PropertySlot&);
 
index 3b6a00a..03a0bc3 100644 (file)
@@ -1,3 +1,16 @@
+2017-11-05  Yusuke Suzuki  <utatane.tea@gmail.com>
+
+        JIT call inline caches should cache calls to objects with getCallData/getConstructData traps
+        https://bugs.webkit.org/show_bug.cgi?id=144458
+
+        Reviewed by Saam Barati.
+
+        * WebProcess/Plugins/Netscape/JSNPMethod.cpp:
+        (WebKit::JSNPMethod::JSNPMethod):
+        (WebKit::JSNPMethod::getCallData): Deleted.
+        * WebProcess/Plugins/Netscape/JSNPMethod.h:
+        (WebKit::JSNPMethod::createStructure):
+
 2017-11-04  Chris Dumez  <cdumez@apple.com>
 
         REGRESSION(r223718): Leaking WebProcessPool after reconfiguration
index 66f50c3..e56088f 100644 (file)
@@ -45,8 +45,10 @@ STATIC_ASSERT_IS_TRIVIALLY_DESTRUCTIBLE(JSNPMethod);
 
 const ClassInfo JSNPMethod::s_info = { "NPMethod", &InternalFunction::s_info, nullptr, nullptr, CREATE_METHOD_TABLE(JSNPMethod) };
 
+static EncodedJSValue JSC_HOST_CALL callMethod(ExecState*);
+
 JSNPMethod::JSNPMethod(JSGlobalObject* globalObject, Structure* structure, NPIdentifier npIdentifier)
-    : InternalFunction(globalObject->vm(), structure)
+    : InternalFunction(globalObject->vm(), structure, callMethod, nullptr)
     , m_npIdentifier(npIdentifier)
 {
 }
@@ -84,12 +86,6 @@ static EncodedJSValue JSC_HOST_CALL callMethod(ExecState* exec)
     return throwVMTypeError(exec, scope);
 }
 
-CallType JSNPMethod::getCallData(JSCell*, CallData& callData)
-{
-    callData.native.function = callMethod;
-    return CallType::Host;
-}
-
 } // namespace WebKit
 
 #endif // ENABLE(NETSCAPE_PLUGIN_API)
index ace7f2d..5c284c9 100644 (file)
@@ -62,11 +62,9 @@ private:
 
     static JSC::Structure* createStructure(JSC::VM& vm, JSC::JSGlobalObject* globalObject, JSC::JSValue prototype)
     {
-        return JSC::Structure::create(vm, globalObject, prototype, JSC::TypeInfo(JSC::ObjectType, StructureFlags), info());
+        return JSC::Structure::create(vm, globalObject, prototype, JSC::TypeInfo(JSC::InternalFunctionType, StructureFlags), info());
     }
 
-    static JSC::CallType getCallData(JSC::JSCell*, JSC::CallData&);
-    
     NPIdentifier m_npIdentifier;
 };
 
index a26d844..ea8fcda 100644 (file)
@@ -193,7 +193,7 @@ public:
 
     static Structure* createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
     {
-        return Structure::create(vm, globalObject, prototype, TypeInfo(ObjectType, StructureFlags), &s_info);
+        return Structure::create(vm, globalObject, prototype, TypeInfo(InternalFunctionType, StructureFlags), &s_info);
     }
 
     DECLARE_INFO;