2009-01-14 Jeremy Moskovich <jeremy@chromium.org>
authoreric@webkit.org <eric@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Wed, 14 Jan 2009 22:22:29 +0000 (22:22 +0000)
committereric@webkit.org <eric@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Wed, 14 Jan 2009 22:22:29 +0000 (22:22 +0000)
        Reviewed by Eric Seidel.

        <https://bugs.webkit.org/show_bug.cgi?id=16829>
        Implement NPN_SetException()

        This mirrors the implementation in the obj-c bindings.

        Test: plugins/netscape-throw-exception.html

        * bridge/NP_jsobject.cpp:
        (_NPN_SetException):
        * bridge/c/c_instance.cpp:
        (JSC::Bindings::getExceptionString):
        (JSC::Bindings::CInstance::setGlobalException):
        (JSC::Bindings::CInstance::moveGlobalExceptionToExecState):
        (JSC::Bindings::CInstance::invokeMethod):
        (JSC::Bindings::CInstance::invokeDefaultMethod):
        (JSC::Bindings::CInstance::invokeConstruct):
        (JSC::Bindings::CInstance::getPropertyNames):
        * bridge/c/c_instance.h:

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

LayoutTests/ChangeLog
LayoutTests/plugins/netscape-throw-exception-expected.txt [new file with mode: 0644]
LayoutTests/plugins/netscape-throw-exception.html [new file with mode: 0644]
WebCore/ChangeLog
WebCore/bridge/NP_jsobject.cpp
WebCore/bridge/c/c_instance.cpp
WebCore/bridge/c/c_instance.h
WebKitTools/ChangeLog
WebKitTools/DumpRenderTree/TestNetscapePlugIn.subproj/PluginObject.cpp
WebKitTools/DumpRenderTree/TestNetscapePlugIn.subproj/TestObject.cpp

index 3db36c6..11a0284 100644 (file)
@@ -1,3 +1,13 @@
+2009-01-14  Jeremy Moskovich  <jeremy@chromium.org>
+
+        Reviewed by Eric Seidel.
+
+        <https://bugs.webkit.org/show_bug.cgi?id=16829>
+        Implement NPN_SetException()
+
+        * plugins/netscape-throw-exception-expected.txt: Added.
+        * plugins/netscape-throw-exception.html: Added.
+
 2009-01-14  David Kilzer  <ddkilzer@apple.com>
 
         Disabling webarchive/test-link-rel-icon.html due to various buildbot failures
diff --git a/LayoutTests/plugins/netscape-throw-exception-expected.txt b/LayoutTests/plugins/netscape-throw-exception-expected.txt
new file mode 100644 (file)
index 0000000..feb761d
--- /dev/null
@@ -0,0 +1,3 @@
+ This tests that a plugin can throw exceptions. If this test is successful the text "SUCCESS" twice below.
+plugin object testThrowException SUCCESS
+test object throwException SUCCESS
diff --git a/LayoutTests/plugins/netscape-throw-exception.html b/LayoutTests/plugins/netscape-throw-exception.html
new file mode 100644 (file)
index 0000000..1175de4
--- /dev/null
@@ -0,0 +1,30 @@
+<html>
+<script>
+function runTest()
+{
+    if (window.layoutTestController)
+        layoutTestController.dumpAsText();
+
+    var plugin = document.getElementById("testPlugin");
+    var result1 = document.getElementById('result1');
+    try {
+        plugin.testThrowException();
+    } catch (e) {
+        result1.innerHTML = e.message;
+    }
+    var result2 = document.getElementById('result2');
+    try {
+        plugin.testObject.throwException();
+    } catch (e) {
+        result2.innerHTML = e.message;
+    }
+}
+</script>
+
+<body onload="runTest();">
+<embed id="testPlugin" type="application/x-webkit-test-netscape" width="200" height="200"></embed>
+This tests that a plugin can throw exceptions. If this test is successful the text "SUCCESS" twice below.
+<div id="result1">FAILURE</div>
+<div id="result2">FAILURE</div>
+</body>
+</html>
index c3d7b35..d5df7de 100644 (file)
@@ -1,3 +1,26 @@
+2009-01-14  Jeremy Moskovich  <jeremy@chromium.org>
+
+        Reviewed by Eric Seidel.
+
+        <https://bugs.webkit.org/show_bug.cgi?id=16829>
+        Implement NPN_SetException()
+
+        This mirrors the implementation in the obj-c bindings.
+
+        Test: plugins/netscape-throw-exception.html
+
+        * bridge/NP_jsobject.cpp:
+        (_NPN_SetException):
+        * bridge/c/c_instance.cpp:
+        (JSC::Bindings::getExceptionString):
+        (JSC::Bindings::CInstance::setGlobalException):
+        (JSC::Bindings::CInstance::moveGlobalExceptionToExecState):
+        (JSC::Bindings::CInstance::invokeMethod):
+        (JSC::Bindings::CInstance::invokeDefaultMethod):
+        (JSC::Bindings::CInstance::invokeConstruct):
+        (JSC::Bindings::CInstance::getPropertyNames):
+        * bridge/c/c_instance.h:
+
 2009-01-14  Pierre-Olivier Latour  <pol@apple.com>
 
         Fixed build warning when LIBXML_VERSION >= 20627.
index 743414a..c72208e 100644 (file)
@@ -32,6 +32,7 @@
 #include "PlatformString.h"
 #include "StringSourceProvider.h"
 #include "c_utility.h"
+#include "c_instance.h"
 #include "npruntime_impl.h"
 #include "npruntime_priv.h"
 #include "runtime_root.h"
@@ -375,11 +376,11 @@ bool _NPN_HasMethod(NPP, NPObject* o, NPIdentifier methodName)
     return false;
 }
 
-void _NPN_SetException(NPObject*, const NPUTF8*)
+void _NPN_SetException(NPObject*, const NPUTF8* message)
 {
-    // FIXME:
-    // Bug 19888: Implement _NPN_SetException() correctly
-    // <https://bugs.webkit.org/show_bug.cgi?id=19888>
+    // Ignorning the NPObject param is consistent with the Mozilla implementation.
+    UString exception(message);
+    CInstance::setGlobalException(exception);
 }
 
 bool _NPN_Enumerate(NPP, NPObject* o, NPIdentifier** identifier, uint32_t* count)
index 37c3dd8..d229c76 100644 (file)
 #include "npruntime_impl.h"
 #include "runtime_root.h"
 #include <runtime/ArgList.h>
+#include <runtime/Error.h>
 #include <interpreter/CallFrame.h>
 #include <runtime/JSLock.h>
 #include <runtime/JSNumberCell.h>
 #include <runtime/PropertyNameArray.h>
 #include <wtf/Assertions.h>
+#include <wtf/StdLibExtras.h>
 #include <wtf/StringExtras.h>
 #include <wtf/Vector.h>
 
 namespace JSC {
 namespace Bindings {
 
+using JSC::UString;
+
+JSC::UString& globalExceptionString()
+{
+    DEFINE_STATIC_LOCAL(JSC::UString, exceptionStr, ());
+    return exceptionStr;
+}
+
+void CInstance::setGlobalException(UString exception)
+{
+    globalExceptionString() = exception;
+}
+
+void CInstance::moveGlobalExceptionToExecState(ExecState* exec)
+{
+    if (globalExceptionString().isNull())
+        return;
+
+    {
+        JSLock lock(false);
+        throwError(exec, GeneralError, globalExceptionString());
+    }
+
+    globalExceptionString() = UString();
+}
+
 CInstance::CInstance(NPObject* o, PassRefPtr<RootObject> rootObject)
     : Instance(rootObject)
 {
@@ -95,7 +123,9 @@ JSValuePtr CInstance::invokeMethod(ExecState* exec, const MethodList& methodList
 
     {
         JSLock::DropAllLocks dropAllLocks(false);
+        ASSERT(globalExceptionString().isNull());
         _object->_class->invoke(_object, ident, cArgs.data(), count, &resultVariant);
+        moveGlobalExceptionToExecState(exec);
     }
 
     for (i = 0; i < count; i++)
@@ -124,9 +154,11 @@ JSValuePtr CInstance::invokeDefaultMethod(ExecState* exec, const ArgList& args)
     VOID_TO_NPVARIANT(resultVariant);
     {
         JSLock::DropAllLocks dropAllLocks(false);
+        ASSERT(globalExceptionString().isNull());
         _object->_class->invokeDefault(_object, cArgs.data(), count, &resultVariant);
+        moveGlobalExceptionToExecState(exec);
     }
-    
+
     for (i = 0; i < count; i++)
         _NPN_ReleaseVariantValue(&cArgs[i]);
 
@@ -157,9 +189,11 @@ JSValuePtr CInstance::invokeConstruct(ExecState* exec, const ArgList& args)
     VOID_TO_NPVARIANT(resultVariant);
     {
         JSLock::DropAllLocks dropAllLocks(false);
+        ASSERT(globalExceptionString().isNull());
         _object->_class->construct(_object, cArgs.data(), count, &resultVariant);
+        moveGlobalExceptionToExecState(exec);
     }
-    
+
     for (i = 0; i < count; i++)
         _NPN_ReleaseVariantValue(&cArgs[i]);
 
@@ -211,7 +245,10 @@ void CInstance::getPropertyNames(ExecState* exec, PropertyNameArray& nameArray)
 
     {
         JSLock::DropAllLocks dropAllLocks(false);
-        if (!_object->_class->enumerate(_object, &identifiers, &count))
+        ASSERT(globalExceptionString().isNull());
+        bool ok = _object->_class->enumerate(_object, &identifiers, &count);
+        moveGlobalExceptionToExecState(exec);
+        if (!ok)
             return;
     }
 
index b16943a..e4b92c7 100644 (file)
@@ -36,6 +36,8 @@ typedef struct NPObject NPObject;
 
 namespace JSC {
 
+class UString;
+
 namespace Bindings {
 
 class CClass;
@@ -46,17 +48,20 @@ public:
     {
         return adoptRef(new CInstance(object, rootObject));
     }
+
+    static void setGlobalException(JSC::UString exception);
+
     ~CInstance ();
-    
+
     virtual Class *getClass() const;
 
     virtual JSValuePtr valueOf(ExecState*) const;
     virtual JSValuePtr defaultValue(ExecState*, PreferredPrimitiveType) const;
-    
+
     virtual JSValuePtr invokeMethod(ExecState*, const MethodList&, const ArgList&);
     virtual bool supportsInvokeDefaultMethod() const;
     virtual JSValuePtr invokeDefaultMethod(ExecState*, const ArgList&);
-    
+
     virtual bool supportsConstruct() const;
     virtual JSValuePtr invokeConstruct(ExecState*, const ArgList&);
 
@@ -65,14 +70,15 @@ public:
     JSValuePtr stringValue(ExecState*) const;
     JSValuePtr numberValue(ExecState*) const;
     JSValuePtr booleanValue() const;
-    
+
     NPObject *getObject() const { return _object; }
 
     virtual BindingLanguage getBindingLanguage() const { return CLanguage; }
 
 private:
+    static void moveGlobalExceptionToExecState(ExecState* exec);
     CInstance(NPObject*, PassRefPtr<RootObject>);
-    
+
     mutable CClass *_class;
     NPObject *_object;
 };
index 48258d7..e781046 100644 (file)
@@ -1,3 +1,17 @@
+2009-01-14  Jeremy Moskovich  <jeremy@chromium.org>
+
+        Reviewed by Eric Seidel.
+
+        <https://bugs.webkit.org/show_bug.cgi?id=16829>
+        Implement NPN_SetException()
+
+        * DumpRenderTree/TestNetscapePlugIn.subproj/PluginObject.cpp:
+        (pluginInvoke):
+        * DumpRenderTree/TestNetscapePlugIn.subproj/TestObject.cpp:
+        (initializeIdentifiers):
+        (testHasMethod):
+        (testInvoke):
+
 2009-01-13  Dmitry Titov  <dimich@chromium.org>
 
         Reviewed by David Kilzer.
index 881824a..9180983 100644 (file)
@@ -98,7 +98,8 @@ static const NPUTF8 *pluginPropertyIdentifierNames[NUM_PROPERTY_IDENTIFIERS] = {
 #define ID_TEST_IDENTIFIER_TO_INT   13
 #define ID_TEST_POSTURL_FILE        14
 #define ID_TEST_CONSTRUCT           15
-#define NUM_METHOD_IDENTIFIERS      16
+#define ID_TEST_THROW_EXCEPTION_METHOD 16
+#define NUM_METHOD_IDENTIFIERS      17
 
 static NPIdentifier pluginMethodIdentifiers[NUM_METHOD_IDENTIFIERS];
 static const NPUTF8 *pluginMethodIdentifierNames[NUM_METHOD_IDENTIFIERS] = {
@@ -118,6 +119,7 @@ static const NPUTF8 *pluginMethodIdentifierNames[NUM_METHOD_IDENTIFIERS] = {
     "testIdentifierToInt",
     "testPostURLFile",
     "testConstruct",
+    "testThrowException",
 };
 
 static NPUTF8* createCStringFromNPVariant(const NPVariant* variant)
@@ -573,6 +575,10 @@ static bool pluginInvoke(NPObject* header, NPIdentifier name, const NPVariant* a
         return testPostURLFile(plugin, args, argCount, result);
     else if (name == pluginMethodIdentifiers[ID_TEST_CONSTRUCT])
         return testConstruct(plugin, args, argCount, result);
+    else if (name == pluginMethodIdentifiers[ID_TEST_THROW_EXCEPTION_METHOD]) {
+        browser->setexception(header, "plugin object testThrowException SUCCESS");
+        return true;
+    }
     
     return false;
 }
index 4cd9402..1e51ece 100644 (file)
@@ -30,7 +30,9 @@
 #include <stdlib.h>
 
 static bool testEnumerate(NPObject *npobj, NPIdentifier **value, uint32_t *count);
-static bool testHasProperty(NPObject *obj, NPIdentifier name);
+static bool testHasMethod(NPObject*, NPIdentifier name);
+static bool testInvoke(NPObject*, NPIdentifier name, const NPVariant* args, uint32_t argCount, NPVariant* result);
+static bool testHasProperty(NPObject*, NPIdentifier name);
 static bool testGetProperty(NPObject*, NPIdentifier name, NPVariant*);
 static NPObject *testAllocate(NPP npp, NPClass *theClass);
 static void testDeallocate(NPObject *obj);
@@ -41,8 +43,8 @@ static NPClass testClass = {
     testAllocate, 
     testDeallocate, 
     0,
-    0,
-    0,
+    testHasMethod,
+    testInvoke,
     0,
     testHasProperty,
     testGetProperty,
@@ -71,9 +73,18 @@ static const NPUTF8 *testIdentifierNames[NUM_TEST_IDENTIFIERS] = {
     "objectPointer",
 };
 
+#define ID_THROW_EXCEPTION_METHOD   0
+#define NUM_METHOD_IDENTIFIERS      1
+
+static NPIdentifier testMethodIdentifiers[NUM_METHOD_IDENTIFIERS];
+static const NPUTF8 *testMethodIdentifierNames[NUM_METHOD_IDENTIFIERS] = {
+    "throwException",
+};
+
 static void initializeIdentifiers(void)
 {
     browser->getstringidentifiers(testIdentifierNames, NUM_TEST_IDENTIFIERS, testIdentifiers);
+    browser->getstringidentifiers(testMethodIdentifierNames, NUM_METHOD_IDENTIFIERS, testMethodIdentifiers);
 }
 
 static NPObject *testAllocate(NPP npp, NPClass *theClass)
@@ -93,7 +104,25 @@ static void testDeallocate(NPObject *obj)
     free(obj);
 }
 
-static bool testHasProperty(NPObject *obj, NPIdentifier name)
+static bool testHasMethod(NPObject*, NPIdentifier name)
+{
+    for (unsigned i = 0; i < NUM_METHOD_IDENTIFIERS; i++) {
+        if (testMethodIdentifiers[i] == name)
+            return true;
+    }
+    return false;
+}
+
+static bool testInvoke(NPObject* header, NPIdentifier name, const NPVariant* args, uint32_t argCount, NPVariant* result)
+{
+    if (name == testMethodIdentifiers[ID_THROW_EXCEPTION_METHOD]) {
+        browser->setexception(header, "test object throwException SUCCESS");
+        return true;
+     }
+     return false;
+}
+
+static bool testHasProperty(NPObject*, NPIdentifier name)
 {
     for (unsigned i = 0; i < NUM_TEST_IDENTIFIERS; i++) {
         if (testIdentifiers[i] == name)