Skip to content

Commit

Permalink
Add GL_TEXTURE_EXTERNAL_OES as supported texture target for CHROMIUM_…
Browse files Browse the repository at this point in the history
…map_image.

This adds GL_TEXTURE_EXTERNAL_OES support for
SharedMemory backed GLImage.
We use an egl image for binding in GLImageShm, and
also update GLImageEGL to use an egl image for its 
"release after use" fallback (required for gpu workaround)

BUG=322780

Review URL: https://codereview.chromium.org/198703002

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@259538 0039d316-1c4b-4281-b951-d872f2087c98
  • Loading branch information
sohan.jyoti@samsung.com committed Mar 26, 2014
1 parent 9dd3ff0 commit 11efdaf
Show file tree
Hide file tree
Showing 5 changed files with 128 additions and 27 deletions.
4 changes: 0 additions & 4 deletions cc/trees/layer_tree_host_impl.cc
Original file line number Diff line number Diff line change
Expand Up @@ -109,14 +109,10 @@ unsigned GetMapImageTextureTarget(cc::ContextProvider* context_provider) {
if (!context_provider)
return GL_TEXTURE_2D;

// TODO(reveman): Determine if GL_TEXTURE_EXTERNAL_OES works well on
// Android before we enable this. crbug.com/322780
#if !defined(OS_ANDROID)
if (context_provider->ContextCapabilities().gpu.egl_image_external)
return GL_TEXTURE_EXTERNAL_OES;
if (context_provider->ContextCapabilities().gpu.texture_rectangle)
return GL_TEXTURE_RECTANGLE_ARB;
#endif

return GL_TEXTURE_2D;
}
Expand Down
68 changes: 47 additions & 21 deletions ui/gl/gl_image_egl.cc
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@

#include "ui/gl/gl_bindings.h"
#include "ui/gl/gl_surface_egl.h"
#include "ui/gl/scoped_binders.h"

namespace gfx {

Expand All @@ -14,8 +15,9 @@ GLImageEGL::GLImageEGL(gfx::Size size)
size_(size),
release_after_use_(false),
in_use_(false),
target_(0) {
}
target_(0),
egl_image_for_unbind_(EGL_NO_IMAGE_KHR),
texture_id_for_unbind_(0) {}

GLImageEGL::~GLImageEGL() {
Destroy();
Expand Down Expand Up @@ -44,18 +46,21 @@ bool GLImageEGL::Initialize(gfx::GpuMemoryBufferHandle buffer) {
}

void GLImageEGL::Destroy() {
if (egl_image_ == EGL_NO_IMAGE_KHR)
return;

EGLBoolean success = eglDestroyImageKHR(
GLSurfaceEGL::GetHardwareDisplay(), egl_image_);
if (egl_image_ != EGL_NO_IMAGE_KHR) {
eglDestroyImageKHR(GLSurfaceEGL::GetHardwareDisplay(), egl_image_);
egl_image_ = EGL_NO_IMAGE_KHR;
}

if (success == EGL_FALSE) {
EGLint error = eglGetError();
LOG(ERROR) << "Error destroying EGLImage: " << error;
if (egl_image_for_unbind_ != EGL_NO_IMAGE_KHR) {
eglDestroyImageKHR(GLSurfaceEGL::GetHardwareDisplay(),
egl_image_for_unbind_);
egl_image_for_unbind_ = EGL_NO_IMAGE_KHR;
}

egl_image_ = EGL_NO_IMAGE_KHR;
if (texture_id_for_unbind_) {
glDeleteTextures(1, &texture_id_for_unbind_);
texture_id_for_unbind_ = 0;
}
}

gfx::Size GLImageEGL::GetSize() {
Expand Down Expand Up @@ -108,16 +113,37 @@ void GLImageEGL::DidUseTexImage() {
if (!release_after_use_)
return;

char zero[4] = { 0, };
glTexImage2D(target_,
0,
GL_RGBA,
1,
1,
0,
GL_RGBA,
GL_UNSIGNED_BYTE,
&zero);
if (egl_image_for_unbind_ == EGL_NO_IMAGE_KHR) {
DCHECK_EQ(0u, texture_id_for_unbind_);
glGenTextures(1, &texture_id_for_unbind_);

{
ScopedTextureBinder texture_binder(GL_TEXTURE_2D, texture_id_for_unbind_);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);

char zero[4] = {0, };
glTexImage2D(
GL_TEXTURE_2D, 0, GL_RGBA, 1, 1, 0, GL_RGBA, GL_UNSIGNED_BYTE, &zero);
}

EGLint attrs[] = {EGL_GL_TEXTURE_LEVEL_KHR, 0, // mip-level.
EGL_IMAGE_PRESERVED_KHR, EGL_TRUE, EGL_NONE};
// Need to pass current EGL rendering context to eglCreateImageKHR for
// target type EGL_GL_TEXTURE_2D_KHR.
egl_image_for_unbind_ = eglCreateImageKHR(
GLSurfaceEGL::GetHardwareDisplay(),
eglGetCurrentContext(),
EGL_GL_TEXTURE_2D_KHR,
reinterpret_cast<EGLClientBuffer>(texture_id_for_unbind_),
attrs);
DCHECK_NE(EGL_NO_IMAGE_KHR, egl_image_for_unbind_)
<< "Error creating EGLImage: " << eglGetError();
}

glEGLImageTargetTexture2DOES(target_, egl_image_for_unbind_);
DCHECK_EQ(static_cast<GLenum>(GL_NO_ERROR), glGetError());
}

void GLImageEGL::WillModifyTexImage() {
Expand Down
2 changes: 2 additions & 0 deletions ui/gl/gl_image_egl.h
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,8 @@ class GL_EXPORT GLImageEGL : public GLImage {
bool release_after_use_;
bool in_use_;
unsigned target_;
EGLImageKHR egl_image_for_unbind_;
GLuint texture_id_for_unbind_;

DISALLOW_COPY_AND_ASSIGN(GLImageEGL);
};
Expand Down
75 changes: 73 additions & 2 deletions ui/gl/gl_image_shm.cc
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,12 @@

#include "base/debug/trace_event.h"
#include "base/process/process_handle.h"
#include "ui/gl/gl_bindings.h"
#include "ui/gl/scoped_binders.h"

#if defined(OS_WIN) || defined(USE_X11) || defined(OS_ANDROID) || \
defined(USE_OZONE)
#include "ui/gl/gl_surface_egl.h"
#endif

namespace gfx {

Expand Down Expand Up @@ -64,7 +69,13 @@ GLenum BytesPerPixel(unsigned internalformat) {

GLImageShm::GLImageShm(gfx::Size size, unsigned internalformat)
: size_(size),
internalformat_(internalformat) {
internalformat_(internalformat)
#if defined(OS_WIN) || defined(USE_X11) || defined(OS_ANDROID) || \
defined(USE_OZONE)
, egl_texture_id_(0u)
, egl_image_(EGL_NO_IMAGE_KHR)
#endif
{
}

GLImageShm::~GLImageShm() {
Expand Down Expand Up @@ -96,6 +107,17 @@ bool GLImageShm::Initialize(gfx::GpuMemoryBufferHandle buffer) {
}

void GLImageShm::Destroy() {
#if defined(OS_WIN) || defined(USE_X11) || defined(OS_ANDROID) || \
defined(USE_OZONE)
if (egl_image_ != EGL_NO_IMAGE_KHR) {
eglDestroyImageKHR(GLSurfaceEGL::GetHardwareDisplay(), egl_image_);
egl_image_ = EGL_NO_IMAGE_KHR;
}
if (egl_texture_id_) {
glDeleteTextures(1, &egl_texture_id_);
egl_texture_id_ = 0u;
}
#endif
}

gfx::Size GLImageShm::GetSize() {
Expand All @@ -115,6 +137,55 @@ bool GLImageShm::BindTexImage(unsigned target) {
}

DCHECK(shared_memory_->memory());

#if defined(OS_WIN) || defined(USE_X11) || defined(OS_ANDROID) || \
defined(USE_OZONE)
if (target == GL_TEXTURE_EXTERNAL_OES) {
if (egl_image_ != EGL_NO_IMAGE_KHR)
eglDestroyImageKHR(GLSurfaceEGL::GetHardwareDisplay(), egl_image_);

if (!egl_texture_id_)
glGenTextures(1, &egl_texture_id_);

{
ScopedTextureBinder texture_binder(GL_TEXTURE_2D, egl_texture_id_);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);

glTexImage2D(GL_TEXTURE_2D,
0, // mip level
TextureFormat(internalformat_),
size_.width(),
size_.height(),
0, // border
DataFormat(internalformat_),
DataType(internalformat_),
shared_memory_->memory());
}

EGLint attrs[] = {EGL_GL_TEXTURE_LEVEL_KHR, 0, // mip-level.
EGL_IMAGE_PRESERVED_KHR, EGL_TRUE, EGL_NONE};
// Need to pass current EGL rendering context to eglCreateImageKHR for
// target type EGL_GL_TEXTURE_2D_KHR.
egl_image_ =
eglCreateImageKHR(GLSurfaceEGL::GetHardwareDisplay(),
eglGetCurrentContext(),
EGL_GL_TEXTURE_2D_KHR,
reinterpret_cast<EGLClientBuffer>(egl_texture_id_),
attrs);
DCHECK_NE(EGL_NO_IMAGE_KHR, egl_image_)
<< "Error creating EGLImage: " << eglGetError();

glEGLImageTargetTexture2DOES(target, egl_image_);
DCHECK_EQ(static_cast<GLenum>(GL_NO_ERROR), glGetError());

shared_memory_->Unmap();
return true;
}
#endif

DCHECK_NE(static_cast<GLenum>(GL_TEXTURE_EXTERNAL_OES), target);
glTexImage2D(target,
0, // mip level
TextureFormat(internalformat_),
Expand Down
6 changes: 6 additions & 0 deletions ui/gl/gl_image_shm.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
#define UI_GL_GL_IMAGE_SHM_H_

#include "base/memory/scoped_ptr.h"
#include "ui/gl/gl_bindings.h"
#include "ui/gl/gl_image.h"

namespace gfx {
Expand Down Expand Up @@ -33,6 +34,11 @@ class GL_EXPORT GLImageShm : public GLImage {
scoped_ptr<base::SharedMemory> shared_memory_;
gfx::Size size_;
unsigned internalformat_;
#if defined(OS_WIN) || defined(USE_X11) || defined(OS_ANDROID) || \
defined(USE_OZONE)
GLuint egl_texture_id_;
EGLImageKHR egl_image_;
#endif

DISALLOW_COPY_AND_ASSIGN(GLImageShm);
};
Expand Down

0 comments on commit 11efdaf

Please sign in to comment.