diff options
author | sgjesse@chromium.org <sgjesse@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2009-05-27 09:26:58 +0000 |
---|---|---|
committer | sgjesse@chromium.org <sgjesse@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2009-05-27 09:26:58 +0000 |
commit | bc296f37929b762850ce2c3b317f8542bdace2a1 (patch) | |
tree | 7ae61fc12388c1c2cc8ae20974d1e78ecb94b45f /webkit | |
parent | 9c5e417def0fef57d5dc79b0348dab9b0d354d42 (diff) | |
download | chromium_src-bc296f37929b762850ce2c3b317f8542bdace2a1.zip chromium_src-bc296f37929b762850ce2c3b317f8542bdace2a1.tar.gz chromium_src-bc296f37929b762850ce2c3b317f8542bdace2a1.tar.bz2 |
Added support for constructor calls in the NPAPI.
The LiveConnect test cases at http://java.sun.com/javase/6/webnotes/6u10/plugin2/liveconnect/LiveConnectTests/ now pass for Chromium.
Parts of this change is rather mechanical, and leaves room for some refactoring afterwards.
Merged the implementation of testConstruct and the "objectPointer" property from WebKit\WebKitTools\DumpRenderTree\TestNetscapePlugIn.subproj\TestObject.cpp to the Chromium TestObject.cpp for the layout test LayoutTests\plugins\netscape-construct.html pass.
BUG=http://crbug.com/3285
BUG=http://crbug.com/10354
TEST=http://java.sun.com/javase/6/webnotes/6u10/plugin2/liveconnect/LiveConnectTests/
TEST=LayoutTests\plugins\netscape-construct.html
Review URL: http://codereview.chromium.org/113823
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@16979 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'webkit')
-rw-r--r-- | webkit/port/bindings/v8/NPV8Object.cpp | 36 | ||||
-rw-r--r-- | webkit/port/bindings/v8/V8NPObject.cpp | 19 | ||||
-rw-r--r-- | webkit/port/bindings/v8/v8_proxy.cpp | 23 | ||||
-rw-r--r-- | webkit/port/bindings/v8/v8_proxy.h | 5 | ||||
-rw-r--r-- | webkit/tools/layout_tests/test_expectations.txt | 2 | ||||
-rw-r--r-- | webkit/tools/npapi_layout_test_plugin/TestObject.cpp | 38 |
6 files changed, 101 insertions, 22 deletions
diff --git a/webkit/port/bindings/v8/NPV8Object.cpp b/webkit/port/bindings/v8/NPV8Object.cpp index 411439f..4eb6f45 100644 --- a/webkit/port/bindings/v8/NPV8Object.cpp +++ b/webkit/port/bindings/v8/NPV8Object.cpp @@ -482,10 +482,40 @@ bool NPN_Construct(NPP npp, NPObject* npobj, const NPVariant* args, uint32_t arg if (!npobj) return false; - // FIXME(estade): implement this case. if (npobj->_class == npScriptObjectClass) { - VOID_TO_NPVARIANT(*result); - return false; + V8NPObject *object = reinterpret_cast<V8NPObject*>(npobj); + + v8::HandleScope handleScope; + v8::Handle<v8::Context> context = getV8Context(npp, npobj); + if (context.IsEmpty()) + return false; + v8::Context::Scope scope(context); + + // Lookup the constructor function. + v8::Handle<v8::Object> ctorObj(object->v8Object); + if (!ctorObj->IsFunction()) + return false; + + // Call the constructor. + v8::Local<v8::Value> resultObj; + v8::Handle<v8::Function> ctor(v8::Function::Cast(*ctorObj)); + if (!ctor->IsNull()) { + WebCore::V8Proxy* proxy = GetV8Proxy(npobj); + ASSERT(proxy); + + // Create list of args to pass to v8. + v8::Handle<v8::Value>* argv = listFromVariantArgs(args, argCount, npobj); + resultObj = proxy->NewInstance(ctor, argCount, argv); + delete[] argv; + } + + // If we had an error return false. + if (resultObj.IsEmpty()) + return false; + + // Convert the result back to an NPVariant. + convertV8ObjectToNPVariant(resultObj, npobj, result); + return true; } if (NP_CLASS_STRUCT_VERSION_HAS_CTOR(npobj->_class) && npobj->_class->construct) diff --git a/webkit/port/bindings/v8/V8NPObject.cpp b/webkit/port/bindings/v8/V8NPObject.cpp index a902ab7..508502b 100644 --- a/webkit/port/bindings/v8/V8NPObject.cpp +++ b/webkit/port/bindings/v8/V8NPObject.cpp @@ -46,7 +46,8 @@ using namespace WebCore; enum InvokeFunctionType { INVOKE_METHOD = 1, - INVOKE_DEFAULT = 2 + INVOKE_CONSTRUCT = 2, + INVOKE_DEFAULT = 3 }; // TODO(mbelshe): need comments. @@ -101,16 +102,13 @@ static v8::Handle<v8::Value> NPObjectInvokeImpl(const v8::Arguments& args, Invok npobject->_class->invoke(npobject, ident, npArgs, argc, &result); } break; + case INVOKE_CONSTRUCT: + if (npobject->_class->construct) + npobject->_class->construct(npobject, npArgs, argc, &result); + break; case INVOKE_DEFAULT: if (npobject->_class->invokeDefault) npobject->_class->invokeDefault(npobject, npArgs, argc, &result); - // The call might be a construct call on an NPObject. - // See http://code.google.com/p/chromium/issues/detail?id=3285 - // - // TODO: when V8 passes in the correct flag args.is_construct_call_, - // make a separate NPN_Construct case. - else if (npobject->_class->construct) - npobject->_class->construct(npobject, npArgs, argc, &result); break; default: break; @@ -136,7 +134,10 @@ v8::Handle<v8::Value> NPObjectMethodHandler(const v8::Arguments& args) v8::Handle<v8::Value> NPObjectInvokeDefaultHandler(const v8::Arguments& args) { - return NPObjectInvokeImpl(args, INVOKE_DEFAULT); + if (args.IsConstructCall()) + return NPObjectInvokeImpl(args, INVOKE_CONSTRUCT); + else + return NPObjectInvokeImpl(args, INVOKE_DEFAULT); } diff --git a/webkit/port/bindings/v8/v8_proxy.cpp b/webkit/port/bindings/v8/v8_proxy.cpp index 3f6aa21..30fcf09 100644 --- a/webkit/port/bindings/v8/v8_proxy.cpp +++ b/webkit/port/bindings/v8/v8_proxy.cpp @@ -1157,6 +1157,29 @@ v8::Local<v8::Value> V8Proxy::CallFunction(v8::Handle<v8::Function> function, } +v8::Local<v8::Value> V8Proxy::NewInstance(v8::Handle<v8::Function> constructor, + int argc, + v8::Handle<v8::Value> args[]) +{ + // No artificial limitations on the depth of recursion, see comment in + // V8Proxy::CallFunction. + v8::Local<v8::Value> result; + { + ConsoleMessageScope scope; + + // See comment in V8Proxy::CallFunction. + m_frame->keepAlive(); + + result = constructor->NewInstance(argc, args); + } + + if (v8::V8::IsDead()) + HandleFatalErrorInV8(); + + return result; +} + + v8::Local<v8::Function> V8Proxy::GetConstructor(V8ClassIndex::V8WrapperType t){ // A DOM constructor is a function instance created from a DOM constructor // template. There is one instance per context. A DOM constructor is diff --git a/webkit/port/bindings/v8/v8_proxy.h b/webkit/port/bindings/v8/v8_proxy.h index c2bb66f..a00c5f9 100644 --- a/webkit/port/bindings/v8/v8_proxy.h +++ b/webkit/port/bindings/v8/v8_proxy.h @@ -258,6 +258,11 @@ class V8Proxy { int argc, v8::Handle<v8::Value> argv[]); + // Call the function as constructor with the given arguments. + v8::Local<v8::Value> NewInstance(v8::Handle<v8::Function> constructor, + int argc, + v8::Handle<v8::Value> argv[]); + // Returns the dom constructor function for the given node type. v8::Local<v8::Function> GetConstructor(V8ClassIndex::V8WrapperType type); diff --git a/webkit/tools/layout_tests/test_expectations.txt b/webkit/tools/layout_tests/test_expectations.txt index b967928..5f5ef0d 100644 --- a/webkit/tools/layout_tests/test_expectations.txt +++ b/webkit/tools/layout_tests/test_expectations.txt @@ -1264,7 +1264,7 @@ BUG10353 DEBUG MAC : LayoutTests/http/tests/misc/dns-prefetch-control.html = TIM // New tests. We should fix these, but they doesn't need to block the current // release BUG10354 WIN LINUX : LayoutTests/fast/layers/opacity-transforms.html = FAIL -BUG10354 : LayoutTests/plugins/netscape-construct.html = FAIL +BUG10354 MAC LINUX : LayoutTests/plugins/netscape-construct.html = FAIL // MERGE 37604:38097 REGRESSIONS // New test. We should fix it, but it doesn't need to block the current release diff --git a/webkit/tools/npapi_layout_test_plugin/TestObject.cpp b/webkit/tools/npapi_layout_test_plugin/TestObject.cpp index 659da76..edf3a856 100644 --- a/webkit/tools/npapi_layout_test_plugin/TestObject.cpp +++ b/webkit/tools/npapi_layout_test_plugin/TestObject.cpp @@ -34,6 +34,8 @@ static bool testHasProperty(NPObject *obj, NPIdentifier name); static bool testGetProperty(NPObject *obj, NPIdentifier name, NPVariant *variant); static NPObject *testAllocate(NPP npp, NPClass *theClass); static void testDeallocate(NPObject *obj); +static bool testConstruct(NPObject* obj, const NPVariant* args, uint32_t argCount, NPVariant* result); + static NPClass testClass = { NP_CLASS_STRUCT_VERSION, @@ -47,7 +49,8 @@ static NPClass testClass = { testGetProperty, 0, 0, - testEnumerate + testEnumerate, + testConstruct }; NPClass *getTestClass(void) @@ -63,11 +66,14 @@ int getTestObjectCount(void) { static bool identifiersInitialized = false; -#define NUM_TEST_IDENTIFIERS 4 -#define ID_PROPERTY_FOO 0 -#define ID_PROPERTY_BAR 1 -#define ID_PROPERTY_TEST_OBJECT 2 -#define ID_PROPERTY_REF_COUNT 3 +#define NUM_ENUMERABLE_TEST_IDENTIFIERS 4 +#define NUM_TEST_IDENTIFIERS 5 + +#define ID_PROPERTY_FOO 0 +#define ID_PROPERTY_BAR 1 +#define ID_PROPERTY_TEST_OBJECT 2 +#define ID_PROPERTY_REF_COUNT 3 +#define ID_PROPERTY_OBJECT_POINTER 4 static NPIdentifier testIdentifiers[NUM_TEST_IDENTIFIERS]; static const NPUTF8 *testIdentifierNames[NUM_TEST_IDENTIFIERS] = { @@ -75,6 +81,7 @@ static const NPUTF8 *testIdentifierNames[NUM_TEST_IDENTIFIERS] = { "bar", "testObject", "refCount", + "objectPointer", }; static void initializeIdentifiers(void) @@ -144,17 +151,30 @@ static bool testGetProperty(NPObject *obj, NPIdentifier name, } else if (name == testIdentifiers[ID_PROPERTY_REF_COUNT]) { INT32_TO_NPVARIANT(obj->referenceCount, *variant); return true; + } else if (name == testIdentifiers[ID_PROPERTY_OBJECT_POINTER]) { + int32_t objectPointer = static_cast<int32_t>(reinterpret_cast<long long>(obj)); + INT32_TO_NPVARIANT(objectPointer, *variant); + return true; } return false; } static bool testEnumerate(NPObject *npobj, NPIdentifier **value, uint32_t *count) { - *count = NUM_TEST_IDENTIFIERS; + *count = NUM_ENUMERABLE_TEST_IDENTIFIERS; + + *value = (NPIdentifier*)browser->memalloc(NUM_ENUMERABLE_TEST_IDENTIFIERS * sizeof(NPIdentifier)); + memcpy(*value, testIdentifiers, sizeof(NPIdentifier) * NUM_ENUMERABLE_TEST_IDENTIFIERS); - *value = (NPIdentifier*)browser->memalloc(NUM_TEST_IDENTIFIERS * sizeof(NPIdentifier)); - memcpy(*value, testIdentifiers, sizeof(NPIdentifier) * NUM_TEST_IDENTIFIERS); + return true; +} + +static bool testConstruct(NPObject* npobj, const NPVariant* args, uint32_t argCount, NPVariant* result) +{ + browser->retainobject(npobj); + // Just return the same object. + OBJECT_TO_NPVARIANT(npobj, *result); return true; } |