summaryrefslogtreecommitdiffstats
path: root/ui/gl
diff options
context:
space:
mode:
authorreveman@google.com <reveman@google.com@0039d316-1c4b-4281-b951-d872f2087c98>2012-10-18 20:54:37 +0000
committerreveman@google.com <reveman@google.com@0039d316-1c4b-4281-b951-d872f2087c98>2012-10-18 20:54:37 +0000
commit09d50362dfdeff4d370c6897890186bd48c5c63d (patch)
tree2dd2456badedae14492f4965ca204ecab38873ef /ui/gl
parentee429b55e3bcc64b8bbf63c1c01bbfc4f1402da2 (diff)
downloadchromium_src-09d50362dfdeff4d370c6897890186bd48c5c63d.zip
chromium_src-09d50362dfdeff4d370c6897890186bd48c5c63d.tar.gz
chromium_src-09d50362dfdeff4d370c6897890186bd48c5c63d.tar.bz2
gpu: Add support for GLX_EXT_texture_from_pixmap extension.
Implement CHROMIUM_texture_from_image. This extension behaves just like EXT_texture_from_pixmap but uses chromium specific image identifiers rather than platform specific pixmap IDs. Add IPC message for creating an image identifier using a gfx::PluginWindowHandle. Each GPU channel maintains a different set of images and deleting an image will cause the internal image representation to be freed once it's no longer bound to a texture. BUG=132342 TEST=gpu_unittests --gtest_filter=TextureInfoTest.GetLevelImage:GLES2DecoderTest.BindTexImage2DCHROMIUM:GLES2DecoderTest.ReleaseTexImage2DCHROMIUM and manual Committed: http://src.chromium.org/viewvc/chrome?view=rev&revision=162654 Review URL: https://codereview.chromium.org/10543125 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@162784 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'ui/gl')
-rw-r--r--ui/gl/gl.gyp16
-rw-r--r--ui/gl/gl_image.cc24
-rw-r--r--ui/gl/gl_image.h50
-rw-r--r--ui/gl/gl_image_android.cc27
-rw-r--r--ui/gl/gl_image_glx.cc175
-rw-r--r--ui/gl/gl_image_glx.h42
-rw-r--r--ui/gl/gl_image_linux.cc38
-rw-r--r--ui/gl/gl_image_mac.cc29
-rw-r--r--ui/gl/gl_image_stub.cc25
-rw-r--r--ui/gl/gl_image_stub.h27
-rw-r--r--ui/gl/gl_image_win.cc29
-rw-r--r--ui/gl/gl_surface_glx.cc8
-rw-r--r--ui/gl/gl_surface_glx.h1
13 files changed, 491 insertions, 0 deletions
diff --git a/ui/gl/gl.gyp b/ui/gl/gl.gyp
index 85e4303..32d5e69 100644
--- a/ui/gl/gl.gyp
+++ b/ui/gl/gl.gyp
@@ -53,6 +53,14 @@
'gl_export.h',
'gl_fence.cc',
'gl_fence.h',
+ 'gl_image.cc',
+ 'gl_image.h',
+ 'gl_image_android.cc',
+ 'gl_image_linux.cc',
+ 'gl_image_mac.cc',
+ 'gl_image_stub.cc',
+ 'gl_image_stub.h',
+ 'gl_image_win.cc',
'gl_implementation.cc',
'gl_implementation.h',
'gl_implementation_android.cc',
@@ -143,6 +151,8 @@
'sources': [
'gl_context_glx.cc',
'gl_context_glx.h',
+ 'gl_image_glx.cc',
+ 'gl_image_glx.h',
'gl_surface_glx.cc',
'gl_surface_glx.h',
'<(gl_binding_output_dir)/gl_bindings_autogen_glx.cc',
@@ -153,6 +163,12 @@
'GL_GLEXT_PROTOTYPES',
],
},
+ 'link_settings': {
+ 'libraries': [
+ '-lX11',
+ '-lXcomposite',
+ ],
+ },
}],
['OS=="win"', {
'sources': [
diff --git a/ui/gl/gl_image.cc b/ui/gl/gl_image.cc
new file mode 100644
index 0000000..aaefb94
--- /dev/null
+++ b/ui/gl/gl_image.cc
@@ -0,0 +1,24 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/gl/gl_image.h"
+
+#include "base/logging.h"
+
+namespace gfx {
+
+GLImage::GLImage() {}
+
+bool GLImage::BindTexImage() {
+ NOTIMPLEMENTED();
+ return false;
+}
+
+void GLImage::ReleaseTexImage() {
+ NOTIMPLEMENTED();
+}
+
+GLImage::~GLImage() {}
+
+} // namespace gfx
diff --git a/ui/gl/gl_image.h b/ui/gl/gl_image.h
new file mode 100644
index 0000000..8df7c71
--- /dev/null
+++ b/ui/gl/gl_image.h
@@ -0,0 +1,50 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_GL_GL_IMAGE_H_
+#define UI_GL_GL_IMAGE_H_
+
+#include "base/memory/ref_counted.h"
+#include "ui/gfx/native_widget_types.h"
+#include "ui/gfx/size.h"
+#include "ui/gl/gl_bindings.h"
+#include "ui/gl/gl_export.h"
+
+namespace gfx {
+
+class GLSurface;
+
+// Encapsulates an image that can be bound to a texture, hiding platform
+// specific management.
+class GL_EXPORT GLImage : public base::RefCounted<GLImage> {
+ public:
+ GLImage();
+
+ // Destroys the image.
+ virtual void Destroy() = 0;
+
+ // Get the size of the image.
+ virtual gfx::Size GetSize() = 0;
+
+ // Bind image to texture currently bound to GL_TEXTURE_2D target.
+ virtual bool BindTexImage();
+
+ // Release image from texture currently bound to GL_TEXTURE_2D target.
+ virtual void ReleaseTexImage();
+
+ // Create a GL image for a window.
+ static scoped_refptr<GLImage> CreateGLImage(gfx::PluginWindowHandle window);
+
+ protected:
+ virtual ~GLImage();
+
+ private:
+ friend class base::RefCounted<GLImage>;
+
+ DISALLOW_COPY_AND_ASSIGN(GLImage);
+};
+
+} // namespace gfx
+
+#endif // UI_GL_GL_IMAGE_H_
diff --git a/ui/gl/gl_image_android.cc b/ui/gl/gl_image_android.cc
new file mode 100644
index 0000000..e55e3bb
--- /dev/null
+++ b/ui/gl/gl_image_android.cc
@@ -0,0 +1,27 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/gl/gl_image.h"
+
+#include "base/debug/trace_event.h"
+#include "ui/gl/gl_image_stub.h"
+#include "ui/gl/gl_implementation.h"
+
+namespace gfx {
+
+scoped_refptr<GLImage> GLImage::CreateGLImage(gfx::PluginWindowHandle window) {
+ TRACE_EVENT0("gpu", "GLImage::CreateGLImage");
+ switch (GetGLImplementation()) {
+ case kGLImplementationEGLGLES2: {
+ return NULL;
+ }
+ case kGLImplementationMockGL:
+ return new GLImageStub;
+ default:
+ NOTREACHED();
+ return NULL;
+ }
+}
+
+} // namespace gfx
diff --git a/ui/gl/gl_image_glx.cc b/ui/gl/gl_image_glx.cc
new file mode 100644
index 0000000..5bb4077
--- /dev/null
+++ b/ui/gl/gl_image_glx.cc
@@ -0,0 +1,175 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+extern "C" {
+#include <X11/extensions/Xcomposite.h>
+}
+
+#include "ui/gl/gl_image_glx.h"
+
+#include "base/basictypes.h"
+#include "base/logging.h"
+#include "base/memory/scoped_ptr.h"
+#include "base/message_loop.h"
+#include "ui/gl/gl_surface_glx.h"
+
+namespace gfx {
+
+namespace {
+
+// scoped_ptr functor for XFree(). Use as follows:
+// scoped_ptr_malloc<XVisualInfo, ScopedPtrXFree> foo(...);
+// where "XVisualInfo" is any X type that is freed with XFree.
+class ScopedPtrXFree {
+ public:
+ void operator()(void* x) const {
+ ::XFree(x);
+ }
+};
+
+int BindToTextureFormat(int depth) {
+ if (depth == 32)
+ return GLX_BIND_TO_TEXTURE_RGBA_EXT;
+
+ return GLX_BIND_TO_TEXTURE_RGB_EXT;
+}
+
+int TextureFormat(int depth) {
+ if (depth == 32)
+ return GLX_TEXTURE_FORMAT_RGBA_EXT;
+
+ return GLX_TEXTURE_FORMAT_RGB_EXT;
+}
+
+} // namespace anonymous
+
+GLImageGLX::GLImageGLX(gfx::PluginWindowHandle window)
+ : display_(base::MessagePumpForUI::GetDefaultXDisplay()),
+ window_(window),
+ pixmap_(0),
+ glx_pixmap_(0) {
+}
+
+bool GLImageGLX::Initialize() {
+ if (!GLSurfaceGLX::IsTextureFromPixmapSupported()) {
+ LOG(ERROR) << "GLX_EXT_texture_from_pixmap not supported.";
+ return false;
+ }
+
+ XWindowAttributes attributes;
+ if (!XGetWindowAttributes(display_, window_, &attributes)) {
+ LOG(ERROR) << "XGetWindowAttributes failed for window " << window_ << ".";
+ return false;
+ }
+
+ XVisualInfo templ;
+ templ.visualid = XVisualIDFromVisual(attributes.visual);
+ int num_visinfo = 0;
+ scoped_ptr_malloc<XVisualInfo, ScopedPtrXFree> visinfo(
+ XGetVisualInfo(display_,
+ VisualIDMask,
+ &templ,
+ &num_visinfo));
+ if (!visinfo.get()) {
+ LOG(ERROR) << "XGetVisualInfo failed for visual id " <<
+ templ.visualid << ".";
+ return false;
+ }
+ if (!num_visinfo) {
+ LOG(ERROR) << "XGetVisualInfo returned 0 elements.";
+ return false;
+ }
+
+ int config_attribs[] = {
+ GLX_VISUAL_ID, visinfo->visualid,
+ GLX_DRAWABLE_TYPE, GLX_PIXMAP_BIT,
+ GLX_BIND_TO_TEXTURE_TARGETS_EXT, GLX_TEXTURE_2D_EXT,
+ BindToTextureFormat(visinfo->depth), GL_TRUE,
+ 0
+ };
+ int num_elements = 0;
+ scoped_ptr_malloc<GLXFBConfig, ScopedPtrXFree> config(
+ glXChooseFBConfig(display_,
+ DefaultScreen(display_),
+ config_attribs,
+ &num_elements));
+ if (!config.get()) {
+ LOG(ERROR) << "glXChooseFBConfig failed.";
+ return false;
+ }
+ if (!num_elements) {
+ LOG(ERROR) << "glXChooseFBConfig returned 0 elements.";
+ return false;
+ }
+
+ // Create backing pixmap reference.
+ pixmap_ = XCompositeNameWindowPixmap(display_, window_);
+
+ XID root = 0;
+ int x = 0;
+ int y = 0;
+ unsigned int width = 0;
+ unsigned int height = 0;
+ unsigned int bw = 0;
+ unsigned int depth = 0;
+ if (!XGetGeometry(
+ display_, pixmap_, &root, &x, &y, &width, &height, &bw, &depth)) {
+ LOG(ERROR) << "XGetGeometry failed for pixmap " << pixmap_ << ".";
+ return false;
+ }
+
+ int pixmap_attribs[] = {
+ GLX_TEXTURE_TARGET_EXT, GLX_TEXTURE_2D_EXT,
+ GLX_TEXTURE_FORMAT_EXT, TextureFormat(visinfo->depth),
+ 0
+ };
+ glx_pixmap_ = glXCreatePixmap(
+ display_,
+ *config.get(),
+ pixmap_,
+ pixmap_attribs);
+ if (!glx_pixmap_) {
+ LOG(ERROR) << "glXCreatePixmap failed.";
+ return false;
+ }
+
+ size_ = gfx::Size(width, height);
+ return true;
+}
+
+void GLImageGLX::Destroy() {
+ if (glx_pixmap_) {
+ glXDestroyGLXPixmap(display_, glx_pixmap_);
+ glx_pixmap_ = 0;
+ }
+ if (pixmap_) {
+ XFreePixmap(display_, pixmap_);
+ pixmap_ = 0;
+ }
+}
+
+gfx::Size GLImageGLX::GetSize() {
+ return size_;
+}
+
+bool GLImageGLX::BindTexImage() {
+ if (!glx_pixmap_)
+ return false;
+
+ glXBindTexImageEXT(display_, glx_pixmap_, GLX_FRONT_LEFT_EXT, 0);
+ return true;
+}
+
+void GLImageGLX::ReleaseTexImage() {
+ if (!glx_pixmap_)
+ return;
+
+ glXReleaseTexImageEXT(display_, glx_pixmap_, GLX_FRONT_LEFT_EXT);
+}
+
+GLImageGLX::~GLImageGLX() {
+ Destroy();
+}
+
+} // namespace gfx
diff --git a/ui/gl/gl_image_glx.h b/ui/gl/gl_image_glx.h
new file mode 100644
index 0000000..a3cec2d
--- /dev/null
+++ b/ui/gl/gl_image_glx.h
@@ -0,0 +1,42 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_GL_GL_IMAGE_GLX_H_
+#define UI_GL_GL_IMAGE_GLX_H_
+
+#include "ui/base/x/x11_util.h"
+#include "ui/gfx/size.h"
+#include "ui/gl/gl_export.h"
+#include "ui/gl/gl_image.h"
+
+namespace gfx {
+
+class GL_EXPORT GLImageGLX : public GLImage {
+ public:
+ explicit GLImageGLX(gfx::PluginWindowHandle window);
+
+ virtual bool Initialize();
+
+ // Implement GLImage.
+ virtual void Destroy() OVERRIDE;
+ virtual gfx::Size GetSize() OVERRIDE;
+ virtual bool BindTexImage() OVERRIDE;
+ virtual void ReleaseTexImage() OVERRIDE;
+
+ protected:
+ virtual ~GLImageGLX();
+
+ private:
+ Display* display_;
+ gfx::PluginWindowHandle window_;
+ XID pixmap_;
+ XID glx_pixmap_;
+ gfx::Size size_;
+
+ DISALLOW_COPY_AND_ASSIGN(GLImageGLX);
+};
+
+} // namespace gfx
+
+#endif // UI_GL_GL_IMAGE_GLX_H_
diff --git a/ui/gl/gl_image_linux.cc b/ui/gl/gl_image_linux.cc
new file mode 100644
index 0000000..75efd2a
--- /dev/null
+++ b/ui/gl/gl_image_linux.cc
@@ -0,0 +1,38 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/gl/gl_image.h"
+
+#include "base/debug/trace_event.h"
+#include "ui/gl/gl_image_glx.h"
+#include "ui/gl/gl_image_stub.h"
+#include "ui/gl/gl_implementation.h"
+
+namespace gfx {
+
+scoped_refptr<GLImage> GLImage::CreateGLImage(gfx::PluginWindowHandle window) {
+ TRACE_EVENT0("gpu", "GLImage::CreateGLImage");
+ switch (GetGLImplementation()) {
+ case kGLImplementationOSMesaGL: {
+ return NULL;
+ }
+ case kGLImplementationDesktopGL: {
+ scoped_refptr<GLImageGLX> image(new GLImageGLX(window));
+ if (!image->Initialize())
+ return NULL;
+
+ return image;
+ }
+ case kGLImplementationEGLGLES2: {
+ return NULL;
+ }
+ case kGLImplementationMockGL:
+ return new GLImageStub;
+ default:
+ NOTREACHED();
+ return NULL;
+ }
+}
+
+} // namespace gfx
diff --git a/ui/gl/gl_image_mac.cc b/ui/gl/gl_image_mac.cc
new file mode 100644
index 0000000..a4b522a
--- /dev/null
+++ b/ui/gl/gl_image_mac.cc
@@ -0,0 +1,29 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/gl/gl_image.h"
+
+#include "base/debug/trace_event.h"
+#include "ui/gl/gl_image_stub.h"
+#include "ui/gl/gl_implementation.h"
+
+namespace gfx {
+
+scoped_refptr<GLImage> GLImage::CreateGLImage(gfx::PluginWindowHandle window) {
+ TRACE_EVENT0("gpu", "GLImage::CreateGLImage");
+ switch (GetGLImplementation()) {
+ case kGLImplementationOSMesaGL:
+ case kGLImplementationDesktopGL:
+ case kGLImplementationAppleGL: {
+ return NULL;
+ }
+ case kGLImplementationMockGL:
+ return new GLImageStub;
+ default:
+ NOTREACHED();
+ return NULL;
+ }
+}
+
+} // namespace gfx
diff --git a/ui/gl/gl_image_stub.cc b/ui/gl/gl_image_stub.cc
new file mode 100644
index 0000000..86efe6e
--- /dev/null
+++ b/ui/gl/gl_image_stub.cc
@@ -0,0 +1,25 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/gl/gl_image_stub.h"
+
+namespace gfx {
+
+void GLImageStub::Destroy() {
+}
+
+gfx::Size GLImageStub::GetSize() {
+ return gfx::Size(1, 1);
+}
+
+bool GLImageStub::BindTexImage() {
+ return true;
+}
+
+void GLImageStub::ReleaseTexImage() {
+}
+
+GLImageStub::~GLImageStub() {}
+
+} // namespace gfx
diff --git a/ui/gl/gl_image_stub.h b/ui/gl/gl_image_stub.h
new file mode 100644
index 0000000..8b47358
--- /dev/null
+++ b/ui/gl/gl_image_stub.h
@@ -0,0 +1,27 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_GL_GL_IMAGE_STUB_H_
+#define UI_GL_GL_IMAGE_STUB_H_
+
+#include "ui/gl/gl_image.h"
+
+namespace gfx {
+
+// A GLImage that does nothing for unit tests.
+class GL_EXPORT GLImageStub : public GLImage {
+ public:
+ // Implement GLImage.
+ virtual void Destroy() OVERRIDE;
+ virtual gfx::Size GetSize() OVERRIDE;
+ virtual bool BindTexImage() OVERRIDE;
+ virtual void ReleaseTexImage() OVERRIDE;
+
+ protected:
+ virtual ~GLImageStub();
+};
+
+} // namespace gfx
+
+#endif // UI_GL_GL_IMAGE_STUB_H_
diff --git a/ui/gl/gl_image_win.cc b/ui/gl/gl_image_win.cc
new file mode 100644
index 0000000..8c54bf4
--- /dev/null
+++ b/ui/gl/gl_image_win.cc
@@ -0,0 +1,29 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/gl/gl_image.h"
+
+#include "base/debug/trace_event.h"
+#include "ui/gl/gl_image_stub.h"
+#include "ui/gl/gl_implementation.h"
+
+namespace gfx {
+
+scoped_refptr<GLImage> GLImage::CreateGLImage(gfx::PluginWindowHandle window) {
+ TRACE_EVENT0("gpu", "GLImage::CreateGLImage");
+ switch (GetGLImplementation()) {
+ case kGLImplementationOSMesaGL:
+ case kGLImplementationDesktopGL:
+ case kGLImplementationEGLGLES2: {
+ return NULL;
+ }
+ case kGLImplementationMockGL:
+ return new GLImageStub;
+ default:
+ NOTREACHED();
+ return NULL;
+ }
+}
+
+} // namespace gfx
diff --git a/ui/gl/gl_surface_glx.cc b/ui/gl/gl_surface_glx.cc
index 8428cfc..6e16754 100644
--- a/ui/gl/gl_surface_glx.cc
+++ b/ui/gl/gl_surface_glx.cc
@@ -36,6 +36,7 @@ class ScopedPtrXFree {
Display* g_display;
const char* g_glx_extensions = NULL;
bool g_glx_create_context_robustness_supported = false;
+bool g_glx_texture_from_pixmap_supported = false;
} // namespace
@@ -66,6 +67,8 @@ bool GLSurfaceGLX::InitializeOneOff() {
g_glx_extensions = glXQueryExtensionsString(g_display, 0);
g_glx_create_context_robustness_supported =
HasGLXExtension("GLX_ARB_create_context_robustness");
+ g_glx_texture_from_pixmap_supported =
+ HasGLXExtension("GLX_EXT_texture_from_pixmap");
initialized = true;
return true;
@@ -86,6 +89,11 @@ bool GLSurfaceGLX::IsCreateContextRobustnessSupported() {
return g_glx_create_context_robustness_supported;
}
+// static
+bool GLSurfaceGLX::IsTextureFromPixmapSupported() {
+ return g_glx_texture_from_pixmap_supported;
+}
+
void* GLSurfaceGLX::GetDisplay() {
return g_display;
}
diff --git a/ui/gl/gl_surface_glx.h b/ui/gl/gl_surface_glx.h
index 644b51b..0dc235c 100644
--- a/ui/gl/gl_surface_glx.h
+++ b/ui/gl/gl_surface_glx.h
@@ -27,6 +27,7 @@ class GL_EXPORT GLSurfaceGLX : public GLSurface {
static const char* GetGLXExtensions();
static bool HasGLXExtension(const char* name);
static bool IsCreateContextRobustnessSupported();
+ static bool IsTextureFromPixmapSupported();
virtual void* GetDisplay() OVERRIDE;