aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAndrew Azores <[email protected]>2013-10-17 10:32:46 -0400
committerAndrew Azores <[email protected]>2013-10-17 10:32:46 -0400
commit72cc555dc703aa3f6a7338b5c3ade9fee7e799e3 (patch)
tree0466bae5ae3699db02603754f98926c1709c57bc
parent7ec1205e53b3516947f61cc19a0affcccf8c4898 (diff)
Back out changeset 420d72e5cee7
Back out changeset 420d72e5cee7 due to breaking LiveConnect feature. http://mail.openjdk.java.net/pipermail/distro-pkg-dev/2013-October/024919.html * plugin/icedteanp/IcedTeaNPPlugin.cc: undo 420d72e5cee7 * plugin/icedteanp/IcedTeaPluginUtils.cc: undo 420d72e5cee7 * plugin/icedteanp/IcedTeaPluginUtils.h: undo 420d72e5cee7 * plugin/icedteanp/IcedTeaScriptablePluginObject.cc: undo 420d72e5cee7 * plugin/icedteanp/IcedTeaScriptablePluginObject.h: undo 420d72e5cee7 * tests/cpp-unit-tests/IcedTeaScriptablePluginObjectTest.cc: undo 420d72e5cee7
-rw-r--r--ChangeLog11
-rw-r--r--plugin/icedteanp/IcedTeaNPPlugin.cc36
-rw-r--r--plugin/icedteanp/IcedTeaPluginUtils.cc134
-rw-r--r--plugin/icedteanp/IcedTeaPluginUtils.h67
-rw-r--r--plugin/icedteanp/IcedTeaScriptablePluginObject.cc208
-rw-r--r--plugin/icedteanp/IcedTeaScriptablePluginObject.h28
-rw-r--r--tests/cpp-unit-tests/IcedTeaScriptablePluginObjectTest.cc15
7 files changed, 164 insertions, 335 deletions
diff --git a/ChangeLog b/ChangeLog
index b2a20b8..7d069cb 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,14 @@
+2013-10-17 Andrew Azores <[email protected]>
+
+ Back out changeset 420d72e5cee7 due to breaking LiveConnect feature.
+ http://mail.openjdk.java.net/pipermail/distro-pkg-dev/2013-October/024919.html
+ * plugin/icedteanp/IcedTeaNPPlugin.cc: undo 420d72e5cee7
+ * plugin/icedteanp/IcedTeaPluginUtils.cc: undo 420d72e5cee7
+ * plugin/icedteanp/IcedTeaPluginUtils.h: undo 420d72e5cee7
+ * plugin/icedteanp/IcedTeaScriptablePluginObject.cc: undo 420d72e5cee7
+ * plugin/icedteanp/IcedTeaScriptablePluginObject.h: undo 420d72e5cee7
+ * tests/cpp-unit-tests/IcedTeaScriptablePluginObjectTest.cc: undo 420d72e5cee7
+
2013-10-16 Andrew Azores <[email protected]>
Resolve deadlock issue when multiple applets are loaded simultaneously
diff --git a/plugin/icedteanp/IcedTeaNPPlugin.cc b/plugin/icedteanp/IcedTeaNPPlugin.cc
index e806d29..bfce1ae 100644
--- a/plugin/icedteanp/IcedTeaNPPlugin.cc
+++ b/plugin/icedteanp/IcedTeaNPPlugin.cc
@@ -2101,6 +2101,14 @@ get_scriptable_object(NPP instance)
if (data->is_applet_instance) // dummy instance/package?
{
+ JavaRequestProcessor java_request = JavaRequestProcessor();
+ JavaResultData* java_result;
+ std::string instance_id = std::string();
+ std::string applet_class_id = std::string();
+
+ int id = get_id_from_instance(instance);
+ gchar* id_str = g_strdup_printf ("%d", id);
+
// Some browsers.. (e.g. chromium) don't call NPP_SetWindow
// for 0x0 plugins and therefore require initialization with
// a 0 handle
@@ -2109,10 +2117,30 @@ get_scriptable_object(NPP instance)
plugin_send_initialization_message(data->instance_id, 0, 0, 0, data->parameters_string);
}
- NPObjectRef applet_object = IcedTeaScriptableJavaObject::get_scriptable_applet_object(instance);
- /* Retain because we are returning an NPObject* */
- applet_object.raw_retain();
- obj = applet_object.get();
+ java_result = java_request.getAppletObjectInstance(id_str);
+
+ g_free(id_str);
+
+ if (java_result->error_occurred)
+ {
+ printf("Error: Unable to fetch applet instance id from Java side.\n");
+ return NULL;
+ }
+
+ instance_id.append(*(java_result->return_string));
+
+ java_result = java_request.getClassID(instance_id);
+
+ if (java_result->error_occurred)
+ {
+ printf("Error: Unable to fetch applet instance id from Java side.\n");
+ return NULL;
+ }
+
+ applet_class_id.append(*(java_result->return_string));
+
+ obj = IcedTeaScriptableJavaObject::get_scriptable_java_object(instance, applet_class_id, instance_id, false);
+
} else
{
obj = IcedTeaScriptableJavaPackageObject::get_scriptable_java_package_object(instance, "");
diff --git a/plugin/icedteanp/IcedTeaPluginUtils.cc b/plugin/icedteanp/IcedTeaPluginUtils.cc
index 6ce37e8..d8ae1ee 100644
--- a/plugin/icedteanp/IcedTeaPluginUtils.cc
+++ b/plugin/icedteanp/IcedTeaPluginUtils.cc
@@ -53,7 +53,7 @@ exception statement from your version. */
int IcedTeaPluginUtilities::reference = -1;
pthread_mutex_t IcedTeaPluginUtilities::reference_mutex = PTHREAD_MUTEX_INITIALIZER;
std::map<void*, NPP>* IcedTeaPluginUtilities::instance_map = new std::map<void*, NPP>();
-std::map<std::string, NPObjectRef> IcedTeaPluginUtilities::object_map;
+std::map<std::string, NPObject*>* IcedTeaPluginUtilities::object_map = new std::map<std::string, NPObject*>();
/* Plugin async call queue */
static std::vector< PluginThreadCall* >* pendingPluginThreadRequests = new std::vector< PluginThreadCall* >();
@@ -433,9 +433,9 @@ void
IcedTeaPluginUtilities::printStringVector(const char* prefix, std::vector<std::string>* str_vector)
{
- // This is a CPU intensive function. Run only if debugging
- if (!plugin_debug)
- return;
+ // This is a CPU intensive function. Run only if debugging
+ if (!plugin_debug)
+ return;
std::string* str = new std::string();
*str += "{ ";
@@ -561,25 +561,27 @@ IcedTeaPluginUtilities::getInstanceFromMemberPtr(void* member_ptr)
* @return The associated active NPObject, NULL otherwise
*/
-NPObjectRef
+NPObject*
IcedTeaPluginUtilities::getNPObjectFromJavaKey(std::string key)
{
+
+ NPObject* object = NULL;
PLUGIN_DEBUG("getNPObjectFromJavaKey looking for %s\n", key.c_str());
- std::map<std::string, NPObjectRef>::iterator iterator = object_map.find(key);
+ std::map<std::string, NPObject*>::iterator iterator = object_map->find(key);
- if (iterator != object_map.end())
+ if (iterator != object_map->end())
{
- NPObjectRef object = object_map.find(key)->second;
+ NPObject* mapped_object = object_map->find(key)->second;
- if (getInstanceFromMemberPtr(object.get()) != NULL)
+ if (getInstanceFromMemberPtr(mapped_object) != NULL)
{
- PLUGIN_DEBUG("getNPObjectFromJavaKey found %s. NPObject = %p\n", key.c_str(), object.get());
- return object;
+ object = mapped_object;
+ PLUGIN_DEBUG("getNPObjectFromJavaKey found %s. NPObject = %p\n", key.c_str(), object);
}
}
- return NPObjectRef(NULL);
+ return object;
}
/**
@@ -590,10 +592,10 @@ IcedTeaPluginUtilities::getNPObjectFromJavaKey(std::string key)
*/
void
-IcedTeaPluginUtilities::storeObjectMapping(std::string key, NPObjectRef object)
+IcedTeaPluginUtilities::storeObjectMapping(std::string key, NPObject* object)
{
- PLUGIN_DEBUG("Storing object %p with key %s\n", object.get(), key.c_str());
- object_map.insert(std::make_pair(key, object));
+ PLUGIN_DEBUG("Storing object %p with key %s\n", object, key.c_str());
+ object_map->insert(std::make_pair(key, object));
}
/**
@@ -606,14 +608,19 @@ void
IcedTeaPluginUtilities::removeObjectMapping(std::string key)
{
PLUGIN_DEBUG("Removing key %s from object map\n", key.c_str());
- object_map.erase(key);
+ object_map->erase(key);
}
/* Clear object_map. Useful for tests. */
void
IcedTeaPluginUtilities::clearObjectMapping()
{
- object_map = std::map<std::string, NPObjectRef>();
+ std::map<std::string, NPObject*>::iterator iter = object_map->begin();
+ for (; iter != object_map->end(); ++iter) {
+ browser_functions.releaseobject(iter->second);
+ }
+ delete object_map;
+ object_map = new std::map<std::string, NPObject*>();
}
/*
@@ -626,9 +633,9 @@ IcedTeaPluginUtilities::clearObjectMapping()
void
IcedTeaPluginUtilities::printStringPtrVector(const char* prefix, std::vector<std::string*>* str_ptr_vector)
{
- // This is a CPU intensive function. Run only if debugging
- if (!plugin_debug)
- return;
+ // This is a CPU intensive function. Run only if debugging
+ if (!plugin_debug)
+ return;
std::string* str = new std::string();
*str += "{ ";
@@ -812,13 +819,18 @@ javaObjectResultToNPVariant(NPP instance, const std::string& jobject_id, NPVaria
std::string jclass_id = *jclass_result->return_string;
- bool is_array = (jclass_id.at(0) == '[');
- NPObjectRef object = IcedTeaScriptableJavaObject::get_scriptable_java_object(instance, jclass_id,
- jobject_id, is_array);
+ NPObject* obj;
+ if (jclass_id.at(0) == '[') // array
+ {
+ obj = IcedTeaScriptableJavaObject::get_scriptable_java_object(instance, jclass_id,
+ jobject_id, true);
+ } else
+ {
+ obj = IcedTeaScriptableJavaObject::get_scriptable_java_object(instance, jclass_id,
+ jobject_id, false);
+ }
- OBJECT_TO_NPVARIANT(object.get(), *variant);
- /* Retain because we are returning an NPObject* */
- object.raw_retain();
+ OBJECT_TO_NPVARIANT(obj, *variant);
return true;
}
@@ -862,12 +874,12 @@ IcedTeaPluginUtilities::javaResultToNPVariant(NPP instance,
}
bool
-IcedTeaPluginUtilities::isObjectJSArray(NPP instance, NPObjectRef object)
+IcedTeaPluginUtilities::isObjectJSArray(NPP instance, NPObject* object)
{
NPVariant constructor_v = NPVariant();
NPIdentifier constructor_id = browser_functions.getstringidentifier("constructor");
- browser_functions.getproperty(instance, object.get(), constructor_id, &constructor_v);
+ browser_functions.getproperty(instance, object, constructor_id, &constructor_v);
IcedTeaPluginUtilities::printNPVariant(constructor_v);
// void constructor => not an array
@@ -1075,34 +1087,6 @@ void IcedTeaPluginUtilities::trim(std::string& str) {
str = str.substr(start, end - start + 1);
}
-std::string
-IcedTeaPluginUtilities::stringPrintf(const char* fmt, /*variable arguments*/ ...)
-{
- /* Extract the variable arguments */
- va_list args;
- va_start(args, fmt);
-
- gchar* result = NULL;
- size_t size;
-
- /* Format the arguments into a new buffer, held in 'result' */
- size = g_vasprintf (&result, fmt, args);
-
- if (result == NULL)
- {
- // We are out of memory
- throw std::bad_alloc();
- }
-
- /* Wrap as string and free buffer */
- std::string str(result, size);
- g_free(result);
-
- va_end(args); /* Finish using variable arguments */
-
- return str;
-}
-
std::string IcedTeaPluginUtilities::NPIdentifierAsString(NPIdentifier id) {
NPUTF8* cstr = browser_functions.utf8fromidentifier(id);
if (cstr == NULL) {
@@ -1258,41 +1242,3 @@ MessageBus::post(const char* message)
PLUGIN_DEBUG("%p unlocked...\n", &msg_queue_mutex);
}
-void
-NPObjectRef::set(NPObject* new_object)
-{
- if (new_object != NULL) {
- /* Increase the new object's reference count */
- browser_functions.retainobject(new_object);
- }
- if (current_object != NULL) {
- /* Decrease the old object's reference count */
- browser_functions.releaseobject(current_object);
- }
-
- this->current_object = new_object;
-}
-
-NPObjectRef
-NPObjectRef::create(NPP instance, NPClass* np_class)
-{
- NPObjectRef ref;
- /* Don't use set(), otherwise we'd double-retain */
- ref.current_object = browser_functions.createobject(instance, np_class);
- return ref;
-}
-
-/* Explicit reference counting operations, use only if needed for interoperating with NPObject* */
-void
-NPObjectRef::raw_retain() {
- if (current_object != NULL) {
- browser_functions.retainobject(current_object);
- }
-}
-
-void
-NPObjectRef::raw_release() {
- if (current_object != NULL) {
- browser_functions.releaseobject(current_object);
- }
-}
diff --git a/plugin/icedteanp/IcedTeaPluginUtils.h b/plugin/icedteanp/IcedTeaPluginUtils.h
index 56aeb94..29cc3ae 100644
--- a/plugin/icedteanp/IcedTeaPluginUtils.h
+++ b/plugin/icedteanp/IcedTeaPluginUtils.h
@@ -153,61 +153,6 @@ typedef struct async_call_thread_data
/* Function to process all pending async calls */
void processAsyncCallQueue(void*);
-/* Reference-counted 'smart pointer' to NPObject */
-class NPObjectRef {
-public:
- /* Create with browser_functions.createobject.
- * This ensures the object is not double-retained. */
- static NPObjectRef create(NPP instance, NPClass* np_class);
-
- NPObjectRef(NPObject* obj = NULL) {
- current_object = NULL;
- set(obj);
- }
-
- NPObjectRef(const NPObjectRef& ref) {
- current_object = NULL;
- set(ref.current_object);
- }
-
- NPObjectRef& operator=(const NPObjectRef& ref) {
- set(ref.current_object);
- return *this;
- }
-
- ~NPObjectRef() {
- clear();
- }
-
- void set(NPObject* new_object);
-
- /* Get's the object pointer */
- NPObject* get() {
- return current_object;
- }
-
- /* Helper for getting object as different type.
- * NOTE: This cast is unchecked. */
- template <typename T>
- T as() {
- return (T)current_object;
- }
-
- /* Explicit reference counting operations, use only if needed for interoperating with NPObject* */
- void raw_retain();
- void raw_release();
-
- bool empty() {
- return (current_object == NULL);
- }
-
- void clear() {
- set(NULL);
- }
-private:
- NPObject* current_object;
-};
-
class IcedTeaPluginUtilities
{
@@ -220,8 +165,8 @@ class IcedTeaPluginUtilities
/* Map holding window pointer<->instance relationships */
static std::map<void*, NPP>* instance_map;
- /* Map holding java-side-obj-key->NPObject relationship. */
- static std::map<std::string, NPObjectRef> object_map;
+ /* Map holding java-side-obj-key->NPObject relationship */
+ static std::map<std::string, NPObject*>* object_map;
/* Posts a call in the async call queue */
static bool postPluginThreadAsyncCall(NPP instance, void (*func) (void *), void* data);
@@ -257,8 +202,6 @@ class IcedTeaPluginUtilities
/* Converts the given integer to a string */
static void itoa(int i, std::string* result);
- static std::string stringPrintf(const char* fmt, ...);
-
/* Copies a variant data type into a C++ string */
static std::string NPVariantAsString(NPVariant variant);
@@ -319,9 +262,9 @@ class IcedTeaPluginUtilities
static NPP getInstanceFromMemberPtr(void* member_ptr);
- static NPObjectRef getNPObjectFromJavaKey(std::string key);
+ static NPObject* getNPObjectFromJavaKey(std::string key);
- static void storeObjectMapping(std::string key, NPObjectRef object);
+ static void storeObjectMapping(std::string key, NPObject* object);
static void removeObjectMapping(std::string key);
@@ -330,7 +273,7 @@ class IcedTeaPluginUtilities
static void invalidateInstance(NPP instance);
- static bool isObjectJSArray(NPP instance, NPObjectRef object);
+ static bool isObjectJSArray(NPP instance, NPObject* object);
static void decodeURL(const char* url, char** decoded_url);
diff --git a/plugin/icedteanp/IcedTeaScriptablePluginObject.cc b/plugin/icedteanp/IcedTeaScriptablePluginObject.cc
index d594afa..51cbcd4 100644
--- a/plugin/icedteanp/IcedTeaScriptablePluginObject.cc
+++ b/plugin/icedteanp/IcedTeaScriptablePluginObject.cc
@@ -306,26 +306,24 @@ IcedTeaScriptableJavaPackageObject::getProperty(NPObject *npobj, NPIdentifier na
//NPIdentifier property = browser_functions.getstringidentifier(property_name.c_str());
- NPObjectRef object;
+ NPObject* obj;
if (isPropertyClass)
{
PLUGIN_DEBUG("Returning package object\n");
- object = IcedTeaScriptableJavaPackageObject::get_scriptable_java_package_object(
+ obj = IcedTeaScriptableJavaPackageObject::get_scriptable_java_package_object(
IcedTeaPluginUtilities::getInstanceFromMemberPtr(npobj),
property_name.c_str());
}
else
{
PLUGIN_DEBUG("Returning Java object\n");
- object = IcedTeaScriptableJavaObject::get_scriptable_java_object(
+ obj = IcedTeaScriptableJavaObject::get_scriptable_java_object(
IcedTeaPluginUtilities::getInstanceFromMemberPtr(npobj),
*(java_result->return_string), "0", false);
}
- OBJECT_TO_NPVARIANT(object.get(), *result);
- /* Retain because we are returning an NPObject* */
- object.raw_retain();
+ OBJECT_TO_NPVARIANT(obj, *result);
return true;
}
@@ -386,33 +384,32 @@ scriptable_java_package_object_class() {
return np_class;
}
-/* Creates a scriptable java object (intended to be called asynch.) */
-static void
-create_scriptable_java_object_async(void* data)
+NPObject*
+IcedTeaScriptableJavaObject::get_scriptable_java_object(NPP instance,
+ std::string class_id,
+ std::string instance_id,
+ bool isArray)
{
- PLUGIN_DEBUG("Asynchronously creating object ...\n");
-
- std::vector<void*> parameters = ((AsyncCallThreadData*) data)->parameters;
- NPP instance = (NPP) parameters.at(0);
- NPClass* np_class = (NPClass*) parameters.at(1);
- NPObjectRef* object_ref = (NPObjectRef*) parameters.at(2);
+ /* Shared NPClass instance for IcedTeaScriptablePluginObject */
+ static NPClass np_class = scriptable_java_package_object_class();
- *object_ref = browser_functions.createobject(instance, np_class);
+ std::string obj_key = class_id + ":" + instance_id;
- ((AsyncCallThreadData*) data)->result_ready = true;
-}
+ PLUGIN_DEBUG("get_scriptable_java_object searching for %s...\n", obj_key.c_str());
+ IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*) IcedTeaPluginUtilities::getNPObjectFromJavaKey(obj_key);
-static NPObjectRef
-create_scriptable_java_object(NPP instance)
-{
- /* Shared NPClass instance for IcedTeaScriptablePluginObject */
- static NPClass np_class = scriptable_java_package_object_class();
+ if (scriptable_object != NULL)
+ {
+ PLUGIN_DEBUG("Returning existing object %p\n", scriptable_object);
+ browser_functions.retainobject(scriptable_object);
+ return scriptable_object;
+ }
// try to create normally
- NPObjectRef np_object = NPObjectRef::create(instance, &np_class);
+ scriptable_object = (IcedTeaScriptableJavaObject*)browser_functions.createobject(instance, &np_class);
// didn't work? try creating asynch
- if (np_object.empty())
+ if (!scriptable_object)
{
AsyncCallThreadData thread_data = AsyncCallThreadData();
thread_data.result_ready = false;
@@ -421,104 +418,45 @@ create_scriptable_java_object(NPP instance)
thread_data.parameters.push_back(instance);
thread_data.parameters.push_back(&np_class);
- thread_data.parameters.push_back(&np_object);
+ thread_data.parameters.push_back(&scriptable_object);
- IcedTeaPluginUtilities::callAndWaitForResult(instance, &create_scriptable_java_object_async, &thread_data);
- }
-
- return np_object;
-}
-
-/* If we are uninitialized, make a Java request for the applet java class & instance ID for the plugin instance.
- * Only objects representing an applet will begin uninitialized, to prevent blocking when the browser requests the object.
- * Returns false on initialization error. */
-bool
-IcedTeaScriptableJavaObject::tryToInitializeIfApplet() {
- if (initialization_failed || initialized)
- {
- return !initialization_failed;
- }
-
- JavaRequestProcessor java_request;
-
- std::string id = IcedTeaPluginUtilities::stringPrintf("%d", get_id_from_instance(instance));
-
- /* Try to fetch the specific applet Java instance */
- JavaResultData* instance_result = java_request.getAppletObjectInstance(id);
- if (instance_result->error_occurred)
- {
- printf("Error: Unable to fetch applet instance id from Java side.\n");
- initialization_failed = true;
- return false;
- }
- this->instance_id = *instance_result->return_string;
-
- /* Try to fetch the applet Java class */
- JavaResultData* class_result = java_request.getClassID(id);
- if (class_result->error_occurred)
+ IcedTeaPluginUtilities::callAndWaitForResult(instance, &_createAndRetainJavaObject, &thread_data);
+ } else
{
- printf("Error: Unable to fetch applet instance id from Java side.\n");
- initialization_failed = true;
- return false;
+ // Else retain object and continue
+ browser_functions.retainobject(scriptable_object);
}
- this->class_id = *class_result->return_string;
- std::string obj_key = getClassID() + ":" + getInstanceID();
- IcedTeaPluginUtilities::storeObjectMapping(obj_key, this);
+ PLUGIN_DEBUG("Constructed new Java Object with classid=%s, instanceid=%s, isArray=%d and scriptable_object=%p\n", class_id.c_str(), instance_id.c_str(), isArray, scriptable_object);
- printf("Object was initialized at '%s'.\n", obj_key.c_str());
+ scriptable_object->class_id = class_id;
+ scriptable_object->is_object_array = isArray;
- initialized = true;
+ if (instance_id != "0")
+ scriptable_object->instance_id = instance_id;
- return true;
-}
+ IcedTeaPluginUtilities::storeInstanceID(scriptable_object, instance);
+ IcedTeaPluginUtilities::storeObjectMapping(obj_key, scriptable_object);
-NPObjectRef
-IcedTeaScriptableJavaObject::get_scriptable_applet_object(NPP instance)
-{
- PLUGIN_DEBUG("get_scriptable_applet_object creating applet object for %p...\n", instance);
-
- /* Do not mark as initialized, object will lookup class & instance IDs before use */
- NPObjectRef object = create_scriptable_java_object(instance);
- IcedTeaPluginUtilities::storeInstanceID(object.get(), instance);
- return object;
+ PLUGIN_DEBUG("Inserting into object_map key %s->%p\n", obj_key.c_str(), scriptable_object);
+ return scriptable_object;
}
-NPObjectRef
-IcedTeaScriptableJavaObject::get_scriptable_java_object(NPP instance,
- std::string class_id,
- std::string instance_id,
- bool isArray)
+/* Creates and retains a scriptable java object (intended to be called asynch.) */
+void
+_createAndRetainJavaObject(void* data)
{
- std::string obj_key = class_id + ":" + instance_id;
-
- PLUGIN_DEBUG("get_scriptable_java_object searching for %s...\n", obj_key.c_str());
- NPObjectRef object = IcedTeaPluginUtilities::getNPObjectFromJavaKey(obj_key);
-
- if (!object.empty())
- {
- PLUGIN_DEBUG("Returning existing object %p\n", object.get());
- return object;
- }
-
- object = create_scriptable_java_object(instance);
- PLUGIN_DEBUG("Constructed new Java Object with classid=%s, instanceid=%s, isArray=%d and scriptable_object=%p\n", class_id.c_str(), instance_id.c_str(), isArray, object.get());
-
- IcedTeaScriptableJavaObject* scriptable_object = object.as<IcedTeaScriptableJavaObject*>();
- scriptable_object->class_id = class_id;
- scriptable_object->is_object_array = isArray;
- /* We know the class & instance already at this point, so we are initialized */
- scriptable_object->initialized = true;
+ PLUGIN_DEBUG("Asynchronously creating/retaining object ...\n");
- if (instance_id != "0") {
- scriptable_object->instance_id = instance_id;
- }
+ std::vector<void*> parameters = ((AsyncCallThreadData*) data)->parameters;
+ NPP instance = (NPP) parameters.at(0);
+ NPClass* np_class = (NPClass*) parameters.at(1);
+ NPObject** scriptable_object = (NPObject**) parameters.at(2);
- IcedTeaPluginUtilities::storeInstanceID(object.get(), instance);
- IcedTeaPluginUtilities::storeObjectMapping(obj_key, object.get());
+ *scriptable_object = browser_functions.createobject(instance, np_class);
+ browser_functions.retainobject(*scriptable_object);
- PLUGIN_DEBUG("Inserting into object_map key %s->%p\n", obj_key.c_str(), object.get());
- return object;
+ ((AsyncCallThreadData*) data)->result_ready = true;
}
bool
@@ -529,13 +467,8 @@ IcedTeaScriptableJavaPackageObject::is_valid_java_object(NPObject* object_ptr) {
bool
IcedTeaScriptableJavaObject::hasMethod(NPObject *npobj, NPIdentifier name_id)
{
- IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*) npobj;
- /* If we are an applet object, we may not be initialized yet. */
- if (!scriptable_object->tryToInitializeIfApplet()) {
- return false;
- }
-
std::string name = IcedTeaPluginUtilities::NPIdentifierAsString(name_id);
+ IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*) npobj;
PLUGIN_DEBUG("IcedTeaScriptableJavaObject::hasMethod %s (ival=%d)\n", name.c_str(), browser_functions.intfromidentifier(name_id));
bool hasMethod = false;
@@ -563,12 +496,6 @@ bool
IcedTeaScriptableJavaObject::invoke(NPObject *npobj, NPIdentifier name_id, const NPVariant *args,
uint32_t argCount, NPVariant *result)
{
- IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*) npobj;
- /* If we are an applet object, we may not be initialized yet. */
- if (!scriptable_object->tryToInitializeIfApplet()) {
- return false;
- }
-
std::string name = IcedTeaPluginUtilities::NPIdentifierAsString(name_id);
// Extract arg type array
@@ -581,6 +508,8 @@ IcedTeaScriptableJavaObject::invoke(NPObject *npobj, NPIdentifier name_id, const
JavaResultData* java_result;
JavaRequestProcessor java_request = JavaRequestProcessor();
+ IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*)npobj;
+
std::string instance_id = scriptable_object->instance_id;
std::string class_id = scriptable_object->class_id;
@@ -629,17 +558,12 @@ IcedTeaScriptableJavaObject::invoke(NPObject *npobj, NPIdentifier name_id, const
bool
IcedTeaScriptableJavaObject::hasProperty(NPObject *npobj, NPIdentifier name_id)
{
- IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*) npobj;
- /* If we are an applet object, we may not be initialized yet. */
- if (!scriptable_object->tryToInitializeIfApplet()) {
- return false;
- }
-
std::string name = IcedTeaPluginUtilities::NPIdentifierAsString(name_id);
PLUGIN_DEBUG("IcedTeaScriptableJavaObject::hasProperty %s (ival=%d)\n", name.c_str(), browser_functions.intfromidentifier(name_id));
bool hasProperty = false;
+ IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*)npobj;
// If it is an array, only length and indexes are valid
if (scriptable_object->is_object_array)
{
@@ -672,12 +596,6 @@ IcedTeaScriptableJavaObject::hasProperty(NPObject *npobj, NPIdentifier name_id)
bool
IcedTeaScriptableJavaObject::getProperty(NPObject *npobj, NPIdentifier name_id, NPVariant *result)
{
- IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*) npobj;
- /* If we are an applet object, we may not be initialized yet. */
- if (!scriptable_object->tryToInitializeIfApplet()) {
- return false;
- }
-
std::string name = IcedTeaPluginUtilities::NPIdentifierAsString(name_id);
bool is_string_id = browser_functions.identifierisstring(name_id);
PLUGIN_DEBUG("IcedTeaScriptableJavaObject::getProperty %s (ival=%d)\n", name.c_str(), browser_functions.intfromidentifier(name_id));
@@ -685,11 +603,13 @@ IcedTeaScriptableJavaObject::getProperty(NPObject *npobj, NPIdentifier name_id,
JavaResultData* java_result;
JavaRequestProcessor java_request = JavaRequestProcessor();
+ IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*)npobj;
+
std::string instance_id = scriptable_object->getInstanceID();
std::string class_id = scriptable_object->getClassID();
NPP instance = scriptable_object->instance;
- if (!instance_id.empty()) // Could be an array or a simple object
+ if (instance_id.length() > 0) // Could be an array or a simple object
{
// If array and requesting length
if ( scriptable_object->is_object_array && name == "length")
@@ -760,18 +680,13 @@ IcedTeaScriptableJavaObject::getProperty(NPObject *npobj, NPIdentifier name_id,
bool
IcedTeaScriptableJavaObject::setProperty(NPObject *npobj, NPIdentifier name_id, const NPVariant *value)
{
- IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*) npobj;
- /* If we are an applet object, we may not be initialized yet. */
- if (!scriptable_object->tryToInitializeIfApplet()) {
- return false;
- }
-
std::string name = IcedTeaPluginUtilities::NPIdentifierAsString(name_id);
PLUGIN_DEBUG("IcedTeaScriptableJavaObject::setProperty %s (ival=%d) to:\n", name.c_str(), browser_functions.intfromidentifier(name_id));
IcedTeaPluginUtilities::printNPVariant(*value);
JavaResultData* java_result;
JavaRequestProcessor java_request = JavaRequestProcessor();
+ IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*)npobj;
std::string instance_id = scriptable_object->getInstanceID();
std::string class_id = scriptable_object->getClassID();
@@ -845,12 +760,7 @@ bool
IcedTeaScriptableJavaObject::construct(NPObject *npobj, const NPVariant *args, uint32_t argCount,
NPVariant *result)
{
- IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*) npobj;
- /* If we are an applet object, we may not be initialized yet. */
- if (!scriptable_object->tryToInitializeIfApplet()) {
- return false;
- }
-
+ IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*)npobj;
// Extract arg type array
PLUGIN_DEBUG("IcedTeaScriptableJavaObject::construct %s. Args follow.\n", scriptable_object->getClassID().c_str());
for (int i=0; i < argCount; i++)
@@ -892,13 +802,11 @@ IcedTeaScriptableJavaObject::construct(NPObject *npobj, const NPVariant *args, u
std::string return_obj_instance_id = *java_result->return_string;
std::string return_obj_class_id = scriptable_object->class_id;
- NPObjectRef object = IcedTeaScriptableJavaObject::get_scriptable_java_object(
+ NPObject* obj = IcedTeaScriptableJavaObject::get_scriptable_java_object(
IcedTeaPluginUtilities::getInstanceFromMemberPtr(npobj),
return_obj_class_id, return_obj_instance_id, false);
- OBJECT_TO_NPVARIANT(object.get(), *result);
- /* Retain because we are returning an NPObject* */
- object.raw_retain();
+ OBJECT_TO_NPVARIANT(obj, *result);
PLUGIN_DEBUG("IcedTeaScriptableJavaObject::construct returning.\n");
return true;
diff --git a/plugin/icedteanp/IcedTeaScriptablePluginObject.h b/plugin/icedteanp/IcedTeaScriptablePluginObject.h
index 99e89c2..a02df53 100644
--- a/plugin/icedteanp/IcedTeaScriptablePluginObject.h
+++ b/plugin/icedteanp/IcedTeaScriptablePluginObject.h
@@ -145,20 +145,13 @@ class IcedTeaScriptableJavaObject: public NPObject
private:
NPP instance;
bool is_object_array;
- /* These may be empty if 'initialized' is false */
+ /* These may be empty if 'is_applet_instance' is true
+ * and the object has not yet been used */
std::string class_id, instance_id;
- bool initialized, initialization_failed;
-
- /* If we are uninitialized, make a Java request for the applet java class & instance ID for the plugin instance.
- * Only objects representing an applet will begin uninitialized, to prevent blocking when the browser requests the object.
- * Returns false on initialization error. */
- bool tryToInitializeIfApplet();
public:
IcedTeaScriptableJavaObject(NPP instance) {
this->instance = instance;
- this->is_object_array = false;
- this->initialized = false;
- this->initialization_failed = false;
+ is_object_array = false;
}
static void deAllocate(NPObject *npobj) {
delete (IcedTeaScriptableJavaObject*)npobj;
@@ -173,12 +166,8 @@ public:
return getClassID() + ":" + getInstanceID();
}
static void invalidate(NPObject *npobj) {
- IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*) npobj;
- /* Nothing to do if we have not been initialized */
- if (!scriptable_object->initialized) {
- return;
- }
IcedTeaPluginUtilities::removeInstanceID(npobj);
+ IcedTeaScriptableJavaObject* scriptable_object = (IcedTeaScriptableJavaObject*) npobj;
IcedTeaPluginUtilities::removeObjectMapping(scriptable_object->objectKey());
}
static bool hasMethod(NPObject *npobj, NPIdentifier name_id);
@@ -206,12 +195,15 @@ public:
}
static bool construct(NPObject *npobj, const NPVariant *args,
uint32_t argCount, NPVariant *result);
-
- static NPObjectRef get_scriptable_applet_object(NPP instance);
- static NPObjectRef get_scriptable_java_object(NPP instance,
+ /* Creates and retains a scriptable java object (intended to be called asynch.) */
+ static NPObject* get_scriptable_java_object(NPP instance,
std::string class_id,
std::string instance_id,
bool isArray);
};
+/* Creates and retains a scriptable java object (intended to be called asynch.) */
+
+void _createAndRetainJavaObject(void* data);
+
#endif /* __ICEDTEASCRIPTABLEPLUGINOBJECT_H_ */
diff --git a/tests/cpp-unit-tests/IcedTeaScriptablePluginObjectTest.cc b/tests/cpp-unit-tests/IcedTeaScriptablePluginObjectTest.cc
index b5c893c..bb2b376 100644
--- a/tests/cpp-unit-tests/IcedTeaScriptablePluginObjectTest.cc
+++ b/tests/cpp-unit-tests/IcedTeaScriptablePluginObjectTest.cc
@@ -66,15 +66,16 @@ SUITE(IcedTeaScriptableJavaObject) {
TEST(get_scriptable_java_object) {
MemoryLeakDetector leak_detector;
- /* Ensure freeing*/ {
- NPObjectRef first_obj = IcedTeaScriptableJavaObject::get_scriptable_java_object(&dummy_npp, "DummyClass", "DummyInstance", false);
+ NPObject* first_obj = IcedTeaScriptableJavaObject::get_scriptable_java_object(&dummy_npp, "DummyClass", "DummyInstance", false);
+ browser_functions.releaseobject(first_obj);
- /* After the first call, the object should be cached in the object map */
- NPObjectRef second_obj = IcedTeaScriptableJavaObject::get_scriptable_java_object(&dummy_npp, "DummyClass", "DummyInstance", false);
+ /* After the first call, the object should be cached in the object map */
+ NPObject* second_obj = IcedTeaScriptableJavaObject::get_scriptable_java_object(&dummy_npp, "DummyClass", "DummyInstance", false);
- /* Objects should be the same, because of caching */
- CHECK(first_obj.get() == second_obj.get());
- }
+ /* Objects should be the same, because of caching */
+ CHECK(first_obj == second_obj);
+
+ browser_functions.releaseobject(second_obj);
CHECK(leak_detector.memory_leaks() == 0);
}