Bug 1010434 - NeckoParent matches a wrong app for the request of a new RemoteOpenFile. r=bent
authorJason Duell <jduell.mcbugs@gmail.com>
Fri, 30 May 2014 12:50:51 -0700
changeset 185975 ed3a1590134957c7fe576bd97644f463a34f5d25
parent 185974 9d19364fe875a7b8f3961e0f0e6b790770f1e05b
child 185976 dc79f34a19f10a21bee9a1dff85bbc9d5615af88
push id26871
push userphilringnalda@gmail.com
push dateSun, 01 Jun 2014 03:29:42 +0000
treeherdermozilla-central@0e10c8151654 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersbent
bugs1010434
milestone32.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1010434 - NeckoParent matches a wrong app for the request of a new RemoteOpenFile. r=bent
modules/libjar/nsJARChannel.cpp
netwerk/ipc/NeckoChild.cpp
netwerk/ipc/NeckoChild.h
netwerk/ipc/NeckoParent.cpp
netwerk/ipc/NeckoParent.h
netwerk/ipc/PNecko.ipdl
netwerk/ipc/RemoteOpenFileChild.cpp
netwerk/ipc/RemoteOpenFileChild.h
--- a/modules/libjar/nsJARChannel.cpp
+++ b/modules/libjar/nsJARChannel.cpp
@@ -370,18 +370,21 @@ nsJARChannel::LookupFile()
                 // JarHandler will trigger OnRemoteFileOpen() after the first
                 // request for this file completes and we'll get a JAR cache
                 // hit.
                 return NS_OK;
             }
 
             // Open file on parent: OnRemoteFileOpenComplete called when done
             nsCOMPtr<nsITabChild> tabChild;
-            NS_QueryNotificationCallbacks(mCallbacks, mLoadGroup, tabChild);
-            rv = remoteFile->AsyncRemoteFileOpen(PR_RDONLY, this, tabChild.get());
+            NS_QueryNotificationCallbacks(this, tabChild);
+            nsCOMPtr<nsILoadContext> loadContext;
+            NS_QueryNotificationCallbacks(this, loadContext);
+            rv = remoteFile->AsyncRemoteFileOpen(PR_RDONLY, this, tabChild,
+                                                 loadContext);
             NS_ENSURE_SUCCESS(rv, rv);
         }
     }
     // try to handle a nested jar
     if (!mJarFile) {
         nsCOMPtr<nsIJARURI> jarURI = do_QueryInterface(mJarBaseURI);
         if (jarURI) {
             nsCOMPtr<nsIFileURL> fileURL;
--- a/netwerk/ipc/NeckoChild.cpp
+++ b/netwerk/ipc/NeckoChild.cpp
@@ -264,17 +264,19 @@ bool
 NeckoChild::DeallocPDNSRequestChild(PDNSRequestChild* aChild)
 {
   DNSRequestChild *p = static_cast<DNSRequestChild*>(aChild);
   p->ReleaseIPDLReference();
   return true;
 }
 
 PRemoteOpenFileChild*
-NeckoChild::AllocPRemoteOpenFileChild(const URIParams&, const OptionalURIParams&)
+NeckoChild::AllocPRemoteOpenFileChild(const SerializedLoadContext& aSerialized,
+                                      const URIParams&,
+                                      const OptionalURIParams&)
 {
   // We don't allocate here: instead we always use IPDL constructor that takes
   // an existing RemoteOpenFileChild
   NS_NOTREACHED("AllocPRemoteOpenFileChild should not be called on child");
   return nullptr;
 }
 
 bool
--- a/netwerk/ipc/NeckoChild.h
+++ b/netwerk/ipc/NeckoChild.h
@@ -52,17 +52,18 @@ protected:
   virtual PUDPSocketChild* AllocPUDPSocketChild(const nsCString& aHost,
                                                 const uint16_t& aPort,
                                                 const nsCString& aFilter) MOZ_OVERRIDE;
   virtual bool DeallocPUDPSocketChild(PUDPSocketChild*) MOZ_OVERRIDE;
   virtual PDNSRequestChild* AllocPDNSRequestChild(const nsCString& aHost,
                                                   const uint32_t& aFlags) MOZ_OVERRIDE;
   virtual bool DeallocPDNSRequestChild(PDNSRequestChild*) MOZ_OVERRIDE;
   virtual PRemoteOpenFileChild*
-    AllocPRemoteOpenFileChild(const URIParams&,
+    AllocPRemoteOpenFileChild(const SerializedLoadContext& aSerialized,
+                              const URIParams&,
                               const OptionalURIParams&) MOZ_OVERRIDE;
   virtual bool DeallocPRemoteOpenFileChild(PRemoteOpenFileChild*) MOZ_OVERRIDE;
   virtual PRtspControllerChild* AllocPRtspControllerChild() MOZ_OVERRIDE;
   virtual bool DeallocPRtspControllerChild(PRtspControllerChild*) MOZ_OVERRIDE;
   virtual PRtspChannelChild*
     AllocPRtspChannelChild(const RtspChannelConnectArgs& aArgs)
                            MOZ_OVERRIDE;
   virtual bool DeallocPRtspChannelChild(PRtspChannelChild*) MOZ_OVERRIDE;
--- a/netwerk/ipc/NeckoParent.cpp
+++ b/netwerk/ipc/NeckoParent.cpp
@@ -495,17 +495,18 @@ bool
 NeckoParent::DeallocPDNSRequestParent(PDNSRequestParent* aParent)
 {
   DNSRequestParent *p = static_cast<DNSRequestParent*>(aParent);
   p->Release();
   return true;
 }
 
 PRemoteOpenFileParent*
-NeckoParent::AllocPRemoteOpenFileParent(const URIParams& aURI,
+NeckoParent::AllocPRemoteOpenFileParent(const SerializedLoadContext& aSerialized,
+                                        const URIParams& aURI,
                                         const OptionalURIParams& aAppURI)
 {
   nsCOMPtr<nsIURI> uri = DeserializeURI(aURI);
   nsCOMPtr<nsIFileURL> fileURL = do_QueryInterface(uri);
   if (!fileURL) {
     return nullptr;
   }
 
@@ -518,27 +519,31 @@ NeckoParent::AllocPRemoteOpenFileParent(
     }
     bool haveValidBrowser = false;
     bool hasManage = false;
     nsCOMPtr<mozIApplication> mozApp;
     for (uint32_t i = 0; i < Manager()->ManagedPBrowserParent().Length(); i++) {
       nsRefPtr<TabParent> tabParent =
         static_cast<TabParent*>(Manager()->ManagedPBrowserParent()[i]);
       uint32_t appId = tabParent->OwnOrContainingAppId();
-      nsresult rv = appsService->GetAppByLocalId(appId, getter_AddRefs(mozApp));
-      if (NS_FAILED(rv) || !mozApp) {
-        continue;
+      // Note: this enforces that SerializedLoadContext.appID is one of the apps
+      // in the child process, but there's currently no way to verify the
+      // request is not from a different app in that process.
+      if (appId == aSerialized.mAppId) {
+        nsresult rv = appsService->GetAppByLocalId(appId, getter_AddRefs(mozApp));
+        if (NS_FAILED(rv) || !mozApp) {
+          break;
+        }
+        rv = mozApp->HasPermission("webapps-manage", &hasManage);
+        if (NS_FAILED(rv)) {
+          break;
+        }
+        haveValidBrowser = true;
+        break;
       }
-      hasManage = false;
-      rv = mozApp->HasPermission("webapps-manage", &hasManage);
-      if (NS_FAILED(rv)) {
-        continue;
-      }
-      haveValidBrowser = true;
-      break;
     }
 
     if (!haveValidBrowser) {
       return nullptr;
     }
 
     nsAutoCString requestedPath;
     fileURL->GetPath(requestedPath);
@@ -616,19 +621,21 @@ NeckoParent::AllocPRemoteOpenFileParent(
     }
   }
 
   RemoteOpenFileParent* parent = new RemoteOpenFileParent(fileURL);
   return parent;
 }
 
 bool
-NeckoParent::RecvPRemoteOpenFileConstructor(PRemoteOpenFileParent* aActor,
-                                            const URIParams& aFileURI,
-                                            const OptionalURIParams& aAppURI)
+NeckoParent::RecvPRemoteOpenFileConstructor(
+                PRemoteOpenFileParent* aActor,
+                const SerializedLoadContext& aSerialized,
+                const URIParams& aFileURI,
+                const OptionalURIParams& aAppURI)
 {
   return static_cast<RemoteOpenFileParent*>(aActor)->OpenSendCloseDelete();
 }
 
 bool
 NeckoParent::DeallocPRemoteOpenFileParent(PRemoteOpenFileParent* actor)
 {
   delete actor;
--- a/netwerk/ipc/NeckoParent.h
+++ b/netwerk/ipc/NeckoParent.h
@@ -95,23 +95,26 @@ protected:
                       const FTPChannelCreationArgs& aOpenArgs) MOZ_OVERRIDE;
   virtual bool DeallocPFTPChannelParent(PFTPChannelParent*) MOZ_OVERRIDE;
   virtual PWebSocketParent*
     AllocPWebSocketParent(PBrowserParent* browser,
                           const SerializedLoadContext& aSerialized) MOZ_OVERRIDE;
   virtual bool DeallocPWebSocketParent(PWebSocketParent*) MOZ_OVERRIDE;
   virtual PTCPSocketParent* AllocPTCPSocketParent() MOZ_OVERRIDE;
 
-  virtual PRemoteOpenFileParent* AllocPRemoteOpenFileParent(const URIParams& aFileURI,
-                                                            const OptionalURIParams& aAppURI)
-                                                            MOZ_OVERRIDE;
-  virtual bool RecvPRemoteOpenFileConstructor(PRemoteOpenFileParent* aActor,
-                                              const URIParams& aFileURI,
-                                              const OptionalURIParams& aAppURI)
-                                              MOZ_OVERRIDE;
+  virtual PRemoteOpenFileParent*
+    AllocPRemoteOpenFileParent(const SerializedLoadContext& aSerialized,
+                               const URIParams& aFileURI,
+                               const OptionalURIParams& aAppURI) MOZ_OVERRIDE;
+  virtual bool
+    RecvPRemoteOpenFileConstructor(PRemoteOpenFileParent* aActor,
+                                   const SerializedLoadContext& aSerialized,
+                                   const URIParams& aFileURI,
+                                   const OptionalURIParams& aAppURI)
+                                   MOZ_OVERRIDE;
   virtual bool DeallocPRemoteOpenFileParent(PRemoteOpenFileParent* aActor)
                                             MOZ_OVERRIDE;
 
   virtual bool DeallocPTCPSocketParent(PTCPSocketParent*) MOZ_OVERRIDE;
   virtual PTCPServerSocketParent*
     AllocPTCPServerSocketParent(const uint16_t& aLocalPort,
                                 const uint16_t& aBacklog,
                                 const nsString& aBinaryType) MOZ_OVERRIDE;
--- a/netwerk/ipc/PNecko.ipdl
+++ b/netwerk/ipc/PNecko.ipdl
@@ -63,17 +63,19 @@ parent:
               FTPChannelCreationArgs args);
 
   PWebSocket(PBrowser browser, SerializedLoadContext loadContext);
   PTCPServerSocket(uint16_t localPort, uint16_t backlog, nsString binaryType);
   PUDPSocket(nsCString host, uint16_t port, nsCString filter);
 
   PDNSRequest(nsCString hostName, uint32_t flags);
 
-  PRemoteOpenFile(URIParams fileuri, OptionalURIParams appuri);
+  PRemoteOpenFile(SerializedLoadContext loadContext,
+                  URIParams fileuri,
+                  OptionalURIParams appuri);
 
   HTMLDNSPrefetch(nsString hostname, uint16_t flags);
   CancelHTMLDNSPrefetch(nsString hostname, uint16_t flags, nsresult reason);
   PRtspController();
   PRtspChannel(RtspChannelConnectArgs args);
   PChannelDiverter(ChannelDiverterArgs channel);
 
 both:
--- a/netwerk/ipc/RemoteOpenFileChild.cpp
+++ b/netwerk/ipc/RemoteOpenFileChild.cpp
@@ -10,16 +10,17 @@
 #include "mozilla/ipc/FileDescriptor.h"
 #include "mozilla/ipc/FileDescriptorUtils.h"
 #include "mozilla/ipc/URIUtils.h"
 #include "mozilla/net/NeckoChild.h"
 #include "nsThreadUtils.h"
 #include "nsJARProtocolHandler.h"
 #include "nsIRemoteOpenFileListener.h"
 #include "nsProxyRelease.h"
+#include "SerializedLoadContext.h"
 
 // needed to alloc/free NSPR file descriptors
 #include "private/pprio.h"
 
 using namespace mozilla::ipc;
 
 namespace mozilla {
 namespace net {
@@ -170,17 +171,18 @@ RemoteOpenFileChild::Init(nsIURI* aRemot
   NS_ENSURE_SUCCESS(rv, rv);
 
   return NS_OK;
 }
 
 nsresult
 RemoteOpenFileChild::AsyncRemoteFileOpen(int32_t aFlags,
                                          nsIRemoteOpenFileListener* aListener,
-                                         nsITabChild* aTabChild)
+                                         nsITabChild* aTabChild,
+                                         nsILoadContext *aLoadContext)
 {
   if (!mFile) {
     return NS_ERROR_NOT_INITIALIZED;
   }
 
   if (!aListener) {
     return NS_ERROR_INVALID_ARG;
   }
@@ -222,17 +224,18 @@ RemoteOpenFileChild::AsyncRemoteFileOpen
     }
   }
 
   URIParams uri;
   SerializeURI(mURI, uri);
   OptionalURIParams appUri;
   SerializeURI(mAppURI, appUri);
 
-  gNeckoChild->SendPRemoteOpenFileConstructor(this, uri, appUri);
+  IPC::SerializedLoadContext loadContext(aLoadContext);
+  gNeckoChild->SendPRemoteOpenFileConstructor(this, loadContext, uri, appUri);
 
   // The chrome process now has a logical ref to us until it calls Send__delete.
   AddIPDLReference();
 
   mListener = aListener;
   mAsyncOpenCalled = true;
   return NS_OK;
 #endif
--- a/netwerk/ipc/RemoteOpenFileChild.h
+++ b/netwerk/ipc/RemoteOpenFileChild.h
@@ -9,16 +9,18 @@
 
 #include "mozilla/Attributes.h"
 #include "mozilla/dom/TabChild.h"
 #include "mozilla/net/PRemoteOpenFileChild.h"
 #include "nsICachedFileDescriptorListener.h"
 #include "nsILocalFile.h"
 #include "nsIRemoteOpenFileListener.h"
 
+class nsILoadContext;
+
 namespace mozilla {
 
 namespace ipc {
 class FileDescriptor;
 }
 
 namespace net {
 
@@ -67,17 +69,18 @@ public:
   // a file:// uri.
   nsresult Init(nsIURI* aRemoteOpenUri, nsIURI* aAppUri);
 
   // Send message to parent to tell it to open file handle for file.
   // TabChild is required, for IPC security.
   // Note: currently only PR_RDONLY is supported for 'flags'
   nsresult AsyncRemoteFileOpen(int32_t aFlags,
                                nsIRemoteOpenFileListener* aListener,
-                               nsITabChild* aTabChild);
+                               nsITabChild* aTabChild,
+                               nsILoadContext *aLoadContext);
 
   void ReleaseIPDLReference()
   {
     Release();
   }
 
 private:
   RemoteOpenFileChild(const RemoteOpenFileChild& other);