Bug 738396 - Only pass canonicalized codebase to Java. r=bsmedberg, sr=jst, a=lsblakk
authorJohn Schoenick <jschoenick@mozilla.com>
Thu, 21 Mar 2013 18:02:23 -0700
changeset 147862 20a1cd5be4fb694f15b71c2c9288f36f4193910f
parent 147861 819cefc60adea7fdb1ce786fb849f28798529b85
child 147863 462bf273f287753314889af0bbb38b0c866abcd7
push id2697
push userbbajaj@mozilla.com
push dateMon, 05 Aug 2013 18:49:53 +0000
treeherdermozilla-beta@dfec938c7b63 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersbsmedberg, jst, lsblakk
bugs738396
milestone24.0a2
Bug 738396 - Only pass canonicalized codebase to Java. r=bsmedberg, sr=jst, a=lsblakk
content/base/public/nsIObjectLoadingContent.idl
content/base/src/nsObjectLoadingContent.cpp
dom/plugins/base/nsPluginInstanceOwner.cpp
--- a/content/base/public/nsIObjectLoadingContent.idl
+++ b/content/base/public/nsIObjectLoadingContent.idl
@@ -20,17 +20,17 @@ interface nsIURI;
 
 /**
  * This interface represents a content node that loads objects.
  *
  * Please make sure to update the MozObjectLoadingContent WebIDL
  * interface to mirror this interface when changing it.
  */
 
-[scriptable, uuid(24a35de3-40e4-498e-9c1b-2fd0a2d4cae5)]
+[scriptable, uuid(070bfc7f-f8b8-4e84-aa31-a0bfaffa8e8e)]
 interface nsIObjectLoadingContent : nsISupports
 {
   /**
    * See notes in nsObjectLoadingContent.h
    */
   const unsigned long TYPE_LOADING  = 0;
   const unsigned long TYPE_IMAGE    = 1;
   const unsigned long TYPE_PLUGIN   = 2;
@@ -83,16 +83,23 @@ interface nsIObjectLoadingContent : nsIS
   /**
    * Gets the content type that corresponds to the give MIME type.  See the
    * constants above for the list of possible values.  If nothing else fits,
    * TYPE_NULL will be returned.
    */
   unsigned long getContentTypeForMIMEType(in AUTF8String aMimeType);
 
   /**
+   * Returns the base URI of the object as seen by plugins. This differs from
+   * the normal codebase in that it takes <param> tags and plugin-specific
+   * quirks into account.
+   */
+  [noscript] readonly attribute nsIURI baseURI;
+
+  /**
    * Returns the plugin instance if it has already been instantiated. This
    * will never instantiate the plugin and so is safe to call even when
    * content script must not execute.
    */
   [noscript] readonly attribute nsNPAPIPluginInstancePtr pluginInstance;
 
   /**
    * Tells the content about an associated object frame.
--- a/content/base/src/nsObjectLoadingContent.cpp
+++ b/content/base/src/nsObjectLoadingContent.cpp
@@ -1062,16 +1062,23 @@ nsObjectLoadingContent::GetPluginInstanc
 NS_IMETHODIMP
 nsObjectLoadingContent::GetContentTypeForMIMEType(const nsACString& aMIMEType,
                                                   uint32_t* aType)
 {
   *aType = GetTypeOfContent(PromiseFlatCString(aMIMEType));
   return NS_OK;
 }
 
+NS_IMETHODIMP
+nsObjectLoadingContent::GetBaseURI(nsIURI **aResult)
+{
+  NS_IF_ADDREF(*aResult = mBaseURI);
+  return NS_OK;
+}
+
 // nsIInterfaceRequestor
 // We use a shim class to implement this so that JS consumers still
 // see an interface requestor even though WebIDL bindings don't expose
 // that stuff.
 class ObjectInterfaceRequestorShim MOZ_FINAL : public nsIInterfaceRequestor,
                                                public nsIChannelEventSink
 {
 public:
--- a/dom/plugins/base/nsPluginInstanceOwner.cpp
+++ b/dom/plugins/base/nsPluginInstanceOwner.cpp
@@ -44,16 +44,17 @@ using mozilla::DefaultXDisplay;
 #include "nsIWebBrowserChrome.h"
 #include "nsLayoutUtils.h"
 #include "nsIPluginWidget.h"
 #include "nsViewManager.h"
 #include "nsIDocShellTreeOwner.h"
 #include "nsIDOMHTMLObjectElement.h"
 #include "nsIAppShell.h"
 #include "nsIDOMHTMLAppletElement.h"
+#include "nsIObjectLoadingContent.h"
 #include "nsAttrName.h"
 #include "nsIFocusManager.h"
 #include "nsFocusManager.h"
 #include "nsIDOMDragEvent.h"
 #include "nsIScrollableFrame.h"
 #include "nsIDocShell.h"
 #include "ImageContainer.h"
 
@@ -1042,16 +1043,21 @@ nsresult nsPluginInstanceOwner::EnsureCa
   // "src" or "wmode" entry below.
   uint32_t cattrs = mContent->GetAttrCount();
   if (cattrs < 0x0000FFFD) {
     mNumCachedAttrs = static_cast<uint16_t>(cattrs);
   } else {
     mNumCachedAttrs = 0xFFFD;
   }
 
+  // Check if we are java for special codebase handling
+  const char* mime = nullptr;
+  bool isJava = NS_SUCCEEDED(mInstance->GetMIMEType(&mime)) && mime &&
+                nsPluginHost::IsJavaMIMEType(mime);
+
   // now, we need to find all the PARAM tags that are children of us
   // however, be careful not to include any PARAMs that don't have us
   // as a direct parent. For nested object (or applet) tags, be sure
   // to only round up the param tags that coorespond with THIS
   // instance. And also, weed out any bogus tags that may get in the
   // way, see bug 39609. Then, with any param tag that meet our
   // qualification, temporarly cache them in an nsCOMArray until
   // we can figure out what size to make our fixed char* array.
@@ -1134,16 +1140,33 @@ nsresult nsPluginInstanceOwner::EnsureCa
 
   // "plugins.force.wmode" preference is forcing wmode type for plugins
   // possible values - "opaque", "transparent", "windowed"
   nsAdoptingCString wmodeType = Preferences::GetCString("plugins.force.wmode");
   if (!wmodeType.IsEmpty()) {
     mNumCachedAttrs++;
   }
 
+  // (Bug 738396) java has quirks in its codebase parsing, pass the
+  // absolute codebase URI as content sees it.
+  bool addCodebase = false;
+  nsAutoCString codebaseStr;
+  if (isJava) {
+    nsCOMPtr<nsIObjectLoadingContent> objlc = do_QueryInterface(mContent);
+    NS_ENSURE_TRUE(objlc, NS_ERROR_UNEXPECTED);
+    nsCOMPtr<nsIURI> codebaseURI;
+    nsresult rv = objlc->GetBaseURI(getter_AddRefs(codebaseURI));
+    NS_ENSURE_SUCCESS(rv, rv);
+    codebaseURI->GetSpec(codebaseStr);
+    if (!mContent->HasAttr(kNameSpaceID_None, nsGkAtoms::codebase)) {
+      mNumCachedAttrs++;
+      addCodebase = true;
+    }
+  }
+
   mCachedAttrParamNames  = (char**)NS_Alloc(sizeof(char*) * (mNumCachedAttrs + 1 + mNumCachedParams));
   NS_ENSURE_TRUE(mCachedAttrParamNames,  NS_ERROR_OUT_OF_MEMORY);
   mCachedAttrParamValues = (char**)NS_Alloc(sizeof(char*) * (mNumCachedAttrs + 1 + mNumCachedParams));
   NS_ENSURE_TRUE(mCachedAttrParamValues, NS_ERROR_OUT_OF_MEMORY);
 
   // Some plugins (eg Flash, see bug 234675.) are actually sensitive to the
   // attribute order.  So we want to make sure we give the plugin the
   // attributes in the order they came in in the source, to be compatible with
@@ -1178,31 +1201,40 @@ nsresult nsPluginInstanceOwner::EnsureCa
     nsAutoString value;
     mContent->GetAttr(attrName->NamespaceID(), atom, value);
     nsAutoString name;
     atom->ToString(name);
 
     FixUpURLS(name, value);
 
     mCachedAttrParamNames [nextAttrParamIndex] = ToNewUTF8String(name);
-    if (!wmodeType.IsEmpty() && 
+    if (!wmodeType.IsEmpty() &&
         0 == PL_strcasecmp(mCachedAttrParamNames[nextAttrParamIndex], "wmode")) {
       mCachedAttrParamValues[nextAttrParamIndex] = ToNewUTF8String(NS_ConvertUTF8toUTF16(wmodeType));
 
       if (!wmodeSet) {
         // We allocated space to add a wmode attr, but we don't need it now.
         mNumCachedAttrs--;
         wmodeSet = true;
       }
+    } else if (isJava && 0 == PL_strcasecmp(mCachedAttrParamNames[nextAttrParamIndex], "codebase")) {
+      mCachedAttrParamValues[nextAttrParamIndex] = ToNewUTF8String(NS_ConvertUTF8toUTF16(codebaseStr));
     } else {
       mCachedAttrParamValues[nextAttrParamIndex] = ToNewUTF8String(value);
     }
     nextAttrParamIndex++;
   }
 
+  // Potentially add CODEBASE attribute
+  if (addCodebase) {
+    mCachedAttrParamNames [nextAttrParamIndex] = ToNewUTF8String(NS_LITERAL_STRING("codebase"));
+    mCachedAttrParamValues[nextAttrParamIndex] = ToNewUTF8String(NS_ConvertUTF8toUTF16(codebaseStr));
+    nextAttrParamIndex++;
+  }
+
   // Potentially add WMODE attribute.
   if (!wmodeType.IsEmpty() && !wmodeSet) {
     mCachedAttrParamNames [nextAttrParamIndex] = ToNewUTF8String(NS_LITERAL_STRING("wmode"));
     mCachedAttrParamValues[nextAttrParamIndex] = ToNewUTF8String(NS_ConvertUTF8toUTF16(wmodeType));
     nextAttrParamIndex++;
   }
 
   // Potentially add SRC attribute.
@@ -1218,41 +1250,50 @@ nsresult nsPluginInstanceOwner::EnsureCa
   // Flash expects an empty string on android
   mCachedAttrParamValues[nextAttrParamIndex] = ToNewUTF8String(NS_LITERAL_STRING(""));
 #else
   mCachedAttrParamValues[nextAttrParamIndex] = nullptr;
 #endif
   nextAttrParamIndex++;
 
   // Add PARAM name/value pairs.
-  for (uint16_t i = 0; i < mNumCachedParams; i++) {
+
+  // We may decrement mNumCachedParams below
+  uint16_t totalParams = mNumCachedParams;
+  for (uint16_t i = 0; i < totalParams; i++) {
     nsIDOMElement* param = ourParams.ObjectAt(i);
     if (!param) {
       continue;
     }
 
     nsAutoString name;
     nsAutoString value;
     param->GetAttribute(NS_LITERAL_STRING("name"), name); // check for empty done above
     param->GetAttribute(NS_LITERAL_STRING("value"), value);
-    
+
     FixUpURLS(name, value);
 
     /*
      * According to the HTML 4.01 spec, at
      * http://www.w3.org/TR/html4/types.html#type-cdata
      * ''User agents may ignore leading and trailing
      * white space in CDATA attribute values (e.g., "
      * myval " may be interpreted as "myval"). Authors
      * should not declare attribute values with
      * leading or trailing white space.''
      * However, do not trim consecutive spaces as in bug 122119
      */
     name.Trim(" \n\r\t\b", true, true, false);
     value.Trim(" \n\r\t\b", true, true, false);
+    if (isJava && name.EqualsIgnoreCase("codebase")) {
+      // We inserted normalized codebase above, don't include other versions in
+      // params
+      mNumCachedParams--;
+      continue;
+    }
     mCachedAttrParamNames [nextAttrParamIndex] = ToNewUTF8String(name);
     mCachedAttrParamValues[nextAttrParamIndex] = ToNewUTF8String(value);
     nextAttrParamIndex++;
   }
 
   return NS_OK;
 }