Update To 11.40.268.0
[platform/framework/web/crosswalk.git] / src / content / common / gpu / client / gl_helper_scaling.cc
index ee90016..be857b4 100644 (file)
 #include "base/memory/ref_counted.h"
 #include "base/message_loop/message_loop.h"
 #include "base/time/time.h"
-#include "third_party/WebKit/public/platform/WebCString.h"
+#include "gpu/command_buffer/client/gles2_interface.h"
 #include "third_party/skia/include/core/SkRegion.h"
 #include "ui/gfx/rect.h"
 #include "ui/gfx/size.h"
-#include "ui/gl/gl_bindings.h"
 
-using WebKit::WebGLId;
-using WebKit::WebGraphicsContext3D;
+using gpu::gles2::GLES2Interface;
 
 namespace content {
 
-GLHelperScaling::GLHelperScaling(WebKit::WebGraphicsContext3D* context,
-                GLHelper* helper)
-  : context_(context),
-    helper_(helper),
-    vertex_attributes_buffer_(context_, context_->createBuffer()) {
+GLHelperScaling::GLHelperScaling(GLES2Interface* gl, GLHelper* helper)
+    : gl_(gl), helper_(helper), vertex_attributes_buffer_(gl_) {
   InitBuffer();
 }
 
-GLHelperScaling::~GLHelperScaling() {
-}
+GLHelperScaling::~GLHelperScaling() {}
 
 // Used to keep track of a generated shader program. The program
 // is passed in as text through Setup and is used by calling
-// UseProgram() with the right parameters. Note that |context_|
+// UseProgram() with the right parameters. Note that |gl_|
 // and |helper_| are assumed to live longer than this program.
 class ShaderProgram : public base::RefCounted<ShaderProgram> {
  public:
-  ShaderProgram(WebGraphicsContext3D* context,
-                GLHelper* helper)
-      : context_(context),
+  ShaderProgram(GLES2Interface* gl, GLHelper* helper)
+      : gl_(gl),
         helper_(helper),
-        program_(context, context->createProgram()) {
-  }
-
-  // Compile shader program, return true if successful.
-  bool Setup(const WebKit::WGC3Dchar* vertex_shader_text,
-             const WebKit::WGC3Dchar* fragment_shader_text);
+        program_(gl_->CreateProgram()),
+        position_location_(-1),
+        texcoord_location_(-1),
+        src_subrect_location_(-1),
+        src_pixelsize_location_(-1),
+        dst_pixelsize_location_(-1),
+        scaling_vector_location_(-1),
+        color_weights_location_(-1) {}
+
+  // Compile shader program.
+  void Setup(const GLchar* vertex_shader_text,
+             const GLchar* fragment_shader_text);
 
   // UseProgram must be called with GL_TEXTURE_2D bound to the
   // source texture and GL_ARRAY_BUFFER bound to a vertex
@@ -64,47 +63,47 @@ class ShaderProgram : public base::RefCounted<ShaderProgram> {
                   bool flip_y,
                   GLfloat color_weights[4]);
 
+  bool Initialized() const { return position_location_ != -1; }
+
  private:
   friend class base::RefCounted<ShaderProgram>;
-  ~ShaderProgram() {}
+  ~ShaderProgram() { gl_->DeleteProgram(program_); }
 
-  WebGraphicsContext3D* context_;
+  GLES2Interface* gl_;
   GLHelper* helper_;
 
   // A program for copying a source texture into a destination texture.
-  ScopedProgram program_;
+  GLuint program_;
 
   // The location of the position in the program.
-  WebKit::WGC3Dint position_location_;
+  GLint position_location_;
   // The location of the texture coordinate in the program.
-  WebKit::WGC3Dint texcoord_location_;
+  GLint texcoord_location_;
   // The location of the source texture in the program.
-  WebKit::WGC3Dint texture_location_;
+  GLint texture_location_;
   // The location of the texture coordinate of
   // the sub-rectangle in the program.
-  WebKit::WGC3Dint src_subrect_location_;
+  GLint src_subrect_location_;
   // Location of size of source image in pixels.
-  WebKit::WGC3Dint src_pixelsize_location_;
+  GLint src_pixelsize_location_;
   // Location of size of destination image in pixels.
-  WebKit::WGC3Dint dst_pixelsize_location_;
+  GLint dst_pixelsize_location_;
   // Location of vector for scaling direction.
-  WebKit::WGC3Dint scaling_vector_location_;
+  GLint scaling_vector_location_;
   // Location of color weights.
-  WebKit::WGC3Dint color_weights_location_;
+  GLint color_weights_location_;
 
   DISALLOW_COPY_AND_ASSIGN(ShaderProgram);
 };
 
-
 // Implementation of a single stage in a scaler pipeline. If the pipeline has
 // multiple stages, it calls Scale() on the subscaler, then further scales the
 // output. Caches textures and framebuffers to avoid allocating/deleting
 // them once per frame, which can be expensive on some drivers.
-class ScalerImpl :
-      public GLHelper::ScalerInterface,
-      public GLHelperScaling::ShaderInterface {
+class ScalerImpl : public GLHelper::ScalerInterface,
+                   public GLHelperScaling::ShaderInterface {
  public:
-  // |context| and |copy_impl| are expected to live longer than this object.
+  // |gl| and |copy_impl| are expected to live longer than this object.
   // |src_size| is the size of the input texture in pixels.
   // |dst_size| is the size of the output texutre in pixels.
   // |src_subrect| is the portion of the src to copy to the output texture.
@@ -114,17 +113,17 @@ class ScalerImpl :
   // If |swizzle| is true, RGBA will be transformed into BGRA.
   // |color_weights| are only used together with SHADER_PLANAR to specify
   //   how to convert RGB colors into a single value.
-  ScalerImpl(WebGraphicsContext3D* context,
+  ScalerImpl(GLES2Interface* gl,
              GLHelperScaling* scaler_helper,
-             const GLHelperScaling::ScalerStage &scaler_stage,
+             const GLHelperScaling::ScalerStagescaler_stage,
              ScalerImpl* subscaler,
-             const float* color_weights) :
-      context_(context),
-      scaler_helper_(scaler_helper),
-      spec_(scaler_stage),
-      intermediate_texture_(0),
-      dst_framebuffer_(context, context_->createFramebuffer()),
-      subscaler_(subscaler) {
+             const float* color_weights)
+      : gl_(gl),
+        scaler_helper_(scaler_helper),
+        spec_(scaler_stage),
+        intermediate_texture_(0),
+        dst_framebuffer_(gl),
+        subscaler_(subscaler) {
     if (color_weights) {
       color_weights_[0] = color_weights[0];
       color_weights_[1] = color_weights[1];
@@ -136,144 +135,130 @@ class ScalerImpl :
       color_weights_[2] = 0.0;
       color_weights_[3] = 0.0;
     }
-    shader_program_ = scaler_helper_->GetShaderProgram(spec_.shader,
-                                                       spec_.swizzle);
+    shader_program_ =
+        scaler_helper_->GetShaderProgram(spec_.shader, spec_.swizzle);
 
     if (subscaler_) {
-      intermediate_texture_ = context_->createTexture();
-      ScopedTextureBinder<GL_TEXTURE_2D> texture_binder(
-          context_,
-          intermediate_texture_);
-      context_->texImage2D(GL_TEXTURE_2D,
-                           0,
-                           GL_RGBA,
-                           spec_.src_size.width(),
-                           spec_.src_size.height(),
-                           0,
-                           GL_RGBA,
-                           GL_UNSIGNED_BYTE,
-                           NULL);
+      intermediate_texture_ = 0u;
+      gl_->GenTextures(1, &intermediate_texture_);
+      ScopedTextureBinder<GL_TEXTURE_2D> texture_binder(gl_,
+                                                        intermediate_texture_);
+      gl_->TexImage2D(GL_TEXTURE_2D,
+                      0,
+                      GL_RGBA,
+                      spec_.src_size.width(),
+                      spec_.src_size.height(),
+                      0,
+                      GL_RGBA,
+                      GL_UNSIGNED_BYTE,
+                      NULL);
     }
   }
 
-  virtual ~ScalerImpl() {
+  ~ScalerImpl() override {
     if (intermediate_texture_) {
-      context_->deleteTexture(intermediate_texture_);
+      gl_->DeleteTextures(1, &intermediate_texture_);
     }
   }
 
   // GLHelperShader::ShaderInterface implementation.
-  virtual void Execute(
-      WebKit::WebGLId source_texture,
-      const std::vector<WebKit::WebGLId>& dest_textures) OVERRIDE {
+  void Execute(GLuint source_texture,
+               const std::vector<GLuint>& dest_textures) override {
     if (subscaler_) {
       subscaler_->Scale(source_texture, intermediate_texture_);
       source_texture = intermediate_texture_;
     }
 
     ScopedFramebufferBinder<GL_FRAMEBUFFER> framebuffer_binder(
-        context_,
-        dst_framebuffer_);
+        gl_, dst_framebuffer_);
     DCHECK_GT(dest_textures.size(), 0U);
-    scoped_ptr<WebKit::WGC3Denum[]> buffers(
-        new WebKit::WGC3Denum[dest_textures.size()]);
+    scoped_ptr<GLenum[]> buffers(new GLenum[dest_textures.size()]);
     for (size_t t = 0; t < dest_textures.size(); t++) {
-      ScopedTextureBinder<GL_TEXTURE_2D> texture_binder(context_,
-                                                        dest_textures[t]);
-      context_->framebufferTexture2D(GL_FRAMEBUFFER,
-                                     GL_COLOR_ATTACHMENT0 + t,
-                                     GL_TEXTURE_2D,
-                                     dest_textures[t],
-                                     0);
+      ScopedTextureBinder<GL_TEXTURE_2D> texture_binder(gl_, dest_textures[t]);
+      gl_->FramebufferTexture2D(GL_FRAMEBUFFER,
+                                GL_COLOR_ATTACHMENT0 + t,
+                                GL_TEXTURE_2D,
+                                dest_textures[t],
+                                0);
       buffers[t] = GL_COLOR_ATTACHMENT0 + t;
     }
-    ScopedTextureBinder<GL_TEXTURE_2D> texture_binder(context_,
-                                                      source_texture);
-
-    context_->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER,
-                            GL_LINEAR);
-    context_->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
-                            GL_LINEAR);
-    context_->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S,
-                            GL_CLAMP_TO_EDGE);
-    context_->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T,
-                            GL_CLAMP_TO_EDGE);
+    ScopedTextureBinder<GL_TEXTURE_2D> texture_binder(gl_, source_texture);
+
+    gl_->TexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
+    gl_->TexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
+    gl_->TexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
+    gl_->TexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
 
     ScopedBufferBinder<GL_ARRAY_BUFFER> buffer_binder(
-        context_,
-        scaler_helper_->vertex_attributes_buffer_);
+        gl_, scaler_helper_->vertex_attributes_buffer_);
+    DCHECK(shader_program_->Initialized());
     shader_program_->UseProgram(spec_.src_size,
                                 spec_.src_subrect,
                                 spec_.dst_size,
                                 spec_.scale_x,
                                 spec_.vertically_flip_texture,
                                 color_weights_);
-    context_->viewport(0, 0, spec_.dst_size.width(), spec_.dst_size.height());
+    gl_->Viewport(0, 0, spec_.dst_size.width(), spec_.dst_size.height());
 
     if (dest_textures.size() > 1) {
       DCHECK_LE(static_cast<int>(dest_textures.size()),
                 scaler_helper_->helper_->MaxDrawBuffers());
-      context_->drawBuffersEXT(dest_textures.size(), buffers.get());
+      gl_->DrawBuffersEXT(dest_textures.size(), buffers.get());
     }
     // Conduct texture mapping by drawing a quad composed of two triangles.
-    context_->drawArrays(GL_TRIANGLE_STRIP, 0, 4);
+    gl_->DrawArrays(GL_TRIANGLE_STRIP, 0, 4);
     if (dest_textures.size() > 1) {
       // Set the draw buffers back to not confuse others.
-      context_->drawBuffersEXT(1, &buffers[0]);
+      gl_->DrawBuffersEXT(1, &buffers[0]);
     }
   }
 
   // GLHelper::ScalerInterface implementation.
-  virtual void Scale(WebKit::WebGLId source_texture,
-                     WebKit::WebGLId dest_texture) OVERRIDE {
-    std::vector<WebKit::WebGLId> tmp(1);
+  void Scale(GLuint source_texture, GLuint dest_texture) override {
+    std::vector<GLuint> tmp(1);
     tmp[0] = dest_texture;
     Execute(source_texture, tmp);
   }
 
-  virtual const gfx::Size& SrcSize() OVERRIDE {
+  const gfx::Size& SrcSize() override {
     if (subscaler_) {
       return subscaler_->SrcSize();
     }
     return spec_.src_size;
   }
-  virtual const gfx::Rect& SrcSubrect() OVERRIDE {
+  const gfx::Rect& SrcSubrect() override {
     if (subscaler_) {
       return subscaler_->SrcSubrect();
     }
     return spec_.src_subrect;
   }
-  virtual const gfx::Size& DstSize() OVERRIDE {
-    return spec_.dst_size;
-  }
+  const gfx::Size& DstSize() override { return spec_.dst_size; }
 
  private:
-  WebGraphicsContext3D* context_;
+  GLES2Interface* gl_;
   GLHelperScaling* scaler_helper_;
   GLHelperScaling::ScalerStage spec_;
   GLfloat color_weights_[4];
-  WebKit::WebGLId intermediate_texture_;
+  GLuint intermediate_texture_;
   scoped_refptr<ShaderProgram> shader_program_;
   ScopedFramebuffer dst_framebuffer_;
   scoped_ptr<ScalerImpl> subscaler_;
 };
 
-GLHelperScaling::ScalerStage::ScalerStage(
-    ShaderType shader_,
-    gfx::Size src_size_,
-    gfx::Rect src_subrect_,
-    gfx::Size dst_size_,
-    bool scale_x_,
-    bool vertically_flip_texture_,
-    bool swizzle_)
+GLHelperScaling::ScalerStage::ScalerStage(ShaderType shader_,
+                                          gfx::Size src_size_,
+                                          gfx::Rect src_subrect_,
+                                          gfx::Size dst_size_,
+                                          bool scale_x_,
+                                          bool vertically_flip_texture_,
+                                          bool swizzle_)
     : shader(shader_),
       src_size(src_size_),
       src_subrect(src_subrect_),
       dst_size(dst_size_),
       scale_x(scale_x_),
       vertically_flip_texture(vertically_flip_texture_),
-      swizzle(swizzle_) {
-}
+      swizzle(swizzle_) {}
 
 // The important inputs for this function is |x_ops| and
 // |y_ops|. They represent scaling operations to be done
@@ -295,7 +280,7 @@ void GLHelperScaling::ConvertScalerOpsToScalerStages(
     bool swizzle,
     std::deque<GLHelperScaling::ScaleOp>* x_ops,
     std::deque<GLHelperScaling::ScaleOp>* y_ops,
-    std::vector<ScalerStage> *scaler_stages) {
+    std::vector<ScalerStage>scaler_stages) {
   while (!x_ops->empty() || !y_ops->empty()) {
     gfx::Size intermediate_size = src_subrect.size();
     std::deque<ScaleOp>* current_queue = NULL;
@@ -354,8 +339,7 @@ void GLHelperScaling::ConvertScalerOpsToScalerStages(
       // * N bilinear Y-passes with 1 bilinear X-pass (down only)
       // Measurements indicate that generalizing this for 3x3 and 4x4
       // makes it slower on some platforms, such as the Pixel.
-      if (!scale_x && x_ops->size() > 0 &&
-          x_ops->front().scale_factor <= 2) {
+      if (!scale_x && x_ops->size() > 0 && x_ops->front().scale_factor <= 2) {
         int x_passes = 0;
         if (current_shader == SHADER_BILINEAR2 && x_ops->size() >= 2) {
           // 2y + 2x passes
@@ -415,7 +399,7 @@ void GLHelperScaling::ComputeScalerStages(
     const gfx::Size& dst_size,
     bool vertically_flip_texture,
     bool swizzle,
-    std::vector<ScalerStage> *scaler_stages) {
+    std::vector<ScalerStage>scaler_stages) {
   if (quality == GLHelper::SCALER_QUALITY_FAST ||
       src_subrect.size() == dst_size) {
     scaler_stages->push_back(ScalerStage(SHADER_BILINEAR,
@@ -440,25 +424,24 @@ void GLHelperScaling::ComputeScalerStages(
                                    quality == GLHelper::SCALER_QUALITY_GOOD,
                                    &y_ops);
 
-  ConvertScalerOpsToScalerStages(
-      quality,
-      src_size,
-      src_subrect,
-      dst_size,
-      vertically_flip_texture,
-      swizzle,
-      &x_ops,
-      &y_ops,
-      scaler_stages);
+  ConvertScalerOpsToScalerStages(quality,
+                                 src_size,
+                                 src_subrect,
+                                 dst_size,
+                                 vertically_flip_texture,
+                                 swizzle,
+                                 &x_ops,
+                                 &y_ops,
+                                 scaler_stages);
 }
 
-GLHelper::ScalerInterface*
-GLHelperScaling::CreateScaler(GLHelper::ScalerQuality quality,
-                              gfx::Size src_size,
-                              gfx::Rect src_subrect,
-                              const gfx::Size& dst_size,
-                              bool vertically_flip_texture,
-                              bool swizzle) {
+GLHelper::ScalerInterface* GLHelperScaling::CreateScaler(
+    GLHelper::ScalerQuality quality,
+    gfx::Size src_size,
+    gfx::Rect src_subrect,
+    const gfx::Size& dst_size,
+    bool vertically_flip_texture,
+    bool swizzle) {
   std::vector<ScalerStage> scaler_stages;
   ComputeScalerStages(quality,
                       src_size,
@@ -470,17 +453,17 @@ GLHelperScaling::CreateScaler(GLHelper::ScalerQuality quality,
 
   ScalerImpl* ret = NULL;
   for (unsigned int i = 0; i < scaler_stages.size(); i++) {
-    ret = new ScalerImpl(context_, this, scaler_stages[i], ret, NULL);
+    ret = new ScalerImpl(gl_, this, scaler_stages[i], ret, NULL);
   }
   return ret;
 }
 
-GLHelper::ScalerInterface*
-GLHelperScaling::CreatePlanarScaler(
+GLHelper::ScalerInterface* GLHelperScaling::CreatePlanarScaler(
     const gfx::Size& src_size,
     const gfx::Rect& src_subrect,
     const gfx::Size& dst_size,
     bool vertically_flip_texture,
+    bool swizzle,
     const float color_weights[4]) {
   ScalerStage stage(SHADER_PLANAR,
                     src_size,
@@ -488,16 +471,16 @@ GLHelperScaling::CreatePlanarScaler(
                     dst_size,
                     true,
                     vertically_flip_texture,
-                    false);
-  return new ScalerImpl(context_, this, stage, NULL, color_weights);
+                    swizzle);
+  return new ScalerImpl(gl_, this, stage, NULL, color_weights);
 }
 
-GLHelperScaling::ShaderInterface*
-GLHelperScaling::CreateYuvMrtShader(
+GLHelperScaling::ShaderInterface* GLHelperScaling::CreateYuvMrtShader(
     const gfx::Size& src_size,
     const gfx::Rect& src_subrect,
     const gfx::Size& dst_size,
     bool vertically_flip_texture,
+    bool swizzle,
     ShaderType shader) {
   DCHECK(shader == SHADER_YUV_MRT_PASS1 || shader == SHADER_YUV_MRT_PASS2);
   ScalerStage stage(shader,
@@ -506,39 +489,37 @@ GLHelperScaling::CreateYuvMrtShader(
                     dst_size,
                     true,
                     vertically_flip_texture,
-                    false);
-  return new ScalerImpl(context_, this, stage, NULL, NULL);
+                    swizzle);
+  return new ScalerImpl(gl_, this, stage, NULL, NULL);
 }
 
-const WebKit::WGC3Dfloat GLHelperScaling::kVertexAttributes[] = {
-  -1.0f, -1.0f, 0.0f, 0.0f,
-  1.0f, -1.0f, 1.0f, 0.0f,
-  -1.0f, 1.0f, 0.0f, 1.0f,
-  1.0f, 1.0f, 1.0f, 1.0f,
-};
+const GLfloat GLHelperScaling::kVertexAttributes[] = {
+    -1.0f, -1.0f, 0.0f, 0.0f,     // vertex 0
+    1.0f,  -1.0f, 1.0f, 0.0f,     // vertex 1
+    -1.0f, 1.0f,  0.0f, 1.0f,     // vertex 2
+    1.0f,  1.0f,  1.0f, 1.0f, };  // vertex 3
 
 void GLHelperScaling::InitBuffer() {
-  ScopedBufferBinder<GL_ARRAY_BUFFER> buffer_binder(
-      context_, vertex_attributes_buffer_);
-  context_->bufferData(GL_ARRAY_BUFFER,
-                       sizeof(kVertexAttributes),
-                       kVertexAttributes,
-                       GL_STATIC_DRAW);
+  ScopedBufferBinder<GL_ARRAY_BUFFER> buffer_binder(gl_,
+                                                    vertex_attributes_buffer_);
+  gl_->BufferData(GL_ARRAY_BUFFER,
+                  sizeof(kVertexAttributes),
+                  kVertexAttributes,
+                  GL_STATIC_DRAW);
 }
 
-scoped_refptr<ShaderProgram>
-GLHelperScaling::GetShaderProgram(ShaderType type,
-                                  bool swizzle) {
+scoped_refptr<ShaderProgram> GLHelperScaling::GetShaderProgram(ShaderType type,
+                                                               bool swizzle) {
   ShaderProgramKeyType key(type, swizzle);
   scoped_refptr<ShaderProgram>& cache_entry(shader_programs_[key]);
   if (!cache_entry.get()) {
-    cache_entry = new ShaderProgram(context_, helper_);
-    std::basic_string<WebKit::WGC3Dchar> vertex_program;
-    std::basic_string<WebKit::WGC3Dchar> fragment_program;
-    std::basic_string<WebKit::WGC3Dchar> vertex_header;
-    std::basic_string<WebKit::WGC3Dchar> fragment_directives;
-    std::basic_string<WebKit::WGC3Dchar> fragment_header;
-    std::basic_string<WebKit::WGC3Dchar> shared_variables;
+    cache_entry = new ShaderProgram(gl_, helper_);
+    std::basic_string<GLchar> vertex_program;
+    std::basic_string<GLchar> fragment_program;
+    std::basic_string<GLchar> vertex_header;
+    std::basic_string<GLchar> fragment_directives;
+    std::basic_string<GLchar> fragment_header;
+    std::basic_string<GLchar> shared_variables;
 
     vertex_header.append(
         "precision highp float;\n"
@@ -606,8 +587,7 @@ GLHelperScaling::GetShaderProgram(ShaderType type,
       case SHADER_BILINEAR4:
         // This is equivialent to three passes of the BILINEAR shader above,
         // It can be used to scale an image down 2.0x-4.0x or exactly 8x.
-        shared_variables.append(
-            "varying vec4 v_texcoords[2];\n");
+        shared_variables.append("varying vec4 v_texcoords[2];\n");
         vertex_header.append(
             "uniform vec2 scaling_vector;\n"
             "uniform vec2 dst_pixelsize;\n");
@@ -631,10 +611,8 @@ GLHelperScaling::GetShaderProgram(ShaderType type,
         // Two in each dimension. It can be used to scale an image down
         // 1.0x-2.0x in both X and Y directions. Or, it could be used to
         // scale an image down by exactly 4x in both dimensions.
-        shared_variables.append(
-            "varying vec4 v_texcoords[2];\n");
-        vertex_header.append(
-            "uniform vec2 dst_pixelsize;\n");
+        shared_variables.append("varying vec4 v_texcoords[2];\n");
+        vertex_header.append("uniform vec2 dst_pixelsize;\n");
         vertex_program.append(
             "  vec2 step = src_subrect.zw / 4.0 / dst_pixelsize;\n"
             "  v_texcoords[0].xy = texcoord + vec2(step.x, step.y);\n"
@@ -678,7 +656,7 @@ GLHelperScaling::GetShaderProgram(ShaderType type,
             "      (texture2D(s_texture, v_texcoords[0].zw) +\n"
             "       texture2D(s_texture, v_texcoords[1].xy)) *\n"
             "          CenterWeight;\n");
-         break;
+        break;
 
       case SHADER_BICUBIC_UPSCALE:
         // When scaling up, we need 4 texture reads, but we can
@@ -687,10 +665,8 @@ GLHelperScaling::GetShaderProgram(ShaderType type,
         // will be in.
         // Also, when sampling the bicubic function like this, the sum
         // is always exactly one, so we can skip normalization as well.
-        shared_variables.append(
-            "varying vec2 v_texcoord;\n");
-        vertex_program.append(
-            "  v_texcoord = texcoord;\n");
+        shared_variables.append("varying vec2 v_texcoord;\n");
+        vertex_program.append("  v_texcoord = texcoord;\n");
         fragment_header.append(
             "uniform vec2 src_pixelsize;\n"
             "uniform vec2 scaling_vector;\n"
@@ -728,8 +704,7 @@ GLHelperScaling::GetShaderProgram(ShaderType type,
         // convert RGBA textures into Y, U and V textures. We do this
         // because single-component textures are not renderable on all
         // architectures.
-        shared_variables.append(
-            "varying vec4 v_texcoords[2];\n");
+        shared_variables.append("varying vec4 v_texcoords[2];\n");
         vertex_header.append(
             "uniform vec2 scaling_vector;\n"
             "uniform vec2 dst_pixelsize;\n");
@@ -740,16 +715,13 @@ GLHelperScaling::GetShaderProgram(ShaderType type,
             "  v_texcoords[0].zw = texcoord - step * 0.5;\n"
             "  v_texcoords[1].xy = texcoord + step * 0.5;\n"
             "  v_texcoords[1].zw = texcoord + step * 1.5;\n");
-        fragment_header.append(
-            "uniform vec4 color_weights;\n");
+        fragment_header.append("uniform vec4 color_weights;\n");
         fragment_program.append(
             "  gl_FragColor = color_weights * mat4(\n"
             "    vec4(texture2D(s_texture, v_texcoords[0].xy).rgb, 1.0),\n"
             "    vec4(texture2D(s_texture, v_texcoords[0].zw).rgb, 1.0),\n"
             "    vec4(texture2D(s_texture, v_texcoords[1].xy).rgb, 1.0),\n"
             "    vec4(texture2D(s_texture, v_texcoords[1].zw).rgb, 1.0));\n");
-        // Swizzle makes no sense for this shader.
-        DCHECK(!swizzle);
         break;
 
       case SHADER_YUV_MRT_PASS1:
@@ -778,8 +750,7 @@ GLHelperScaling::GetShaderProgram(ShaderType type,
         //     pass                     +--> { UUUU + VVVV }
         //                                     UUUU   VVVV
         //
-        shared_variables.append(
-            "varying vec4 v_texcoords[2];\n");
+        shared_variables.append("varying vec4 v_texcoords[2];\n");
         vertex_header.append(
             "uniform vec2 scaling_vector;\n"
             "uniform vec2 dst_pixelsize;\n");
@@ -790,8 +761,7 @@ GLHelperScaling::GetShaderProgram(ShaderType type,
             "  v_texcoords[0].zw = texcoord - step * 0.5;\n"
             "  v_texcoords[1].xy = texcoord + step * 0.5;\n"
             "  v_texcoords[1].zw = texcoord + step * 1.5;\n");
-        fragment_directives.append(
-            "#extension GL_EXT_draw_buffers : enable\n");
+        fragment_directives.append("#extension GL_EXT_draw_buffers : enable\n");
         fragment_header.append(
             "const vec3 kRGBtoY = vec3(0.257, 0.504, 0.098);\n"
             "const float kYBias = 0.0625;\n"
@@ -814,16 +784,13 @@ GLHelperScaling::GetShaderProgram(ShaderType type,
             "                        dot(pixel34, kRGBtoU),\n"
             "                        dot(pixel12, kRGBtoV),\n"
             "                        dot(pixel34, kRGBtoV)) + kUVBias;\n");
-        // Swizzle makes no sense for this shader.
-        DCHECK(!swizzle);
         break;
 
       case SHADER_YUV_MRT_PASS2:
         // We're just sampling two pixels and unswizzling them.  There's
         // no need to do vertical scaling with math, since bilinear
         // interpolation in the sampler takes care of that.
-        shared_variables.append(
-            "varying vec4 v_texcoords;\n");
+        shared_variables.append("varying vec4 v_texcoords;\n");
         vertex_header.append(
             "uniform vec2 scaling_vector;\n"
             "uniform vec2 dst_pixelsize;\n");
@@ -832,136 +799,131 @@ GLHelperScaling::GetShaderProgram(ShaderType type,
             "  step /= 2.0;\n"
             "  v_texcoords.xy = texcoord - step * 0.5;\n"
             "  v_texcoords.zw = texcoord + step * 0.5;\n");
-        fragment_directives.append(
-            "#extension GL_EXT_draw_buffers : enable\n");
+        fragment_directives.append("#extension GL_EXT_draw_buffers : enable\n");
         fragment_program.append(
             "  vec4 lo_uuvv = texture2D(s_texture, v_texcoords.xy);\n"
             "  vec4 hi_uuvv = texture2D(s_texture, v_texcoords.zw);\n"
             "  gl_FragData[0] = vec4(lo_uuvv.rg, hi_uuvv.rg);\n"
             "  gl_FragData[1] = vec4(lo_uuvv.ba, hi_uuvv.ba);\n");
-        // Swizzle makes no sense for this shader.
-        DCHECK(!swizzle);
         break;
     }
     if (swizzle) {
-      fragment_program.append("  gl_FragColor = gl_FragColor.bgra;\n");
+      switch(type) {
+        case SHADER_YUV_MRT_PASS1:
+          fragment_program.append("  gl_FragData[0] = gl_FragData[0].bgra;\n");
+          break;
+        case SHADER_YUV_MRT_PASS2:
+          fragment_program.append("  gl_FragData[0] = gl_FragData[0].bgra;\n");
+          fragment_program.append("  gl_FragData[1] = gl_FragData[1].bgra;\n");
+          break;
+        default:
+          fragment_program.append("  gl_FragColor = gl_FragColor.bgra;\n");
+          break;
+      }
     }
 
-    vertex_program =
-        vertex_header +
-        shared_variables +
-        "void main() {\n" +
-        vertex_program +
-        "}\n";
-
-    fragment_program =
-        fragment_directives +
-        fragment_header +
-        shared_variables +
-        "void main() {\n" +
-        fragment_program +
-        "}\n";
-
-    bool result = cache_entry->Setup(vertex_program.c_str(),
-                                     fragment_program.c_str());
-    DCHECK(result || context_->isContextLost())
-        << "vertex_program =\n" << vertex_program
-        << "fragment_program =\n" << fragment_program;
+    vertex_program = vertex_header + shared_variables + "void main() {\n" +
+                     vertex_program + "}\n";
+
+    fragment_program = fragment_directives + fragment_header +
+                       shared_variables + "void main() {\n" + fragment_program +
+                       "}\n";
+
+    cache_entry->Setup(vertex_program.c_str(), fragment_program.c_str());
   }
   return cache_entry;
 }
 
-bool ShaderProgram::Setup(const WebKit::WGC3Dchar* vertex_shader_text,
-                          const WebKit::WGC3Dchar* fragment_shader_text) {
+void ShaderProgram::Setup(const GLchar* vertex_shader_text,
+                          const GLchar* fragment_shader_text) {
   // Shaders to map the source texture to |dst_texture_|.
-  ScopedShader vertex_shader(context_, helper_->CompileShaderFromSource(
-      vertex_shader_text, GL_VERTEX_SHADER));
-  if (vertex_shader.id() == 0) {
-    return false;
-  }
-  context_->attachShader(program_, vertex_shader);
-  ScopedShader fragment_shader(context_, helper_->CompileShaderFromSource(
-      fragment_shader_text, GL_FRAGMENT_SHADER));
-  if (fragment_shader.id() == 0) {
-    return false;
-  }
-  context_->attachShader(program_, fragment_shader);
-  context_->linkProgram(program_);
-
-  WebKit::WGC3Dint link_status = 0;
-  context_->getProgramiv(program_, GL_LINK_STATUS, &link_status);
-  if (!link_status) {
-    LOG(ERROR) << std::string(context_->getProgramInfoLog(program_).utf8());
-    return false;
-  }
-  position_location_ = context_->getAttribLocation(program_, "a_position");
-  texcoord_location_ = context_->getAttribLocation(program_, "a_texcoord");
-  texture_location_ = context_->getUniformLocation(program_, "s_texture");
-  src_subrect_location_ = context_->getUniformLocation(program_, "src_subrect");
-  src_pixelsize_location_ = context_->getUniformLocation(program_,
-                                                         "src_pixelsize");
-  dst_pixelsize_location_ = context_->getUniformLocation(program_,
-                                                         "dst_pixelsize");
-  scaling_vector_location_ = context_->getUniformLocation(program_,
-                                                          "scaling_vector");
-  color_weights_location_ = context_->getUniformLocation(program_,
-                                                         "color_weights");
-  return true;
+  GLuint vertex_shader =
+      helper_->CompileShaderFromSource(vertex_shader_text, GL_VERTEX_SHADER);
+  if (vertex_shader == 0)
+    return;
+
+  gl_->AttachShader(program_, vertex_shader);
+  gl_->DeleteShader(vertex_shader);
+
+  GLuint fragment_shader = helper_->CompileShaderFromSource(
+      fragment_shader_text, GL_FRAGMENT_SHADER);
+  if (fragment_shader == 0)
+    return;
+  gl_->AttachShader(program_, fragment_shader);
+  gl_->DeleteShader(fragment_shader);
+
+  gl_->LinkProgram(program_);
+
+  GLint link_status = 0;
+  gl_->GetProgramiv(program_, GL_LINK_STATUS, &link_status);
+  if (!link_status)
+    return;
+
+  position_location_ = gl_->GetAttribLocation(program_, "a_position");
+  texcoord_location_ = gl_->GetAttribLocation(program_, "a_texcoord");
+  texture_location_ = gl_->GetUniformLocation(program_, "s_texture");
+  src_subrect_location_ = gl_->GetUniformLocation(program_, "src_subrect");
+  src_pixelsize_location_ = gl_->GetUniformLocation(program_, "src_pixelsize");
+  dst_pixelsize_location_ = gl_->GetUniformLocation(program_, "dst_pixelsize");
+  scaling_vector_location_ =
+      gl_->GetUniformLocation(program_, "scaling_vector");
+  color_weights_location_ = gl_->GetUniformLocation(program_, "color_weights");
+  return;
 }
 
-void ShaderProgram::UseProgram(
-    const gfx::Size& src_size,
-    const gfx::Rect& src_subrect,
-    const gfx::Size& dst_size,
-    bool scale_x,
-    bool flip_y,
-    GLfloat color_weights[4]) {
-  context_->useProgram(program_);
-
-  WebKit::WGC3Dintptr offset = 0;
-  context_->vertexAttribPointer(position_location_,
-                                2,
-                                GL_FLOAT,
-                                GL_FALSE,
-                                4 * sizeof(WebKit::WGC3Dfloat),
-                                offset);
-  context_->enableVertexAttribArray(position_location_);
-
-  offset += 2 * sizeof(WebKit::WGC3Dfloat);
-  context_->vertexAttribPointer(texcoord_location_,
-                                2,
-                                GL_FLOAT,
-                                GL_FALSE,
-                                4 * sizeof(WebKit::WGC3Dfloat),
-                                offset);
-  context_->enableVertexAttribArray(texcoord_location_);
-
-  context_->uniform1i(texture_location_, 0);
+void ShaderProgram::UseProgram(const gfx::Size& src_size,
+                               const gfx::Rect& src_subrect,
+                               const gfx::Size& dst_size,
+                               bool scale_x,
+                               bool flip_y,
+                               GLfloat color_weights[4]) {
+  gl_->UseProgram(program_);
+
+  // OpenGL defines the last parameter to VertexAttribPointer as type
+  // "const GLvoid*" even though it is actually an offset into the buffer
+  // object's data store and not a pointer to the client's address space.
+  const void* offsets[2] = {
+      0, reinterpret_cast<const void*>(2 * sizeof(GLfloat))
+  };
+
+  gl_->VertexAttribPointer(position_location_,
+                           2,
+                           GL_FLOAT,
+                           GL_FALSE,
+                           4 * sizeof(GLfloat),
+                           offsets[0]);
+  gl_->EnableVertexAttribArray(position_location_);
+
+  gl_->VertexAttribPointer(texcoord_location_,
+                           2,
+                           GL_FLOAT,
+                           GL_FALSE,
+                           4 * sizeof(GLfloat),
+                           offsets[1]);
+  gl_->EnableVertexAttribArray(texcoord_location_);
+
+  gl_->Uniform1i(texture_location_, 0);
 
   // Convert |src_subrect| to texture coordinates.
   GLfloat src_subrect_texcoord[] = {
-    static_cast<float>(src_subrect.x()) / src_size.width(),
-    static_cast<float>(src_subrect.y()) / src_size.height(),
-    static_cast<float>(src_subrect.width()) / src_size.width(),
-    static_cast<float>(src_subrect.height()) / src_size.height(),
-  };
+      static_cast<float>(src_subrect.x()) / src_size.width(),
+      static_cast<float>(src_subrect.y()) / src_size.height(),
+      static_cast<float>(src_subrect.width()) / src_size.width(),
+      static_cast<float>(src_subrect.height()) / src_size.height(), };
   if (flip_y) {
     src_subrect_texcoord[1] += src_subrect_texcoord[3];
     src_subrect_texcoord[3] *= -1.0;
   }
-  context_->uniform4fv(src_subrect_location_, 1, src_subrect_texcoord);
-
-  context_->uniform2f(src_pixelsize_location_,
-                      src_size.width(),
-                      src_size.height());
-  context_->uniform2f(dst_pixelsize_location_,
-                      static_cast<float>(dst_size.width()),
-                      static_cast<float>(dst_size.height()));
-
-  context_->uniform2f(scaling_vector_location_,
-                      scale_x ? 1.0 : 0.0,
-                      scale_x ? 0.0 : 1.0);
-  context_->uniform4fv(color_weights_location_, 1, color_weights);
+  gl_->Uniform4fv(src_subrect_location_, 1, src_subrect_texcoord);
+
+  gl_->Uniform2f(src_pixelsize_location_, src_size.width(), src_size.height());
+  gl_->Uniform2f(dst_pixelsize_location_,
+                 static_cast<float>(dst_size.width()),
+                 static_cast<float>(dst_size.height()));
+
+  gl_->Uniform2f(
+      scaling_vector_location_, scale_x ? 1.0 : 0.0, scale_x ? 0.0 : 1.0);
+  gl_->Uniform4fv(color_weights_location_, 1, color_weights);
 }
 
 }  // namespace content