Bug 1496003 - Add sync ipc WebRenderBridgeChild::SendEnsureConnected() r=mattwoodrow,froydnj
authorsotaro <sotaro.ikeda.g@gmail.com>
Fri, 05 Oct 2018 16:35:29 +0900
changeset 495512 0052f643487612ccd8993a8687b1a3b1cbede32d
parent 495511 463cee9e37d965f514aec1bc546db7ce7321ece6
child 495513 19b215c7a61e1ae5e018cbf22e0f18033f73ceef
push id9984
push userffxbld-merge
push dateMon, 15 Oct 2018 21:07:35 +0000
treeherdermozilla-beta@183d27ea8570 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmattwoodrow, froydnj
bugs1496003
milestone64.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 1496003 - Add sync ipc WebRenderBridgeChild::SendEnsureConnected() r=mattwoodrow,froydnj
gfx/layers/ipc/CompositorBridgeChild.cpp
gfx/layers/ipc/CompositorBridgeChild.h
gfx/layers/ipc/CompositorBridgeParent.cpp
gfx/layers/ipc/CompositorBridgeParent.h
gfx/layers/ipc/CrossProcessCompositorBridgeParent.cpp
gfx/layers/ipc/CrossProcessCompositorBridgeParent.h
gfx/layers/ipc/PCompositorBridge.ipdl
gfx/layers/ipc/PWebRenderBridge.ipdl
gfx/layers/wr/WebRenderBridgeParent.cpp
gfx/layers/wr/WebRenderBridgeParent.h
gfx/layers/wr/WebRenderLayerManager.cpp
gfx/webrender_bindings/WebRenderTypes.h
ipc/ipdl/sync-messages.ini
--- a/gfx/layers/ipc/CompositorBridgeChild.cpp
+++ b/gfx/layers/ipc/CompositorBridgeChild.cpp
@@ -1092,19 +1092,17 @@ CompositorBridgeChild::DeallocPAPZCTreeM
 void
 CompositorBridgeChild::WillEndTransaction()
 {
   ResetShmemCounter();
 }
 
 PWebRenderBridgeChild*
 CompositorBridgeChild::AllocPWebRenderBridgeChild(const wr::PipelineId& aPipelineId,
-                                                  const LayoutDeviceIntSize&,
-                                                  TextureFactoryIdentifier*,
-                                                  wr::IdNamespace *aIdNamespace)
+                                                  const LayoutDeviceIntSize&)
 {
   WebRenderBridgeChild* child = new WebRenderBridgeChild(aPipelineId);
   child->AddIPDLReference();
   return child;
 }
 
 bool
 CompositorBridgeChild::DeallocPWebRenderBridgeChild(PWebRenderBridgeChild* aActor)
--- a/gfx/layers/ipc/CompositorBridgeChild.h
+++ b/gfx/layers/ipc/CompositorBridgeChild.h
@@ -205,19 +205,17 @@ public:
   bool DeallocPAPZCTreeManagerChild(PAPZCTreeManagerChild* aActor) override;
 
   PAPZChild* AllocPAPZChild(const LayersId& aLayersId) override;
   bool DeallocPAPZChild(PAPZChild* aActor) override;
 
   void WillEndTransaction();
 
   PWebRenderBridgeChild* AllocPWebRenderBridgeChild(const wr::PipelineId& aPipelineId,
-                                                    const LayoutDeviceIntSize&,
-                                                    TextureFactoryIdentifier*,
-                                                    wr::IdNamespace*) override;
+                                                    const LayoutDeviceIntSize&) override;
   bool DeallocPWebRenderBridgeChild(PWebRenderBridgeChild* aActor) override;
 
   wr::MaybeExternalImageId GetNextExternalImageId() override;
 
   wr::PipelineId GetNextPipelineId();
 
   // Must only be called from the main thread. Ensures that any paints from
   // previous frames have been flushed. The main thread blocks until the
--- a/gfx/layers/ipc/CompositorBridgeParent.cpp
+++ b/gfx/layers/ipc/CompositorBridgeParent.cpp
@@ -1849,19 +1849,17 @@ CompositorBridgeParent::RecvAdoptChild(c
     }
     mApzUpdater->NotifyLayerTreeAdopted(child, oldApzUpdater);
   }
   return IPC_OK();
 }
 
 PWebRenderBridgeParent*
 CompositorBridgeParent::AllocPWebRenderBridgeParent(const wr::PipelineId& aPipelineId,
-                                                    const LayoutDeviceIntSize& aSize,
-                                                    TextureFactoryIdentifier* aTextureFactoryIdentifier,
-                                                    wr::IdNamespace* aIdNamespace)
+                                                    const LayoutDeviceIntSize& aSize)
 {
 #ifndef MOZ_BUILD_WEBRENDER
   // Extra guard since this in the parent process and we don't want a malicious
   // child process invoking this codepath before it's ready
   MOZ_RELEASE_ASSERT(false);
 #endif
   MOZ_ASSERT(wr::AsLayersId(aPipelineId) == mRootLayerTreeID);
   MOZ_ASSERT(!mWrBridge);
@@ -1880,38 +1878,34 @@ CompositorBridgeParent::AllocPWebRenderB
   if (mApzSampler) {
     // Same as for mApzUpdater, but for the sampler thread.
     mApzSampler->SetWebRenderWindowId(windowId);
   }
   RefPtr<wr::WebRenderAPI> api = wr::WebRenderAPI::Create(this, std::move(widget), windowId, aSize);
   if (!api) {
     mWrBridge = WebRenderBridgeParent::CreateDestroyed(aPipelineId);
     mWrBridge.get()->AddRef(); // IPDL reference
-    *aIdNamespace = mWrBridge->GetIdNamespace();
-    *aTextureFactoryIdentifier = TextureFactoryIdentifier(LayersBackend::LAYERS_NONE);
     return mWrBridge;
   }
   mAsyncImageManager = new AsyncImagePipelineManager(api->Clone());
   RefPtr<AsyncImagePipelineManager> asyncMgr = mAsyncImageManager;
   wr::TransactionBuilder txn;
   txn.SetRootPipeline(aPipelineId);
   api->SendTransaction(txn);
   RefPtr<CompositorAnimationStorage> animStorage = GetAnimationStorage();
   mWrBridge = new WebRenderBridgeParent(this, aPipelineId, mWidget, nullptr, std::move(api), std::move(asyncMgr), std::move(animStorage), mVsyncRate);
   mWrBridge.get()->AddRef(); // IPDL reference
 
-  *aIdNamespace = mWrBridge->GetIdNamespace();
   mCompositorScheduler = mWrBridge->CompositorScheduler();
   MOZ_ASSERT(mCompositorScheduler);
   { // scope lock
     MonitorAutoLock lock(*sIndirectLayerTreesLock);
     MOZ_ASSERT(sIndirectLayerTrees[mRootLayerTreeID].mWrBridge == nullptr);
     sIndirectLayerTrees[mRootLayerTreeID].mWrBridge = mWrBridge;
   }
-  *aTextureFactoryIdentifier = mWrBridge->GetTextureFactoryIdentifier();
   return mWrBridge;
 }
 
 bool
 CompositorBridgeParent::DeallocPWebRenderBridgeParent(PWebRenderBridgeParent* aActor)
 {
 #ifndef MOZ_BUILD_WEBRENDER
   // Extra guard since this in the parent process and we don't want a malicious
--- a/gfx/layers/ipc/CompositorBridgeParent.h
+++ b/gfx/layers/ipc/CompositorBridgeParent.h
@@ -482,19 +482,17 @@ public:
   }
 
   TimeDuration GetVsyncInterval() const {
     // the variable is called "rate" but really it's an interval
     return mVsyncRate;
   }
 
   PWebRenderBridgeParent* AllocPWebRenderBridgeParent(const wr::PipelineId& aPipelineId,
-                                                      const LayoutDeviceIntSize& aSize,
-                                                      TextureFactoryIdentifier* aTextureFactoryIdentifier,
-                                                      wr::IdNamespace* aIdNamespace) override;
+                                                      const LayoutDeviceIntSize& aSize) override;
   bool DeallocPWebRenderBridgeParent(PWebRenderBridgeParent* aActor) override;
   RefPtr<WebRenderBridgeParent> GetWebRenderBridgeParent() const;
   Maybe<TimeStamp> GetTestingTimeStamp() const;
 
   static CompositorBridgeParent* GetCompositorBridgeParentFromLayersId(const LayersId& aLayersId);
   static RefPtr<CompositorBridgeParent> GetCompositorBridgeParentFromWindowId(const wr::WindowId& aWindowId);
 
   /**
--- a/gfx/layers/ipc/CrossProcessCompositorBridgeParent.cpp
+++ b/gfx/layers/ipc/CrossProcessCompositorBridgeParent.cpp
@@ -190,19 +190,17 @@ CrossProcessCompositorBridgeParent::Deal
 {
   RemoteContentController* controller = static_cast<RemoteContentController*>(aActor);
   controller->Release();
   return true;
 }
 
 PWebRenderBridgeParent*
 CrossProcessCompositorBridgeParent::AllocPWebRenderBridgeParent(const wr::PipelineId& aPipelineId,
-                                                                const LayoutDeviceIntSize& aSize,
-                                                                TextureFactoryIdentifier* aTextureFactoryIdentifier,
-                                                                wr::IdNamespace *aIdNamespace)
+                                                                const LayoutDeviceIntSize& aSize)
 {
 #ifndef MOZ_BUILD_WEBRENDER
   // Extra guard since this in the parent process and we don't want a malicious
   // child process invoking this codepath before it's ready
   MOZ_RELEASE_ASSERT(false);
 #endif
   LayersId layersId = wr::AsLayersId(aPipelineId);
   // Check to see if this child process has access to this layer tree.
@@ -230,35 +228,31 @@ CrossProcessCompositorBridgeParent::Allo
   }
 
   if (!root || !api) {
     // This could happen when this function is called after CompositorBridgeParent destruction.
     // This was observed during Tab move between different windows.
     NS_WARNING(nsPrintfCString("Created child without a matching parent? root %p", root.get()).get());
     WebRenderBridgeParent* parent = WebRenderBridgeParent::CreateDestroyed(aPipelineId);
     parent->AddRef(); // IPDL reference
-    *aIdNamespace = parent->GetIdNamespace();
-    *aTextureFactoryIdentifier = TextureFactoryIdentifier(LayersBackend::LAYERS_NONE);
     return parent;
   }
 
   api = api->Clone();
   RefPtr<AsyncImagePipelineManager> holder = root->AsyncImageManager();
   RefPtr<CompositorAnimationStorage> animStorage = cbp->GetAnimationStorage();
   WebRenderBridgeParent* parent = new WebRenderBridgeParent(
           this, aPipelineId, nullptr, root->CompositorScheduler(), std::move(api), std::move(holder), std::move(animStorage), cbp->GetVsyncInterval());
   parent->AddRef(); // IPDL reference
 
   { // scope lock
     MonitorAutoLock lock(*sIndirectLayerTreesLock);
     sIndirectLayerTrees[layersId].mCrossProcessParent = this;
     sIndirectLayerTrees[layersId].mWrBridge = parent;
   }
-  *aTextureFactoryIdentifier = parent->GetTextureFactoryIdentifier();
-  *aIdNamespace = parent->GetIdNamespace();
 
   return parent;
 }
 
 bool
 CrossProcessCompositorBridgeParent::DeallocPWebRenderBridgeParent(PWebRenderBridgeParent* aActor)
 {
 #ifndef MOZ_BUILD_WEBRENDER
--- a/gfx/layers/ipc/CrossProcessCompositorBridgeParent.h
+++ b/gfx/layers/ipc/CrossProcessCompositorBridgeParent.h
@@ -140,19 +140,17 @@ public:
   bool DeallocPAPZCTreeManagerParent(PAPZCTreeManagerParent* aActor) override;
 
   PAPZParent* AllocPAPZParent(const LayersId& aLayersId) override;
   bool DeallocPAPZParent(PAPZParent* aActor) override;
 
   void UpdatePaintTime(LayerTransactionParent* aLayerTree, const TimeDuration& aPaintTime) override;
 
   PWebRenderBridgeParent* AllocPWebRenderBridgeParent(const wr::PipelineId& aPipelineId,
-                                                      const LayoutDeviceIntSize& aSize,
-                                                      TextureFactoryIdentifier* aTextureFactoryIdentifier,
-                                                      wr::IdNamespace* aIdNamespace) override;
+                                                      const LayoutDeviceIntSize& aSize) override;
   bool DeallocPWebRenderBridgeParent(PWebRenderBridgeParent* aActor) override;
 
   void ObserveLayersUpdate(LayersId aLayersId, LayersObserverEpoch aEpoch, bool aActive) override;
 
   bool IsRemote() const override {
     return true;
   }
 
--- a/gfx/layers/ipc/PCompositorBridge.ipdl
+++ b/gfx/layers/ipc/PCompositorBridge.ipdl
@@ -237,18 +237,17 @@ parent:
    */
   async AllPluginsCaptured();
 
   async PTexture(SurfaceDescriptor aSharedData, ReadLockDescriptor aReadLock, LayersBackend aBackend, TextureFlags aTextureFlags, LayersId id, uint64_t aSerial, MaybeExternalImageId aExternalImageId);
 
   sync SyncWithCompositor();
 
   // The pipelineId is the same as the layersId
-  sync PWebRenderBridge(PipelineId pipelineId, LayoutDeviceIntSize aSize)
-    returns (TextureFactoryIdentifier textureFactoryIdentifier, IdNamespace idNamespace);
+  async PWebRenderBridge(PipelineId pipelineId, LayoutDeviceIntSize aSize);
 
   sync CheckContentOnlyTDR(uint32_t sequenceNum)
     returns (bool isContentOnlyTDR);
 
 child:
   // Send back Compositor Frame Metrics from APZCs so tiled layers can
   // update progressively.
   async SharedCompositorFrameMetrics(Handle metrics, CrossProcessMutexHandle mutex, LayersId aLayersId, uint32_t aAPZCId);
--- a/gfx/layers/ipc/PWebRenderBridge.ipdl
+++ b/gfx/layers/ipc/PWebRenderBridge.ipdl
@@ -17,29 +17,33 @@ include protocol PTexture;
 using mozilla::layers::APZTestData from "mozilla/layers/APZTestData.h";
 using mozilla::layers::ScrollUpdatesMap from "FrameMetrics.h";
 using struct mozilla::layers::ScrollableLayerGuid from "FrameMetrics.h";
 using struct mozilla::layers::TextureFactoryIdentifier from "mozilla/layers/CompositorTypes.h";
 using struct mozilla::layers::TextureInfo from "mozilla/layers/CompositorTypes.h";
 using mozilla::layers::CompositableHandle from "mozilla/layers/LayersTypes.h";
 using mozilla::wr::BuiltDisplayListDescriptor from "mozilla/webrender/webrender_ffi.h";
 using mozilla::wr::IdNamespace from "mozilla/webrender/WebRenderTypes.h";
+using mozilla::wr::MaybeIdNamespace from "mozilla/webrender/WebRenderTypes.h";
 using mozilla::layers::WebRenderScrollData from "mozilla/layers/WebRenderScrollData.h";
 using mozilla::layers::FocusTarget from "mozilla/layers/FocusTarget.h";
 using mozilla::layers::LayersObserverEpoch from "mozilla/layers/LayersTypes.h";
 using mozilla::layers::TransactionId from "mozilla/layers/LayersTypes.h";
 
 namespace mozilla {
 namespace layers {
 
 sync protocol PWebRenderBridge
 {
   manager PCompositorBridge;
 
 parent:
+  sync EnsureConnected()
+    returns (TextureFactoryIdentifier textureFactoryIdentifier, MaybeIdNamespace maybeIdNamespace);
+
   async NewCompositable(CompositableHandle handle, TextureInfo info);
   async ReleaseCompositable(CompositableHandle compositable);
 
   async DeleteCompositorAnimations(uint64_t[] aIds);
   async SetDisplayList(IntSize aSize, WebRenderParentCommand[] commands, OpDestroy[] toDestroy, uint64_t fwdTransactionId, TransactionId transactionId,
                        LayoutSize aContentSize, ByteBuf aDL, BuiltDisplayListDescriptor aDLDesc,
                        WebRenderScrollData aScrollData,
                        OpUpdateResource[] aResourceUpdates, RefCountedShmem[] aSmallShmems, Shmem[] aLargeShmems,
--- a/gfx/layers/wr/WebRenderBridgeParent.cpp
+++ b/gfx/layers/wr/WebRenderBridgeParent.cpp
@@ -258,16 +258,33 @@ WebRenderBridgeParent::CreateDestroyed(c
   return new WebRenderBridgeParent(aPipelineId);
 }
 
 WebRenderBridgeParent::~WebRenderBridgeParent()
 {
 }
 
 mozilla::ipc::IPCResult
+WebRenderBridgeParent::RecvEnsureConnected(TextureFactoryIdentifier* aTextureFactoryIdentifier,
+                                           MaybeIdNamespace* aMaybeIdNamespace)
+{
+  if (mDestroyed) {
+    *aTextureFactoryIdentifier = TextureFactoryIdentifier(LayersBackend::LAYERS_NONE);
+    *aMaybeIdNamespace = Nothing();
+    return IPC_OK();
+  }
+
+  MOZ_ASSERT(mIdNamespace.mHandle != 0);
+  *aTextureFactoryIdentifier = GetTextureFactoryIdentifier();
+  *aMaybeIdNamespace = Some(mIdNamespace);
+
+  return IPC_OK();
+}
+
+mozilla::ipc::IPCResult
 WebRenderBridgeParent::RecvShutdown()
 {
   return HandleShutdown();
 }
 
 mozilla::ipc::IPCResult
 WebRenderBridgeParent::RecvShutdownSync()
 {
--- a/gfx/layers/wr/WebRenderBridgeParent.h
+++ b/gfx/layers/wr/WebRenderBridgeParent.h
@@ -60,16 +60,19 @@ public:
 
   static WebRenderBridgeParent* CreateDestroyed(const wr::PipelineId& aPipelineId);
 
   wr::PipelineId PipelineId() { return mPipelineId; }
   already_AddRefed<wr::WebRenderAPI> GetWebRenderAPI() { return do_AddRef(mApi); }
   AsyncImagePipelineManager* AsyncImageManager() { return mAsyncImageManager; }
   CompositorVsyncScheduler* CompositorScheduler() { return mCompositorScheduler.get(); }
 
+  mozilla::ipc::IPCResult RecvEnsureConnected(TextureFactoryIdentifier* aTextureFactoryIdentifier,
+                                              MaybeIdNamespace* aMaybeIdNamespace) override;
+
   mozilla::ipc::IPCResult RecvNewCompositable(const CompositableHandle& aHandle,
                                               const TextureInfo& aInfo) override;
   mozilla::ipc::IPCResult RecvReleaseCompositable(const CompositableHandle& aHandle) override;
 
   mozilla::ipc::IPCResult RecvShutdown() override;
   mozilla::ipc::IPCResult RecvShutdownSync() override;
   mozilla::ipc::IPCResult RecvDeleteCompositorAnimations(InfallibleTArray<uint64_t>&& aIds) override;
   mozilla::ipc::IPCResult RecvUpdateResources(nsTArray<OpUpdateResource>&& aUpdates,
--- a/gfx/layers/wr/WebRenderLayerManager.cpp
+++ b/gfx/layers/wr/WebRenderLayerManager.cpp
@@ -56,35 +56,41 @@ bool
 WebRenderLayerManager::Initialize(PCompositorBridgeChild* aCBChild,
                                   wr::PipelineId aLayersId,
                                   TextureFactoryIdentifier* aTextureFactoryIdentifier)
 {
   MOZ_ASSERT(mWrChild == nullptr);
   MOZ_ASSERT(aTextureFactoryIdentifier);
 
   LayoutDeviceIntSize size = mWidget->GetClientSize();
-  TextureFactoryIdentifier textureFactoryIdentifier;
-  wr::IdNamespace id_namespace;
   PWebRenderBridgeChild* bridge = aCBChild->SendPWebRenderBridgeConstructor(aLayersId,
-                                                                            size,
-                                                                            &textureFactoryIdentifier,
-                                                                            &id_namespace);
+                                                                            size);
   if (!bridge) {
     // This should only fail if we attempt to access a layer we don't have
     // permission for, or more likely, the GPU process crashed again during
     // reinitialization. We can expect to be notified again to reinitialize
     // (which may or may not be using WebRender).
     gfxCriticalNote << "Failed to create WebRenderBridgeChild.";
     return false;
   }
 
+  TextureFactoryIdentifier textureFactoryIdentifier;
+  wr::MaybeIdNamespace idNamespace;
+  // Sync ipc
+  bridge->SendEnsureConnected(&textureFactoryIdentifier, &idNamespace);
+  if (textureFactoryIdentifier.mParentBackend == LayersBackend::LAYERS_NONE ||
+      idNamespace.isNothing()) {
+    gfxCriticalNote << "Failed to connect WebRenderBridgeChild.";
+    return false;
+  }
+
   mWrChild = static_cast<WebRenderBridgeChild*>(bridge);
   WrBridge()->SetWebRenderLayerManager(this);
   WrBridge()->IdentifyTextureHost(textureFactoryIdentifier);
-  WrBridge()->SetNamespace(id_namespace);
+  WrBridge()->SetNamespace(idNamespace.ref());
   *aTextureFactoryIdentifier = textureFactoryIdentifier;
   return true;
 }
 
 void
 WebRenderLayerManager::Destroy()
 {
   DoDestroy(/* aIsSync */ false);
--- a/gfx/webrender_bindings/WebRenderTypes.h
+++ b/gfx/webrender_bindings/WebRenderTypes.h
@@ -38,16 +38,17 @@ typedef wr::WrWindowId WindowId;
 typedef wr::WrPipelineId PipelineId;
 typedef wr::WrImageKey ImageKey;
 typedef wr::WrFontKey FontKey;
 typedef wr::WrFontInstanceKey FontInstanceKey;
 typedef wr::WrEpoch Epoch;
 typedef wr::WrExternalImageId ExternalImageId;
 typedef wr::WrDebugFlags DebugFlags;
 
+typedef mozilla::Maybe<mozilla::wr::IdNamespace> MaybeIdNamespace;
 typedef mozilla::Maybe<mozilla::wr::WrImageMask> MaybeImageMask;
 typedef Maybe<ExternalImageId> MaybeExternalImageId;
 
 typedef Maybe<FontInstanceOptions> MaybeFontInstanceOptions;
 typedef Maybe<FontInstancePlatformOptions> MaybeFontInstancePlatformOptions;
 
 /* Generate a brand new window id and return it. */
 WindowId NewWindowId();
--- a/ipc/ipdl/sync-messages.ini
+++ b/ipc/ipdl/sync-messages.ini
@@ -975,18 +975,16 @@ description =
 [PCompositorBridge::WaitOnTransactionProcessed]
 description = bug 1364626
 [PCompositorBridge::StartFrameTimeRecording]
 description =
 [PCompositorBridge::StopFrameTimeRecording]
 description =
 [PCompositorBridge::SyncWithCompositor]
 description =
-[PCompositorBridge::PWebRenderBridge]
-description =
 [PCompositorBridge::CheckContentOnlyTDR]
 description =
 [PCompositorWidget::EnterPresentLock]
 description =
 platform = win
 [PCompositorWidget::LeavePresentLock]
 description =
 platform = win
@@ -1016,16 +1014,18 @@ description =
 [PLayerTransaction::GetTextureFactoryIdentifier]
 description = bug 1350634
 [PUiCompositorController::Pause]
 description =
 [PUiCompositorController::Resume]
 description =
 [PUiCompositorController::ResumeAndResize]
 description =
+[PWebRenderBridge::EnsureConnected]
+description =
 [PWebRenderBridge::GetSnapshot]
 description =
 [PWebRenderBridge::SetTestSampleTime]
 description = test only
 [PWebRenderBridge::LeaveTestMode]
 description = test only
 [PWebRenderBridge::GetAnimationValue]
 description = test only