# HG changeset patch # User Deepak Bhole # Date 1330372059 18000 # Node ID a25e0ec36020bed436d59d4a2c7d1994eb45e434 # Parent c9a253d0952b5baaf39c924e3fcce062dff5fd14 PR820: IcedTea-Web 1.1.3 crashing Firefox when loading Citrix XenApp Patch from Thomas Meyer (primary) and Deepak Bhole diff -r c9a253d0952b -r a25e0ec36020 ChangeLog --- a/ChangeLog Wed Feb 22 10:18:45 2012 -0500 +++ b/ChangeLog Mon Feb 27 14:47:39 2012 -0500 @@ -1,3 +1,23 @@ +2012-02-27 Thomas Meyer + Deepak Bhole + + PR820: IcedTea-Web 1.1.3 crashing Firefox when loading Citrix XenApp + * plugin/icedteanp/IcedTeaJavaRequestProcessor.cc + (createJavaObjectFromVariant): If variant is a generic object array, + create a JSObject on Java side instead of JSObject array. + * plugin/icedteanp/IcedTeaPluginRequestProcessor.cc + (newMessageOnBus): Run finalize on main thread. + (eval): Create Java object in _eval + (call): Create Java object in _call. + (setMember): Create Java object in _setMember. + (sendMember): Create Java object in _getMember. + (sendString): Create Java object in _getString. + (_setMember): Process result and create Java object if needed. + (_getMember): Same. + (_eval): Same. + (_call): Same. + (_getString): Same. + 2012-02-22 Danesh Dadachanji Add ability to check for jnlp_href use outside of PluginBridge. diff -r c9a253d0952b -r a25e0ec36020 NEWS --- a/NEWS Wed Feb 22 10:18:45 2012 -0500 +++ b/NEWS Mon Feb 27 14:47:39 2012 -0500 @@ -21,6 +21,7 @@ * Plugin - PR749: sun.applet.PluginStreamHandler#handleMessage(String) really slow - PR782: Support building against npapi-sdk as well + - PR820: IcedTea-Web 1.1.3 crashing Firefox when loading Citrix XenApp - PR838: IcedTea plugin crashes with chrome browser when javascript is executed - PR852: Classloader not being flushed after last applet from a site is closed - RH586194: Unable to connect to connect with Juniper VPN client diff -r c9a253d0952b -r a25e0ec36020 plugin/icedteanp/IcedTeaJavaRequestProcessor.cc --- a/plugin/icedteanp/IcedTeaJavaRequestProcessor.cc Wed Feb 22 10:18:45 2012 -0500 +++ b/plugin/icedteanp/IcedTeaJavaRequestProcessor.cc Mon Feb 27 14:47:39 2012 -0500 @@ -921,6 +921,7 @@ { PLUGIN_DEBUG("NPObject is not a Java object\n"); NPIdentifier length_id = browser_functions.getstringidentifier("length"); + bool isJSObjectArray = false; // FIXME: We currently only handle <= 2 dim arrays. Do we really need more though? @@ -936,7 +937,7 @@ std::string length_str = std::string(); IcedTeaPluginUtilities::itoa(NPVARIANT_TO_INT32(length), &length_str); - if (NPVARIANT_TO_INT32(length) > 0) + if (NPVARIANT_TO_INT32(length) >= 0) { NPIdentifier id_0 = browser_functions.getintidentifier(0); NPVariant first_element = NPVariant(); @@ -956,8 +957,14 @@ { getArrayTypeForJava(instance, first_element, &java_array_type); } - } else - java_array_type.append("jsobject"); + } + + // For JSObject arrays, we create a regular object (accessible via JSObject.getSlot()) + if (NPVARIANT_TO_INT32(length) < 0 || !java_array_type.compare("jsobject")) + { + isJSObjectArray = true; + goto createRegularObject; + } java_result = java_request.newArray(java_array_type, length_str); @@ -995,7 +1002,10 @@ // Got here => no errors above. We're good to return! return; - } else // Else it is not an array + } + + createRegularObject: + if (!IcedTeaPluginUtilities::isObjectJSArray(instance, obj) || isJSObjectArray) // Else it is not an array { NPVariant* variant_copy = new NPVariant(); diff -r c9a253d0952b -r a25e0ec36020 plugin/icedteanp/IcedTeaPluginRequestProcessor.cc --- a/plugin/icedteanp/IcedTeaPluginRequestProcessor.cc Wed Feb 22 10:18:45 2012 -0500 +++ b/plugin/icedteanp/IcedTeaPluginRequestProcessor.cc Mon Feb 27 14:47:39 2012 -0500 @@ -123,6 +123,12 @@ // returns immediately, so we do it in the same thread. this->sendWindow(message_parts); return true; + } else if (!command->find("Finalize")) + { + // Object can be finalized from the main thread only. And this + // call returns immediately, so we do it in the same thread. + this->finalize(message_parts); + return true; } else if (!command->find("GetMember") || !command->find("SetMember") || !command->find("ToString") || @@ -130,7 +136,6 @@ !command->find("GetSlot") || !command->find("SetSlot") || !command->find("Eval") || - !command->find("Finalize") || !command->find("LoadURL")) { @@ -241,19 +246,9 @@ IcedTeaPluginUtilities::callAndWaitForResult(instance, &_eval, &thread_data); - NPVariant* result_variant = (NPVariant*) IcedTeaPluginUtilities::stringToJSID(thread_data.result); - std::string result_variant_jniid = std::string(); - if (result_variant) - { - createJavaObjectFromVariant(instance, *result_variant, &result_variant_jniid); - } else - { - result_variant_jniid = "0"; - } - IcedTeaPluginUtilities::constructMessagePrefix(0, reference, &response); response += " JavaScriptEval "; - response += result_variant_jniid; + response += thread_data.result; plugin_to_java_bus->post(response.c_str()); } @@ -336,19 +331,9 @@ IcedTeaPluginUtilities::callAndWaitForResult(instance, &_call, &thread_data); - result_variant = (NPVariant*) IcedTeaPluginUtilities::stringToJSID(thread_data.result); - - if (result_variant) - { - createJavaObjectFromVariant(instance, *result_variant, &result_variant_jniid); - } else - { - result_variant_jniid = "0"; - } - IcedTeaPluginUtilities::constructMessagePrefix(0, reference, &response); response += " JavaScriptCall "; - response += result_variant_jniid; + response += thread_data.result; plugin_to_java_bus->post(response.c_str()); @@ -415,7 +400,8 @@ NPP instance; NPVariant* member; - NPIdentifier property_identifier; + std::string property_id = std::string(); + bool int_identifier; JavaRequestProcessor java_request = JavaRequestProcessor(); JavaResultData* java_result; @@ -445,7 +431,8 @@ if (*(message_parts->at(4)) == "SetSlot") { - property_identifier = browser_functions.getintidentifier(atoi(message_parts->at(6)->c_str())); + property_id.append(*(message_parts->at(6))); + int_identifier = true; } else { java_result = java_request.getString(propertyNameID); @@ -457,7 +444,8 @@ //goto cleanup; } - property_identifier = browser_functions.getstringidentifier(java_result->return_string->c_str()); + property_id.append(*(java_result->return_string)); + int_identifier = false; } AsyncCallThreadData thread_data = AsyncCallThreadData(); @@ -467,8 +455,9 @@ thread_data.parameters.push_back(instance); thread_data.parameters.push_back(NPVARIANT_TO_OBJECT(*member)); - thread_data.parameters.push_back(&property_identifier); + thread_data.parameters.push_back(&property_id); thread_data.parameters.push_back(&value); + thread_data.parameters.push_back(&int_identifier); IcedTeaPluginUtilities::callAndWaitForResult(instance, &_setMember, &thread_data); @@ -508,6 +497,7 @@ int method_id; int instance_id; int reference; + bool int_identifier; // debug printout of parent thread data IcedTeaPluginUtilities::printStringPtrVector("PluginRequestProcessor::getMember:", message_parts); @@ -522,7 +512,7 @@ /** Request data from Java if necessary **/ if (*(message_parts->at(4)) == "GetSlot") { - member_identifier = browser_functions.getintidentifier(atoi(member_id.c_str())); + int_identifier=true; } else { // make a new request for getString, to get the name of the identifier @@ -535,7 +525,8 @@ //goto cleanup; } - member_identifier = browser_functions.getstringidentifier(java_result->return_string->c_str()); + member_id.assign(*(java_result->return_string)); + int_identifier=false; } AsyncCallThreadData thread_data = AsyncCallThreadData(); @@ -551,16 +542,11 @@ thread_data.parameters.push_back(instance); thread_data.parameters.push_back(NPVARIANT_TO_OBJECT(*parent_ptr)); - thread_data.parameters.push_back(&member_identifier); + thread_data.parameters.push_back(&member_id); + thread_data.parameters.push_back(&int_identifier); IcedTeaPluginUtilities::callAndWaitForResult(instance, &_getMember, &thread_data); - PLUGIN_DEBUG("Member PTR after internal request: %s\n", thread_data.result.c_str()); - - member_ptr = (NPVariant*) IcedTeaPluginUtilities::stringToJSID(thread_data.result); - - createJavaObjectFromVariant(instance, *member_ptr, &result_id); - IcedTeaPluginUtilities::constructMessagePrefix(0, reference, &response); if (*(message_parts->at(4)) == "GetSlot") { @@ -568,7 +554,7 @@ } else { response.append(" JavaScriptGetMember "); } - response.append(result_id.c_str()); + response.append(thread_data.result); plugin_to_java_bus->post(response.c_str()); } @@ -720,12 +706,6 @@ pthread_mutex_lock(&syn_write_mutex); processor->setMember(message_parts); pthread_mutex_unlock(&syn_write_mutex); - } else if (command == "Finalize") - { - // write methods are synchronized - pthread_mutex_lock(&syn_write_mutex); - processor->finalize(message_parts); - pthread_mutex_unlock(&syn_write_mutex); } else if (command == "LoadURL") // For instance X url { // write methods are synchronized @@ -768,19 +748,26 @@ NPP instance; NPVariant value_variant = NPVariant(); NPObject* member; - NPIdentifier* property; + NPIdentifier property_identifier; + std::vector parameters = ((AsyncCallThreadData*) data)->parameters; instance = (NPP) parameters.at(0); member = (NPObject*) parameters.at(1); - property = (NPIdentifier*) parameters.at(2); + std::string* property_id = (std::string*) parameters.at(2); value = (std::string*) parameters.at(3); + bool* int_identifier = (bool*) parameters.at(4); - PLUGIN_DEBUG("Setting %s on instance %p, object %p to value %s\n", browser_functions.utf8fromidentifier(*property), instance, member, value->c_str()); + if(*int_identifier==true) + property_identifier = browser_functions.getintidentifier(atoi(property_id->c_str())); + else + property_identifier = browser_functions.getstringidentifier(property_id->c_str()); + + PLUGIN_DEBUG("Setting %s on instance %p, object %p to value %s\n", browser_functions.utf8fromidentifier(property_identifier), instance, member, value->c_str()); IcedTeaPluginUtilities::javaResultToNPVariant(instance, value, &value_variant); - ((AsyncCallThreadData*) data)->call_successful = browser_functions.setproperty(instance, member, *property, &value_variant); + ((AsyncCallThreadData*) data)->call_successful = browser_functions.setproperty(instance, member, property_identifier, &value_variant); ((AsyncCallThreadData*) data)->result_ready = true; } @@ -797,23 +784,32 @@ instance = (NPP) parameters.at(0); parent_ptr = (NPObject*) parameters.at(1); - NPIdentifier* member_identifier = (NPIdentifier*) parameters.at(2); + std::string* member_id = (std::string*) parameters.at(2); + NPIdentifier member_identifier; + + bool* int_identifier = (bool*) parameters.at(3); + + if(*int_identifier==true) + member_identifier = browser_functions.getintidentifier(atoi(member_id->c_str())); + else + member_identifier = browser_functions.getstringidentifier(member_id->c_str()); // Get the NPVariant corresponding to this member - PLUGIN_DEBUG("Looking for %p %p %p (%s)\n", instance, parent_ptr, member_identifier, browser_functions.utf8fromidentifier(*member_identifier)); + PLUGIN_DEBUG("Looking for %p %p %p (%s)\n", instance, parent_ptr, member_identifier, browser_functions.utf8fromidentifier(member_identifier)); - if (!browser_functions.hasproperty(instance, parent_ptr, *member_identifier)) + if (!browser_functions.hasproperty(instance, parent_ptr, member_identifier)) { - printf("%s not found!\n", browser_functions.utf8fromidentifier(*member_identifier)); + printf("%s not found!\n", browser_functions.utf8fromidentifier(member_identifier)); } - ((AsyncCallThreadData*) data)->call_successful = browser_functions.getproperty(instance, parent_ptr, *member_identifier, member_ptr); + ((AsyncCallThreadData*) data)->call_successful = browser_functions.getproperty(instance, parent_ptr, member_identifier, member_ptr); IcedTeaPluginUtilities::printNPVariant(*member_ptr); if (((AsyncCallThreadData*) data)->call_successful) { - IcedTeaPluginUtilities::JSIDToString(member_ptr, &member_ptr_str); + createJavaObjectFromVariant(instance, *member_ptr, &member_ptr_str); ((AsyncCallThreadData*) data)->result.append(member_ptr_str); + } ((AsyncCallThreadData*) data)->result_ready = true; @@ -831,8 +827,8 @@ std::string* script_str; NPIdentifier script_identifier; NPString script = NPString(); - NPVariant* eval_result = new NPVariant(); - std::string eval_result_ptr_str = std::string(); + NPVariant* eval_variant = new NPVariant(); + std::string eval_variant_str = std::string(); PLUGIN_DEBUG("_eval called\n"); @@ -854,13 +850,19 @@ PLUGIN_DEBUG("Evaluating: %s\n", script.UTF8Characters); #endif - ((AsyncCallThreadData*) data)->call_successful = browser_functions.evaluate(instance, window_ptr, &script, eval_result); - IcedTeaPluginUtilities::printNPVariant(*eval_result); + ((AsyncCallThreadData*) data)->call_successful = browser_functions.evaluate(instance, window_ptr, &script, eval_variant); + IcedTeaPluginUtilities::printNPVariant(*eval_variant); if (((AsyncCallThreadData*) data)->call_successful) { - IcedTeaPluginUtilities::JSIDToString(eval_result, &eval_result_ptr_str); - ((AsyncCallThreadData*) data)->result.append(eval_result_ptr_str); + if (eval_variant) + { + createJavaObjectFromVariant(instance, *eval_variant, &eval_variant_str); + } else + { + eval_variant_str = "0"; + } + ((AsyncCallThreadData*) data)->result.append(eval_variant_str); } ((AsyncCallThreadData*) data)->result_ready = true; @@ -904,7 +906,15 @@ if (((AsyncCallThreadData*) data)->call_successful) { - IcedTeaPluginUtilities::JSIDToString(call_result, &call_result_ptr_str); + + if (call_result) + { + createJavaObjectFromVariant(instance, *call_result, &call_result_ptr_str); + } else + { + call_result_ptr_str = "0"; + } + ((AsyncCallThreadData*) data)->result.append(call_result_ptr_str); }