implement and use pbuffers in ANGLE for faster d3d interop

RESOLVED FIXED

Status

()

defect
RESOLVED FIXED
9 years ago
9 years ago

People

(Reporter: vlad, Assigned: vlad)

Tracking

Firefox Tracking Flags

(Not tracked)

Details

Attachments

(3 attachments)

We really want some type of renderable type in ANGLE that we can just use directly as a source in our compositing layers to avoid the expensive and unnecessary readback.  To keep consistent API, we could either implement pbuffers, or implement EGL images.  The latter is much more complex, and pbuffers get us basically exactly what we want anyway.
This is upstream bug http://code.google.com/p/angleproject/issues/detail?id=91

Implements pbuffers, and a custom surface attribute that will obtain a IDirect3D9Texture* object from a pbuffer surface.  It also has to introduce a new getter so that it can return a pointer-sized value.
The mozilla-side work to use pbuffers/texture exported by ANGLE.

This is the minimum amount of work needed to make things be efficient with D3D10 layers.  It assumes that share handles are available and that a Direct3D9Ex device is used.  This significantly speeds up WebGL rendering in many cases when we use ANGLE.

I didn't do any work to make this work with D3D9 layers, because there's additional work that needs to be done to make it work with a passed-in D3D9 device (such as we'd have to do on XP, since we don't have D3D9Ex there).  But, I don't think that work is important, especially not for Firefox 4.  I think early WebGL adopters will already be on 7 by now, and we can fix the d3d9 bits later.
Attachment #497304 - Flags: review?
Attachment #497304 - Flags: review? → review?(bas.schouten)
Comment on attachment 497304 [details] [diff] [review]
actually use ANGLE pbuffers support with d3d10 layers


>diff --git a/gfx/layers/d3d10/CanvasLayerD3D10.cpp b/gfx/layers/d3d10/CanvasLayerD3D10.cpp
>--- a/gfx/layers/d3d10/CanvasLayerD3D10.cpp
>+++ b/gfx/layers/d3d10/CanvasLayerD3D10.cpp
>@@ -76,23 +76,34 @@ CanvasLayerD3D10::Initialize(const Data&
>     void *data = mSurface->GetData(&gKeyD3D10Texture);
>     if (data) {
>       mTexture = static_cast<ID3D10Texture2D*>(data);
>-      mIsD2DTexture = true;
>+      mIsD2DTexture = PR_TRUE;
I don't personally care for PRBool. I should be punished for using PRPackedBool as a type for these and would prefer switching those to bool over using PR_TRUE here!

>-  CD3D10_TEXTURE2D_DESC desc(DXGI_FORMAT_B8G8R8A8_UNORM, mBounds.width, mBounds.height, 1, 1);
>-  desc.Usage = D3D10_USAGE_DYNAMIC;
>-  desc.CPUAccessFlags = D3D10_CPU_ACCESS_WRITE;
>+  HANDLE shareHandle = mGLContext ? mGLContext->GetD3DShareHandle() : nsnull;
>+  if (shareHandle) {
>+    HRESULT hr = device()->OpenSharedResource(shareHandle, __uuidof(ID3D10Texture2D), getter_AddRefs(mTexture));
>+    if (SUCCEEDED(hr))
>+      mUsingSharedTexture = PR_TRUE;
nit: Let's { } this for consistency with the rest of the file/layers.

> 
>+ID3D10Device1 *
>+LayerManagerD3D10::GlobalDevice()
>+{
>+  cairo_device_t *device = gfxWindowsPlatform::GetPlatform()->GetD2DDevice();
>+  if (!device) {
>+      return nsnull;
>+  }
>+
>+  return cairo_d2d_device_get_device(device);
>+}
>+
> bool
> LayerManagerD3D10::Initialize()
> {
>   HRESULT hr;
> 
>-  cairo_device_t *device = gfxWindowsPlatform::GetPlatform()->GetD2DDevice();
>-  if (!device) {
>-    return false;
>+  mDevice = GlobalDevice();

I'm not sure this patch should touch this code, but if it does, let's just use gfxWindowsPlatform::GetD3D10Device() which has been added since this code was written.
Attachment #497304 - Flags: review?(bas.schouten) → review+
updated the "use" patch a bit, but roughly the same.  Seems to work well.
Attachment #501481 - Flags: review?
Attachment #501481 - Flags: review? → review?(bas.schouten)
Comment on attachment 501481 [details] [diff] [review]
use ANGLE pbuffers, v2

># HG changeset patch
># Parent bf2901cfd6a56e21bef98a4fc12241d7eadc970b
>
>+ID3D10Device1 *
>+LayerManagerD3D10::GlobalDevice()
>+{
>+  cairo_device_t *device = gfxWindowsPlatform::GetPlatform()->GetD2DDevice();
>+  if (!device) {
>+      return nsnull;
>+  }
>+
>+  return cairo_d2d_device_get_device(device);
>+}
>+
> bool
> LayerManagerD3D10::Initialize()
> {
>   HRESULT hr;
> 
>-  cairo_device_t *device = gfxWindowsPlatform::GetPlatform()->GetD2DDevice();
>-  if (!device) {
>-    return false;
>+  mDevice = GlobalDevice();

What's wrong with gfxWindowsPlatform::GetD3D10Device ?
Attachment #501481 - Flags: review?(bas.schouten) → review+
You need to log in before you can comment on or make changes to this bug.