| Index: ui/gfx/gl/egl_util.h
 | 
| ===================================================================
 | 
| --- ui/gfx/gl/egl_util.h	(revision 80956)
 | 
| +++ ui/gfx/gl/egl_util.h	(working copy)
 | 
| @@ -2,431 +2,14 @@
 | 
|  // Use of this source code is governed by a BSD-style license that can be
 | 
|  // found in the LICENSE file.
 | 
|  
 | 
| +#ifndef UI_GFX_GL_EGL_UTIL_H_
 | 
| +#define UI_GFX_GL_EGL_UTIL_H_
 | 
|  
 | 
| -#include "build/build_config.h"
 | 
| -#include "base/logging.h"
 | 
| -#include "base/memory/scoped_ptr.h"
 | 
| -#include "third_party/angle/include/EGL/egl.h"
 | 
| -#include "ui/gfx/gl/gl_context_egl.h"
 | 
| -
 | 
| -// This header must come after the above third-party include, as
 | 
| -// it brings in #defines that cause conflicts.
 | 
| -#include "ui/gfx/gl/gl_bindings.h"
 | 
| -
 | 
| -#if defined(OS_LINUX)
 | 
| -extern "C" {
 | 
| -#include <X11/Xlib.h>
 | 
| -}
 | 
| -#define EGL_HAS_PBUFFERS 1
 | 
| -#endif
 | 
| -
 | 
|  namespace gfx {
 | 
|  
 | 
| -namespace {
 | 
| -
 | 
| -// The EGL configuration to use.
 | 
| -EGLDisplay g_display;
 | 
| -EGLConfig g_config;
 | 
| -
 | 
|  // Returns the last EGL error as a string.
 | 
| -const char* GetLastEGLErrorString() {
 | 
| -  EGLint error = eglGetError();
 | 
| -  switch (error) {
 | 
| -    case EGL_SUCCESS:
 | 
| -      return "EGL_SUCCESS";
 | 
| -    case EGL_BAD_ACCESS:
 | 
| -      return "EGL_BAD_ACCESS";
 | 
| -    case EGL_BAD_ALLOC:
 | 
| -      return "EGL_BAD_ALLOC";
 | 
| -    case EGL_BAD_ATTRIBUTE:
 | 
| -      return "EGL_BAD_ATTRIBUTE";
 | 
| -    case EGL_BAD_CONTEXT:
 | 
| -      return "EGL_BAD_CONTEXT";
 | 
| -    case EGL_BAD_CONFIG:
 | 
| -      return "EGL_BAD_CONFIG";
 | 
| -    case EGL_BAD_CURRENT_SURFACE:
 | 
| -      return "EGL_BAD_CURRENT_SURFACE";
 | 
| -    case EGL_BAD_DISPLAY:
 | 
| -      return "EGL_BAD_DISPLAY";
 | 
| -    case EGL_BAD_SURFACE:
 | 
| -      return "EGL_BAD_SURFACE";
 | 
| -    case EGL_BAD_MATCH:
 | 
| -      return "EGL_BAD_MATCH";
 | 
| -    case EGL_BAD_PARAMETER:
 | 
| -      return "EGL_BAD_PARAMETER";
 | 
| -    case EGL_BAD_NATIVE_PIXMAP:
 | 
| -      return "EGL_BAD_NATIVE_PIXMAP";
 | 
| -    case EGL_BAD_NATIVE_WINDOW:
 | 
| -      return "EGL_BAD_NATIVE_WINDOW";
 | 
| -    default:
 | 
| -      return "UNKNOWN";
 | 
| -  }
 | 
| -}
 | 
| -}  // namespace anonymous
 | 
| +const char* GetLastEGLErrorString();
 | 
|  
 | 
| -SharedEGLSurface::SharedEGLSurface(EGLSurface surface) : surface_(surface) {
 | 
| -}
 | 
| -
 | 
| -SharedEGLSurface::~SharedEGLSurface() {
 | 
| -  if (surface_) {
 | 
| -    if (!eglDestroySurface(g_display, surface_)) {
 | 
| -      LOG(ERROR) << "eglDestroySurface failed with error "
 | 
| -                 << GetLastEGLErrorString();
 | 
| -    }
 | 
| -  }
 | 
| -}
 | 
| -
 | 
| -EGLSurface SharedEGLSurface::egl_surface() const {
 | 
| -  return surface_;
 | 
| -}
 | 
| -
 | 
| -bool BaseEGLContext::InitializeOneOff() {
 | 
| -  static bool initialized = false;
 | 
| -  if (initialized)
 | 
| -    return true;
 | 
| -
 | 
| -#ifdef OS_LINUX
 | 
| -  EGLNativeDisplayType native_display = XOpenDisplay(NULL);
 | 
| -#else
 | 
| -  EGLNativeDisplayType native_display = EGL_DEFAULT_DISPLAY;
 | 
| -#endif
 | 
| -  g_display = eglGetDisplay(native_display);
 | 
| -  if (!g_display) {
 | 
| -    LOG(ERROR) << "eglGetDisplay failed with error " << GetLastEGLErrorString();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  if (!eglInitialize(g_display, NULL, NULL)) {
 | 
| -    LOG(ERROR) << "eglInitialize failed with error " << GetLastEGLErrorString();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  // Choose an EGL configuration.
 | 
| -  static const EGLint kConfigAttribs[] = {
 | 
| -    EGL_BUFFER_SIZE, 32,
 | 
| -    EGL_ALPHA_SIZE, 8,
 | 
| -    EGL_BLUE_SIZE, 8,
 | 
| -    EGL_RED_SIZE, 8,
 | 
| -    EGL_DEPTH_SIZE, 16,
 | 
| -    EGL_STENCIL_SIZE, 8,
 | 
| -    EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT,
 | 
| -#ifdef EGL_HAS_PBUFFERS
 | 
| -    EGL_SURFACE_TYPE, EGL_WINDOW_BIT | EGL_PBUFFER_BIT,
 | 
| -#else
 | 
| -    EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
 | 
| -#endif
 | 
| -    EGL_NONE
 | 
| -  };
 | 
| -
 | 
| -  EGLint num_configs;
 | 
| -  if (!eglChooseConfig(g_display,
 | 
| -                       kConfigAttribs,
 | 
| -                       NULL,
 | 
| -                       0,
 | 
| -                       &num_configs)) {
 | 
| -    LOG(ERROR) << "eglChooseConfig failed failed with error "
 | 
| -               << GetLastEGLErrorString();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  if (num_configs == 0) {
 | 
| -    LOG(ERROR) << "No suitable EGL configs found.";
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  scoped_array<EGLConfig> configs(new EGLConfig[num_configs]);
 | 
| -  if (!eglChooseConfig(g_display,
 | 
| -                       kConfigAttribs,
 | 
| -                       configs.get(),
 | 
| -                       num_configs,
 | 
| -                       &num_configs)) {
 | 
| -    LOG(ERROR) << "eglChooseConfig failed with error "
 | 
| -               << GetLastEGLErrorString();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  g_config = configs[0];
 | 
| -
 | 
| -  initialized = true;
 | 
| -  return true;
 | 
| -}
 | 
| -
 | 
| -EGLDisplay BaseEGLContext::GetDisplay() {
 | 
| -  return g_display;
 | 
| -}
 | 
| -
 | 
| -std::string BaseEGLContext::GetExtensions() {
 | 
| -  const char* extensions = eglQueryString(g_display, EGL_EXTENSIONS);
 | 
| -  if (!extensions)
 | 
| -    return GLContext::GetExtensions();
 | 
| -
 | 
| -  return GLContext::GetExtensions() + " " + extensions;
 | 
| -}
 | 
| -
 | 
| -NativeViewEGLContext::NativeViewEGLContext(void* window)
 | 
| -    : window_(window),
 | 
| -      context_(NULL)
 | 
| -{
 | 
| -}
 | 
| -
 | 
| -NativeViewEGLContext::~NativeViewEGLContext() {
 | 
| -}
 | 
| -
 | 
| -bool NativeViewEGLContext::Initialize() {
 | 
| -  DCHECK(!context_);
 | 
| -
 | 
| -  // Create a surface for the native window.
 | 
| -  EGLNativeWindowType native_window =
 | 
| -      reinterpret_cast<EGLNativeWindowType>(window_);
 | 
| -  surface_ = new SharedEGLSurface(eglCreateWindowSurface(g_display,
 | 
| -                                                         g_config,
 | 
| -                                                         native_window,
 | 
| -                                                         NULL));
 | 
| -
 | 
| -  if (!surface_->egl_surface()) {
 | 
| -    LOG(ERROR) << "eglCreateWindowSurface failed with error "
 | 
| -               << GetLastEGLErrorString();
 | 
| -    Destroy();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  static const EGLint kContextAttributes[] = {
 | 
| -    EGL_CONTEXT_CLIENT_VERSION, 2,
 | 
| -    EGL_NONE
 | 
| -  };
 | 
| -
 | 
| -  context_ = eglCreateContext(g_display, g_config, NULL, kContextAttributes);
 | 
| -  if (!context_) {
 | 
| -    LOG(ERROR) << "eglCreateContext failed with error "
 | 
| -               << GetLastEGLErrorString();
 | 
| -    Destroy();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  if (!MakeCurrent()) {
 | 
| -    LOG(ERROR) << "MakeCurrent failed.";
 | 
| -    Destroy();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  if (!InitializeCommon()) {
 | 
| -    LOG(ERROR) << "GLContext::InitializeCommon failed.";
 | 
| -    Destroy();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  return true;
 | 
| -}
 | 
| -
 | 
| -void NativeViewEGLContext::Destroy() {
 | 
| -  if (context_) {
 | 
| -    if (!eglDestroyContext(g_display, context_)) {
 | 
| -      LOG(ERROR) << "eglDestroyContext failed with error "
 | 
| -                 << GetLastEGLErrorString();
 | 
| -    }
 | 
| -
 | 
| -    context_ = NULL;
 | 
| -  }
 | 
| -
 | 
| -  surface_ = NULL;
 | 
| -}
 | 
| -
 | 
| -bool NativeViewEGLContext::MakeCurrent() {
 | 
| -  DCHECK(context_);
 | 
| -  if (context_ == eglGetCurrentContext())
 | 
| -      return true;
 | 
| -  if (!eglMakeCurrent(g_display,
 | 
| -                      surface_->egl_surface(),
 | 
| -                      surface_->egl_surface(),
 | 
| -                      context_)) {
 | 
| -    VLOG(1) << "eglMakeCurrent failed with error "
 | 
| -            << GetLastEGLErrorString();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  return true;
 | 
| -}
 | 
| -
 | 
| -bool NativeViewEGLContext::IsCurrent() {
 | 
| -  DCHECK(context_);
 | 
| -  return context_ == eglGetCurrentContext();
 | 
| -}
 | 
| -
 | 
| -bool NativeViewEGLContext::IsOffscreen() {
 | 
| -  return false;
 | 
| -}
 | 
| -
 | 
| -bool NativeViewEGLContext::SwapBuffers() {
 | 
| -  if (!eglSwapBuffers(g_display, surface_->egl_surface())) {
 | 
| -    VLOG(1) << "eglSwapBuffers failed with error "
 | 
| -            << GetLastEGLErrorString();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  return true;
 | 
| -}
 | 
| -
 | 
| -gfx::Size NativeViewEGLContext::GetSize() {
 | 
| -#if defined(OS_WIN)
 | 
| -  RECT rect;
 | 
| -  if (!GetClientRect(static_cast<HWND>(window_), &rect)) {
 | 
| -    DCHECK(false) << "GetClientRect failed.";
 | 
| -    return gfx::Size();
 | 
| -  }
 | 
| -
 | 
| -  return gfx::Size(rect.right - rect.left, rect.bottom - rect.top);
 | 
| -#else
 | 
| -  // TODO(piman): This doesn't work correctly on Windows yet, the size doesn't
 | 
| -  // get updated on resize. When it does, we can share the code.
 | 
| -  EGLint width;
 | 
| -  EGLint height;
 | 
| -  if (!eglQuerySurface(
 | 
| -          g_display, surface_->egl_surface(), EGL_WIDTH, &width) ||
 | 
| -      !eglQuerySurface(
 | 
| -          g_display, surface_->egl_surface(), EGL_HEIGHT, &height)) {
 | 
| -    NOTREACHED() << "eglQuerySurface failed with error "
 | 
| -                 << GetLastEGLErrorString();
 | 
| -    return gfx::Size();
 | 
| -  }
 | 
| -
 | 
| -  return gfx::Size(width, height);
 | 
| -#endif
 | 
| -}
 | 
| -
 | 
| -void* NativeViewEGLContext::GetHandle() {
 | 
| -  return context_;
 | 
| -}
 | 
| -
 | 
| -void NativeViewEGLContext::SetSwapInterval(int interval) {
 | 
| -  DCHECK(IsCurrent());
 | 
| -  if (!eglSwapInterval(g_display, interval)) {
 | 
| -    LOG(ERROR) << "eglSwapInterval failed with error "
 | 
| -               << GetLastEGLErrorString();
 | 
| -  }
 | 
| -}
 | 
| -
 | 
| -SharedEGLSurface* NativeViewEGLContext::GetSurface() {
 | 
| -  return surface_;
 | 
| -}
 | 
| -
 | 
| -SecondaryEGLContext::SecondaryEGLContext()
 | 
| -    : context_(NULL)
 | 
| -{
 | 
| -}
 | 
| -
 | 
| -SecondaryEGLContext::~SecondaryEGLContext() {
 | 
| -}
 | 
| -
 | 
| -bool SecondaryEGLContext::Initialize(GLContext* shared_context) {
 | 
| -  DCHECK(!context_);
 | 
| -
 | 
| -  static const EGLint kContextAttributes[] = {
 | 
| -    EGL_CONTEXT_CLIENT_VERSION, 2,
 | 
| -    EGL_NONE
 | 
| -  };
 | 
| -
 | 
| -  if (shared_context) {
 | 
| -    surface_ = static_cast<BaseEGLContext*>(shared_context)->GetSurface();
 | 
| -
 | 
| -    // Create a context.
 | 
| -    context_ = eglCreateContext(g_display,
 | 
| -                                g_config,
 | 
| -                                shared_context->GetHandle(),
 | 
| -                                kContextAttributes);
 | 
| -  } else {
 | 
| -#ifdef EGL_HAS_PBUFFERS
 | 
| -    static const EGLint kPbufferAttribs[] = {
 | 
| -      EGL_WIDTH, 1,
 | 
| -      EGL_HEIGHT, 1,
 | 
| -      EGL_NONE
 | 
| -    };
 | 
| -
 | 
| -    surface_ = new SharedEGLSurface(eglCreatePbufferSurface(g_display,
 | 
| -                                                            g_config,
 | 
| -                                                            kPbufferAttribs));
 | 
| -    if (!surface_->egl_surface()) {
 | 
| -      LOG(ERROR) << "eglCreatePbufferSurface failed with error "
 | 
| -                 << GetLastEGLErrorString();
 | 
| -      Destroy();
 | 
| -      return false;
 | 
| -    }
 | 
| -
 | 
| -    context_ = eglCreateContext(g_display, g_config, NULL, kContextAttributes);
 | 
| -#else
 | 
| -    NOTIMPLEMENTED() << "Offscreen non-shared GLES context";
 | 
| -    return false;
 | 
| -#endif
 | 
| -  }
 | 
| -
 | 
| -  if (!context_) {
 | 
| -    LOG(ERROR) << "eglCreateContext failed with error "
 | 
| -               << GetLastEGLErrorString();
 | 
| -    Destroy();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  return true;
 | 
| -}
 | 
| -
 | 
| -void SecondaryEGLContext::Destroy() {
 | 
| -  if (context_) {
 | 
| -    if (!eglDestroyContext(g_display, context_)) {
 | 
| -      LOG(ERROR) << "eglDestroyContext failed with error "
 | 
| -                 << GetLastEGLErrorString();
 | 
| -    }
 | 
| -
 | 
| -    context_ = NULL;
 | 
| -  }
 | 
| -
 | 
| -  surface_ = NULL;
 | 
| -}
 | 
| -
 | 
| -bool SecondaryEGLContext::MakeCurrent() {
 | 
| -  DCHECK(context_);
 | 
| -  if (context_ == eglGetCurrentContext())
 | 
| -      return true;
 | 
| -  if (!eglMakeCurrent(g_display,
 | 
| -                      surface_->egl_surface(),
 | 
| -                      surface_->egl_surface(),
 | 
| -                      context_)) {
 | 
| -    VLOG(1) << "eglMakeCurrent failed with error "
 | 
| -            << GetLastEGLErrorString();
 | 
| -    return false;
 | 
| -  }
 | 
| -
 | 
| -  return true;
 | 
| -}
 | 
| -
 | 
| -bool SecondaryEGLContext::IsCurrent() {
 | 
| -  DCHECK(context_);
 | 
| -  return context_ == eglGetCurrentContext();
 | 
| -}
 | 
| -
 | 
| -bool SecondaryEGLContext::IsOffscreen() {
 | 
| -  return true;
 | 
| -}
 | 
| -
 | 
| -bool SecondaryEGLContext::SwapBuffers() {
 | 
| -  NOTREACHED() << "Attempted to call SwapBuffers on a SecondaryEGLContext.";
 | 
| -  return false;
 | 
| -}
 | 
| -
 | 
| -gfx::Size SecondaryEGLContext::GetSize() {
 | 
| -  NOTREACHED() << "Should not be requesting size of this SecondaryEGLContext.";
 | 
| -  return gfx::Size(1, 1);
 | 
| -}
 | 
| -
 | 
| -void* SecondaryEGLContext::GetHandle() {
 | 
| -  return context_;
 | 
| -}
 | 
| -
 | 
| -void SecondaryEGLContext::SetSwapInterval(int interval) {
 | 
| -  DCHECK(IsCurrent());
 | 
| -  NOTREACHED() << "Attempt to call SetSwapInterval on a SecondaryEGLContext.";
 | 
| -}
 | 
| -
 | 
| -SharedEGLSurface* SecondaryEGLContext::GetSurface() {
 | 
| -  return surface_;
 | 
| -}
 | 
| -
 | 
|  }  // namespace gfx
 | 
| +
 | 
| +#endif  // UI_GFX_GL_EGL_UTIL_H_
 | 
| 
 |