Bug 1394705 - let HTMLMediaElement::MediaLoadListener implement nsIThreadRetargetableStreamListener. r=cpearce
authorJW Wang <jwwang@mozilla.com>
Tue, 29 Aug 2017 14:28:13 +0800
changeset 377724 163c90f28357a4131e8e44006ffbe97b6ddaf632
parent 377723 bb77b7d5e34acbed2e5da823c2fb3527c2cf8c50
child 377725 fc4d31fca3f1afd6cc3b111d1e8c960671d115dc
push id32415
push userkwierso@gmail.com
push dateThu, 31 Aug 2017 02:52:55 +0000
treeherdermozilla-central@04b6be50a252 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewerscpearce
bugs1394705
milestone57.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 1394705 - let HTMLMediaElement::MediaLoadListener implement nsIThreadRetargetableStreamListener. r=cpearce This is required to use nsIThreadRetargetableRequest::RetargetDeliveryTo(). MozReview-Commit-ID: GFuAjovabpY
dom/html/HTMLMediaElement.cpp
dom/media/MediaResource.cpp
dom/media/MediaResource.h
--- a/dom/html/HTMLMediaElement.cpp
+++ b/dom/html/HTMLMediaElement.cpp
@@ -444,47 +444,54 @@ private:
 };
 
 /**
  * There is a reference cycle involving this class: MediaLoadListener
  * holds a reference to the HTMLMediaElement, which holds a reference
  * to an nsIChannel, which holds a reference to this listener.
  * We break the reference cycle in OnStartRequest by clearing mElement.
  */
-class HTMLMediaElement::MediaLoadListener final : public nsIStreamListener,
-                                                  public nsIChannelEventSink,
-                                                  public nsIInterfaceRequestor,
-                                                  public nsIObserver
+class HTMLMediaElement::MediaLoadListener final
+  : public nsIStreamListener
+  , public nsIChannelEventSink
+  , public nsIInterfaceRequestor
+  , public nsIObserver
+  , public nsIThreadRetargetableStreamListener
 {
   ~MediaLoadListener() {}
 
   NS_DECL_ISUPPORTS
   NS_DECL_NSIREQUESTOBSERVER
   NS_DECL_NSISTREAMLISTENER
   NS_DECL_NSICHANNELEVENTSINK
   NS_DECL_NSIOBSERVER
   NS_DECL_NSIINTERFACEREQUESTOR
+  NS_DECL_NSITHREADRETARGETABLESTREAMLISTENER
 
 public:
   explicit MediaLoadListener(HTMLMediaElement* aElement)
     : mElement(aElement),
       mLoadID(aElement->GetCurrentLoadID())
   {
     MOZ_ASSERT(mElement, "Must pass an element to call back");
   }
 
 private:
   RefPtr<HTMLMediaElement> mElement;
   nsCOMPtr<nsIStreamListener> mNextListener;
   const uint32_t mLoadID;
 };
 
-NS_IMPL_ISUPPORTS(HTMLMediaElement::MediaLoadListener, nsIRequestObserver,
-                  nsIStreamListener, nsIChannelEventSink,
-                  nsIInterfaceRequestor, nsIObserver)
+NS_IMPL_ISUPPORTS(HTMLMediaElement::MediaLoadListener,
+                  nsIRequestObserver,
+                  nsIStreamListener,
+                  nsIChannelEventSink,
+                  nsIInterfaceRequestor,
+                  nsIObserver,
+                  nsIThreadRetargetableStreamListener)
 
 NS_IMETHODIMP
 HTMLMediaElement::MediaLoadListener::Observe(nsISupports* aSubject,
                                              const char* aTopic,
                                              const char16_t* aData)
 {
   nsContentUtils::UnregisterShutdownObserver(this);
 
@@ -617,16 +624,28 @@ HTMLMediaElement::MediaLoadListener::Asy
   if (sink) {
     return sink->AsyncOnChannelRedirect(aOldChannel, aNewChannel, aFlags, cb);
   }
   cb->OnRedirectVerifyCallback(NS_OK);
   return NS_OK;
 }
 
 NS_IMETHODIMP
+HTMLMediaElement::MediaLoadListener::CheckListenerChain()
+{
+  MOZ_ASSERT(mNextListener);
+  nsCOMPtr<nsIThreadRetargetableStreamListener> retargetable =
+    do_QueryInterface(mNextListener);
+  if (retargetable) {
+    return retargetable->CheckListenerChain();
+  }
+  return NS_ERROR_NO_INTERFACE;
+}
+
+NS_IMETHODIMP
 HTMLMediaElement::MediaLoadListener::GetInterface(const nsIID& aIID,
                                                   void** aResult)
 {
   return QueryInterface(aIID, aResult);
 }
 
 void HTMLMediaElement::ReportLoadError(const char* aMsg,
                                        const char16_t** aParams,
--- a/dom/media/MediaResource.cpp
+++ b/dom/media/MediaResource.cpp
@@ -117,18 +117,21 @@ ChannelMediaResource::~ChannelMediaResou
 
 // ChannelMediaResource::Listener just observes the channel and
 // forwards notifications to the ChannelMediaResource. We use multiple
 // listener objects so that when we open a new stream for a seek we can
 // disconnect the old listener from the ChannelMediaResource and hook up
 // a new listener, so notifications from the old channel are discarded
 // and don't confuse us.
 NS_IMPL_ISUPPORTS(ChannelMediaResource::Listener,
-                  nsIRequestObserver, nsIStreamListener, nsIChannelEventSink,
-                  nsIInterfaceRequestor)
+                  nsIRequestObserver,
+                  nsIStreamListener,
+                  nsIChannelEventSink,
+                  nsIInterfaceRequestor,
+                  nsIThreadRetargetableStreamListener)
 
 nsresult
 ChannelMediaResource::Listener::OnStartRequest(nsIRequest* aRequest,
                                                nsISupports* aContext)
 {
   if (!mResource)
     return NS_OK;
   return mResource->OnStartRequest(aRequest);
@@ -169,17 +172,23 @@ ChannelMediaResource::Listener::AsyncOnC
   if (NS_FAILED(rv))
     return rv;
 
   cb->OnRedirectVerifyCallback(NS_OK);
   return NS_OK;
 }
 
 nsresult
-ChannelMediaResource::Listener::GetInterface(const nsIID & aIID, void **aResult)
+ChannelMediaResource::Listener::CheckListenerChain()
+{
+  return NS_OK;
+}
+
+nsresult
+ChannelMediaResource::Listener::GetInterface(const nsIID& aIID, void** aResult)
 {
   return QueryInterface(aIID, aResult);
 }
 
 static bool
 IsPayloadCompressed(nsIHttpChannel* aChannel)
 {
   nsAutoCString encoding;
--- a/dom/media/MediaResource.h
+++ b/dom/media/MediaResource.h
@@ -8,16 +8,17 @@
 
 #include "mozilla/Mutex.h"
 #include "nsIChannel.h"
 #include "nsIURI.h"
 #include "nsISeekableStream.h"
 #include "nsIStreamListener.h"
 #include "nsIChannelEventSink.h"
 #include "nsIInterfaceRequestor.h"
+#include "nsIThreadRetargetableStreamListener.h"
 #include "Intervals.h"
 #include "MediaCache.h"
 #include "MediaContainerType.h"
 #include "MediaData.h"
 #include "MediaPrefs.h"
 #include "MediaResourceCallback.h"
 #include "mozilla/Atomics.h"
 #include "mozilla/Attributes.h"
@@ -498,29 +499,32 @@ public:
 
     return size;
   }
 
   size_t SizeOfIncludingThis(MallocSizeOf aMallocSizeOf) const override {
     return aMallocSizeOf(this) + SizeOfExcludingThis(aMallocSizeOf);
   }
 
-  class Listener final : public nsIStreamListener,
-                         public nsIInterfaceRequestor,
-                         public nsIChannelEventSink
+  class Listener final
+    : public nsIStreamListener
+    , public nsIInterfaceRequestor
+    , public nsIChannelEventSink
+    , public nsIThreadRetargetableStreamListener
   {
     ~Listener() {}
   public:
     explicit Listener(ChannelMediaResource* aResource) : mResource(aResource) {}
 
     NS_DECL_ISUPPORTS
     NS_DECL_NSIREQUESTOBSERVER
     NS_DECL_NSISTREAMLISTENER
     NS_DECL_NSICHANNELEVENTSINK
     NS_DECL_NSIINTERFACEREQUESTOR
+    NS_DECL_NSITHREADRETARGETABLESTREAMLISTENER
 
     void Revoke() { mResource = nullptr; }
 
   private:
     RefPtr<ChannelMediaResource> mResource;
   };
   friend class Listener;