1 // Copyright 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "ui/gl/init/gl_factory.h"
6
7 #include "base/logging.h"
8 #include "base/trace_event/trace_event.h"
9 #include "ui/gl/gl_bindings.h"
10 #include "ui/gl/gl_context.h"
11 #include "ui/gl/gl_context_egl.h"
12 #include "ui/gl/gl_context_stub.h"
13 #include "ui/gl/gl_egl_api_implementation.h"
14 #include "ui/gl/gl_implementation.h"
15 #include "ui/gl/gl_share_group.h"
16 #include "ui/gl/gl_surface.h"
17 #include "ui/gl/gl_surface_egl.h"
18 #include "ui/gl/gl_surface_stub.h"
19
20 namespace gl {
21 namespace init {
22
23 namespace {
24
25 // Used to render into an already current context+surface,
26 // that we do not have ownership of (draw callback).
27 // TODO(boliu): Make this inherit from GLContextEGL.
28 class GLNonOwnedContext : public GLContextReal {
29 public:
30 explicit GLNonOwnedContext(GLShareGroup* share_group);
31
32 // Implement GLContext.
33 bool Initialize(GLSurface* compatible_surface,
34 const GLContextAttribs& attribs) override;
35 bool MakeCurrent(GLSurface* surface) override;
ReleaseCurrent(GLSurface * surface)36 void ReleaseCurrent(GLSurface* surface) override {}
IsCurrent(GLSurface * surface)37 bool IsCurrent(GLSurface* surface) override { return true; }
GetHandle()38 void* GetHandle() override { return nullptr; }
39
40 protected:
~GLNonOwnedContext()41 ~GLNonOwnedContext() override {}
42
43 private:
44 EGLDisplay display_;
45
46 DISALLOW_COPY_AND_ASSIGN(GLNonOwnedContext);
47 };
48
GLNonOwnedContext(GLShareGroup * share_group)49 GLNonOwnedContext::GLNonOwnedContext(GLShareGroup* share_group)
50 : GLContextReal(share_group), display_(nullptr) {}
51
Initialize(GLSurface * compatible_surface,const GLContextAttribs & attribs)52 bool GLNonOwnedContext::Initialize(GLSurface* compatible_surface,
53 const GLContextAttribs& attribs) {
54 display_ = eglGetDisplay(EGL_DEFAULT_DISPLAY);
55 return true;
56 }
57
MakeCurrent(GLSurface * surface)58 bool GLNonOwnedContext::MakeCurrent(GLSurface* surface) {
59 BindGLApi();
60 SetCurrent(surface);
61 InitializeDynamicBindings();
62 return true;
63 }
64
65 } // namespace
66
GetAllowedGLImplementations()67 std::vector<GLImplementation> GetAllowedGLImplementations() {
68 std::vector<GLImplementation> impls;
69 impls.push_back(kGLImplementationEGLGLES2);
70 impls.push_back(kGLImplementationEGLANGLE);
71 return impls;
72 }
73
GetGLWindowSystemBindingInfo(const GLVersionInfo & gl_info,GLWindowSystemBindingInfo * info)74 bool GetGLWindowSystemBindingInfo(const GLVersionInfo& gl_info,
75 GLWindowSystemBindingInfo* info) {
76 switch (GetGLImplementation()) {
77 case kGLImplementationEGLGLES2:
78 case kGLImplementationEGLANGLE:
79 return GetGLWindowSystemBindingInfoEGL(info);
80 default:
81 return false;
82 }
83 }
84
CreateGLContext(GLShareGroup * share_group,GLSurface * compatible_surface,const GLContextAttribs & attribs)85 scoped_refptr<GLContext> CreateGLContext(GLShareGroup* share_group,
86 GLSurface* compatible_surface,
87 const GLContextAttribs& attribs) {
88 TRACE_EVENT0("gpu", "gl::init::CreateGLContext");
89 switch (GetGLImplementation()) {
90 case kGLImplementationMockGL:
91 return scoped_refptr<GLContext>(new GLContextStub(share_group));
92 case kGLImplementationStubGL: {
93 scoped_refptr<GLContextStub> stub_context =
94 new GLContextStub(share_group);
95 stub_context->SetUseStubApi(true);
96 return stub_context;
97 }
98 case kGLImplementationDisabled:
99 NOTREACHED();
100 return nullptr;
101 default:
102 if (compatible_surface->GetHandle() ||
103 compatible_surface->IsSurfaceless()) {
104 return InitializeGLContext(new GLContextEGL(share_group),
105 compatible_surface, attribs);
106 } else {
107 return InitializeGLContext(new GLNonOwnedContext(share_group),
108 compatible_surface, attribs);
109 }
110 }
111 }
112
CreateViewGLSurface(gfx::AcceleratedWidget window)113 scoped_refptr<GLSurface> CreateViewGLSurface(gfx::AcceleratedWidget window) {
114 TRACE_EVENT0("gpu", "gl::init::CreateViewGLSurface");
115 CHECK_NE(kGLImplementationNone, GetGLImplementation());
116 switch (GetGLImplementation()) {
117 case kGLImplementationEGLGLES2:
118 case kGLImplementationEGLANGLE:
119 if (window != gfx::kNullAcceleratedWidget) {
120 return InitializeGLSurface(new NativeViewGLSurfaceEGL(window, nullptr));
121 } else {
122 return InitializeGLSurface(new GLSurfaceStub());
123 }
124 default:
125 NOTREACHED();
126 return nullptr;
127 }
128 }
129
CreateOffscreenGLSurfaceWithFormat(const gfx::Size & size,GLSurfaceFormat format)130 scoped_refptr<GLSurface> CreateOffscreenGLSurfaceWithFormat(
131 const gfx::Size& size, GLSurfaceFormat format) {
132 TRACE_EVENT0("gpu", "gl::init::CreateOffscreenGLSurface");
133 CHECK_NE(kGLImplementationNone, GetGLImplementation());
134 switch (GetGLImplementation()) {
135 case kGLImplementationEGLGLES2:
136 case kGLImplementationEGLANGLE: {
137 if (GLSurfaceEGL::IsEGLSurfacelessContextSupported() &&
138 (size.width() == 0 && size.height() == 0)) {
139 return InitializeGLSurfaceWithFormat(new SurfacelessEGL(size), format);
140 } else {
141 return InitializeGLSurfaceWithFormat(new PbufferGLSurfaceEGL(size),
142 format);
143 }
144 }
145 case kGLImplementationMockGL:
146 case kGLImplementationStubGL:
147 return new GLSurfaceStub;
148 default:
149 NOTREACHED();
150 return nullptr;
151 }
152 }
153
SetDisabledExtensionsPlatform(const std::string & disabled_extensions)154 void SetDisabledExtensionsPlatform(const std::string& disabled_extensions) {
155 GLImplementation implementation = GetGLImplementation();
156 DCHECK_NE(kGLImplementationNone, implementation);
157 switch (implementation) {
158 case kGLImplementationEGLGLES2:
159 case kGLImplementationEGLANGLE:
160 SetDisabledExtensionsEGL(disabled_extensions);
161 break;
162 case kGLImplementationMockGL:
163 case kGLImplementationStubGL:
164 break;
165 default:
166 NOTREACHED();
167 }
168 }
169
InitializeExtensionSettingsOneOffPlatform()170 bool InitializeExtensionSettingsOneOffPlatform() {
171 GLImplementation implementation = GetGLImplementation();
172 DCHECK_NE(kGLImplementationNone, implementation);
173 switch (implementation) {
174 case kGLImplementationEGLGLES2:
175 case kGLImplementationEGLANGLE:
176 return InitializeExtensionSettingsOneOffEGL();
177 case kGLImplementationMockGL:
178 case kGLImplementationStubGL:
179 return true;
180 default:
181 NOTREACHED();
182 return false;
183 }
184 }
185
186 } // namespace init
187 } // namespace gl
188