Bug 619488 - Inform child processes of the compositor's layer-manager type. r=jones.chris.g a=b-f
authorOleg Romashin <romaxa@gmail.com>
Fri, 31 Dec 2010 09:40:19 +0200
changeset 59743 75928a70efe72c9b907927cc70467813ef0d33be
parent 59742 5344d5110a0f8fc4fadb4bd1287911e0d003dd76
child 59744 b083bc8b79ab0afb0371d419f0ac1246a9004412
push id1
push usershaver@mozilla.com
push dateTue, 04 Jan 2011 17:58:04 +0000
reviewersjones, b-f
bugs619488
milestone2.0b9pre
Bug 619488 - Inform child processes of the compositor's layer-manager type. r=jones.chris.g a=b-f
gfx/layers/Layers.h
gfx/layers/ipc/PLayers.ipdl
gfx/layers/ipc/ShadowLayers.cpp
gfx/layers/ipc/ShadowLayers.h
gfx/layers/ipc/ShadowLayersParent.cpp
gfx/layers/ipc/ShadowLayersParent.h
ipc/glue/IPCMessageUtils.h
--- a/gfx/layers/Layers.h
+++ b/gfx/layers/Layers.h
@@ -227,20 +227,22 @@ private:
  * Layers are refcounted. The layer manager holds a reference to the
  * root layer, and each container layer holds a reference to its children.
  */
 class THEBES_API LayerManager {
   NS_INLINE_DECL_REFCOUNTING(LayerManager)
 
 public:
   enum LayersBackend {
-    LAYERS_BASIC = 0,
+    LAYERS_NONE = 0,
+    LAYERS_BASIC,
     LAYERS_OPENGL,
     LAYERS_D3D9,
-    LAYERS_D3D10
+    LAYERS_D3D10,
+    LAYERS_LAST
   };
 
   LayerManager() : mDestroyed(PR_FALSE), mSnapEffectiveTransforms(PR_TRUE)
   {
     InitLog();
   }
   virtual ~LayerManager() {}
 
--- a/gfx/layers/ipc/PLayers.ipdl
+++ b/gfx/layers/ipc/PLayers.ipdl
@@ -49,16 +49,17 @@ using gfxRGBA;
 using nsIntPoint;
 using nsIntRect;
 using nsIntRegion;
 using nsIntSize;
 using mozilla::GraphicsFilterType;
 using mozilla::layers::FrameMetrics;
 using mozilla::layers::SurfaceDescriptorX11;
 using mozilla::null_t;
+using mozilla::LayersBackend;
 
 /**
  * The layers protocol is spoken between thread contexts that manage
  * layer (sub)trees.  The protocol comprises atomically publishing
  * layer subtrees to a "shadow" thread context (which grafts the
  * subtree into its own tree), and atomically updating a published
  * subtree.  ("Atomic" in this sense is wrt painting.)
  */
@@ -238,13 +239,16 @@ sync protocol PLayers {
   manages PLayer;
 
 parent:
   async PLayer();
 
   sync Update(Edit[] cset)
     returns (EditReply[] reply);
 
+  sync GetParentType()
+    returns (LayersBackend backend);
+
   async __delete__();
 };
 
 } // namespace layers
 } // namespace mozilla
--- a/gfx/layers/ipc/ShadowLayers.cpp
+++ b/gfx/layers/ipc/ShadowLayers.cpp
@@ -118,17 +118,19 @@ private:
   Transaction& operator=(const Transaction&);
 };
 struct AutoTxnEnd {
   AutoTxnEnd(Transaction* aTxn) : mTxn(aTxn) {}
   ~AutoTxnEnd() { mTxn->End(); }
   Transaction* mTxn;
 };
 
-ShadowLayerForwarder::ShadowLayerForwarder() : mShadowManager(NULL)
+ShadowLayerForwarder::ShadowLayerForwarder()
+ : mShadowManager(NULL)
+ , mParentBackend(LayerManager::LAYERS_NONE)
 {
   mTxn = new Transaction();
 }
 
 ShadowLayerForwarder::~ShadowLayerForwarder()
 {
   NS_ABORT_IF_FALSE(mTxn->Finished(), "unfinished transaction?");
   delete mTxn;
@@ -367,16 +369,28 @@ ShadowLayerForwarder::EndTransaction(Inf
     MOZ_LAYERS_LOG(("[LayersForwarder] WARNING: sending transaction failed!"));
     return PR_FALSE;
   }
 
   MOZ_LAYERS_LOG(("[LayersForwarder] ... done"));
   return PR_TRUE;
 }
 
+LayersBackend
+ShadowLayerForwarder::GetParentBackendType()
+{
+  if (mParentBackend == LayerManager::LAYERS_NONE) {
+    LayersBackend backend;
+    if (mShadowManager->SendGetParentType(&backend)) {
+      mParentBackend = backend;
+    }
+  }
+  return mParentBackend;
+}
+
 static gfxASurface::gfxImageFormat
 OptimalFormatFor(gfxASurface::gfxContentType aContent)
 {
   switch (aContent) {
   case gfxASurface::CONTENT_COLOR:
 #ifdef MOZ_GFX_OPTIMIZE_MOBILE
     return gfxASurface::ImageFormatRGB16_565;
 #else
--- a/gfx/layers/ipc/ShadowLayers.h
+++ b/gfx/layers/ipc/ShadowLayers.h
@@ -106,16 +106,18 @@ class Transaction;
  * There are only shadow types for layers that have different shadow
  * vs. not-shadow behavior.  ColorLayers and ContainerLayers behave
  * the same way in both regimes (so far).
  */
 
 class ShadowLayerForwarder
 {
 public:
+  typedef LayerManager::LayersBackend LayersBackend;
+
   virtual ~ShadowLayerForwarder();
 
   /**
    * Begin recording a transaction to be forwarded atomically to a
    * ShadowLayerManager.
    */
   void BeginTransaction();
 
@@ -300,16 +302,18 @@ public:
   void DestroySharedSurface(SurfaceDescriptor* aSurface);
 
   /**
    * Construct a shadow of |aLayer| on the "other side", at the
    * ShadowLayerManager.
    */
   PLayerChild* ConstructShadowFor(ShadowableLayer* aLayer);
 
+  LayersBackend GetParentBackendType();
+
 protected:
   ShadowLayerForwarder();
 
   PLayersChild* mShadowManager;
 
 private:
   PRBool PlatformAllocDoubleBuffer(const gfxIntSize& aSize,
                                    gfxASurface::gfxContentType aContent,
@@ -319,16 +323,17 @@ private:
   static already_AddRefed<gfxASurface>
   PlatformOpenDescriptor(const SurfaceDescriptor& aDescriptor);
 
   PRBool PlatformDestroySharedSurface(SurfaceDescriptor* aSurface);
 
   static void PlatformSyncBeforeUpdate();
 
   Transaction* mTxn;
+  LayersBackend mParentBackend;
 };
 
 
 class ShadowLayerManager : public LayerManager
 {
 public:
   virtual ~ShadowLayerManager() {}
 
--- a/gfx/layers/ipc/ShadowLayersParent.cpp
+++ b/gfx/layers/ipc/ShadowLayersParent.cpp
@@ -439,16 +439,23 @@ ShadowLayersParent::RecvUpdate(const Inf
   // other's buffer contents.
   ShadowLayerManager::PlatformSyncBeforeReplyUpdate();
 
   Frame()->ShadowLayersUpdated();
 
   return true;
 }
 
+bool
+ShadowLayersParent::RecvGetParentType(LayersBackend* aBackend)
+{
+  *aBackend = layer_manager()->GetBackendType();
+  return true;
+}
+
 PLayerParent*
 ShadowLayersParent::AllocPLayer()
 {
   return new ShadowLayerParent();
 }
 
 bool
 ShadowLayersParent::DeallocPLayer(PLayerParent* actor)
--- a/gfx/layers/ipc/ShadowLayersParent.h
+++ b/gfx/layers/ipc/ShadowLayersParent.h
@@ -67,16 +67,18 @@ public:
   ShadowLayerManager* layer_manager() const { return mLayerManager; }
 
   ContainerLayer* GetRoot() const { return mRoot; }
 
 protected:
   NS_OVERRIDE virtual bool RecvUpdate(const EditArray& cset,
                                       EditReplyArray* reply);
 
+  NS_OVERRIDE virtual bool RecvGetParentType(LayersBackend* aBackend);
+
   NS_OVERRIDE virtual PLayerParent* AllocPLayer();
   NS_OVERRIDE virtual bool DeallocPLayer(PLayerParent* actor);
 
 private:
   RenderFrameParent* Frame();
 
   nsRefPtr<ShadowLayerManager> mLayerManager;
   // Hold the root because it might be grafted under various
--- a/ipc/glue/IPCMessageUtils.h
+++ b/ipc/glue/IPCMessageUtils.h
@@ -46,34 +46,38 @@
 #include "nsTArray.h"
 #include "gfx3DMatrix.h"
 #include "gfxColor.h"
 #include "gfxMatrix.h"
 #include "gfxPattern.h"
 #include "nsRect.h"
 #include "nsRegion.h"
 #include "gfxASurface.h"
+#include "Layers.h"
 
 #ifdef _MSC_VER
 #pragma warning( disable : 4800 )
 #endif
 
 #if !defined(OS_POSIX)
 // This condition must be kept in sync with the one in
 // ipc_message_utils.h, but this dummy definition of
 // base::FileDescriptor acts as a static assert that we only get one
 // def or the other (or neither, in which case code using
 // FileDescriptor fails to build)
 namespace base { class FileDescriptor { }; }
 #endif
 
+using mozilla::layers::LayerManager;
+
 namespace mozilla {
 
 typedef gfxPattern::GraphicsFilter GraphicsFilterType;
 typedef gfxASurface::gfxSurfaceType gfxSurfaceType;
+typedef LayerManager::LayersBackend LayersBackend;
 
 // XXX there are out of place and might be generally useful.  Could
 // move to nscore.h or something.
 struct void_t {
   bool operator==(const void_t&) const { return true; }
 };
 struct null_t {
   bool operator==(const null_t&) const { return true; }
@@ -493,16 +497,45 @@ struct ParamTraits<mozilla::gfxSurfaceTy
         filter < gfxASurface::SurfaceTypeMax) {
       *result = paramType(filter);
       return true;
     }
     return false;
   }
 };
 
+ template<>
+struct ParamTraits<mozilla::LayersBackend>
+{
+  typedef mozilla::LayersBackend paramType;
+
+  static void Write(Message* msg, const paramType& param)
+  {
+    if (LayerManager::LAYERS_NONE < param &&
+        param < LayerManager::LAYERS_LAST) {
+      WriteParam(msg, int32(param));
+      return;
+    }
+    NS_RUNTIMEABORT("surface type not reached");
+  }
+
+  static bool Read(const Message* msg, void** iter, paramType* result)
+  {
+    int32 type;
+    if (!ReadParam(msg, iter, &type))
+      return false;
+
+    if (LayerManager::LAYERS_NONE < type &&
+        type < LayerManager::LAYERS_LAST) {
+      *result = paramType(type);
+      return true;
+    }
+    return false;
+  }
+};
 
 template<>
 struct ParamTraits<gfxRGBA>
 {
   typedef gfxRGBA paramType;
 
   static void Write(Message* msg, const paramType& param)
   {