Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(10)

Side by Side Diff: ui/gl/gl_surface_ozone.cc

Issue 1001833005: Update from https://crrev.com/320343 (Closed) Base URL: git@github.com:domokit/mojo.git@master
Patch Set: Supress Created 5 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « ui/gl/gl_surface_glx.cc ('k') | ui/gl/gpu_timing.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "ui/gl/gl_surface.h" 5 #include "ui/gl/gl_surface.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/callback.h"
9 #include "base/location.h"
8 #include "base/logging.h" 10 #include "base/logging.h"
9 #include "base/memory/ref_counted.h" 11 #include "base/memory/ref_counted.h"
12 #include "base/memory/weak_ptr.h"
13 #include "base/threading/worker_pool.h"
10 #include "ui/gfx/native_widget_types.h" 14 #include "ui/gfx/native_widget_types.h"
11 #include "ui/gl/gl_context.h" 15 #include "ui/gl/gl_context.h"
12 #include "ui/gl/gl_image.h" 16 #include "ui/gl/gl_image.h"
13 #include "ui/gl/gl_image_linux_dma_buffer.h" 17 #include "ui/gl/gl_image_linux_dma_buffer.h"
14 #include "ui/gl/gl_implementation.h" 18 #include "ui/gl/gl_implementation.h"
15 #include "ui/gl/gl_surface_egl.h" 19 #include "ui/gl/gl_surface_egl.h"
16 #include "ui/gl/gl_surface_osmesa.h" 20 #include "ui/gl/gl_surface_osmesa.h"
17 #include "ui/gl/gl_surface_stub.h" 21 #include "ui/gl/gl_surface_stub.h"
18 #include "ui/gl/scoped_binders.h" 22 #include "ui/gl/scoped_binders.h"
19 #include "ui/gl/scoped_make_current.h" 23 #include "ui/gl/scoped_make_current.h"
20 #include "ui/ozone/public/native_pixmap.h" 24 #include "ui/ozone/public/native_pixmap.h"
21 #include "ui/ozone/public/surface_factory_ozone.h" 25 #include "ui/ozone/public/surface_factory_ozone.h"
22 #include "ui/ozone/public/surface_ozone_egl.h" 26 #include "ui/ozone/public/surface_ozone_egl.h"
23 27
24 namespace gfx { 28 namespace gfx {
25 29
26 namespace { 30 namespace {
27 31
32 void WaitForFence(EGLDisplay display, EGLSyncKHR fence) {
33 eglClientWaitSyncKHR(display, fence, EGL_SYNC_FLUSH_COMMANDS_BIT_KHR,
34 EGL_FOREVER_KHR);
35 }
36
28 // A thin wrapper around GLSurfaceEGL that owns the EGLNativeWindow 37 // A thin wrapper around GLSurfaceEGL that owns the EGLNativeWindow
29 class GL_EXPORT GLSurfaceOzoneEGL : public NativeViewGLSurfaceEGL { 38 class GL_EXPORT GLSurfaceOzoneEGL : public NativeViewGLSurfaceEGL {
30 public: 39 public:
31 GLSurfaceOzoneEGL(scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface, 40 GLSurfaceOzoneEGL(scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface,
32 AcceleratedWidget widget) 41 AcceleratedWidget widget)
33 : NativeViewGLSurfaceEGL(ozone_surface->GetNativeWindow()), 42 : NativeViewGLSurfaceEGL(ozone_surface->GetNativeWindow()),
34 ozone_surface_(ozone_surface.Pass()), 43 ozone_surface_(ozone_surface.Pass()),
35 widget_(widget) {} 44 widget_(widget) {}
36 45
37 bool Initialize() override { 46 bool Initialize() override {
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after
104 }; 113 };
105 114
106 class GL_EXPORT GLSurfaceOzoneSurfaceless : public SurfacelessEGL { 115 class GL_EXPORT GLSurfaceOzoneSurfaceless : public SurfacelessEGL {
107 public: 116 public:
108 GLSurfaceOzoneSurfaceless(scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface, 117 GLSurfaceOzoneSurfaceless(scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface,
109 AcceleratedWidget widget) 118 AcceleratedWidget widget)
110 : SurfacelessEGL(gfx::Size()), 119 : SurfacelessEGL(gfx::Size()),
111 ozone_surface_(ozone_surface.Pass()), 120 ozone_surface_(ozone_surface.Pass()),
112 widget_(widget), 121 widget_(widget),
113 has_implicit_external_sync_( 122 has_implicit_external_sync_(
114 HasEGLExtension("EGL_ARM_implicit_external_sync")) {} 123 HasEGLExtension("EGL_ARM_implicit_external_sync")),
124 last_swap_buffers_result_(true),
125 weak_factory_(this) {}
115 126
116 bool Initialize() override { 127 bool Initialize() override {
117 if (!SurfacelessEGL::Initialize()) 128 if (!SurfacelessEGL::Initialize())
118 return false; 129 return false;
119 vsync_provider_ = ozone_surface_->CreateVSyncProvider(); 130 vsync_provider_ = ozone_surface_->CreateVSyncProvider();
120 if (!vsync_provider_) 131 if (!vsync_provider_)
121 return false; 132 return false;
122 return true; 133 return true;
123 } 134 }
124 bool Resize(const gfx::Size& size) override { 135 bool Resize(const gfx::Size& size) override {
125 if (!ozone_surface_->ResizeNativeWindow(size)) 136 if (!ozone_surface_->ResizeNativeWindow(size))
126 return false; 137 return false;
127 138
128 return SurfacelessEGL::Resize(size); 139 return SurfacelessEGL::Resize(size);
129 } 140 }
130 bool SwapBuffers() override { 141 bool SwapBuffers() override {
131 if (!Flush()) 142 glFlush();
132 return false; 143 // TODO: the following should be replaced by a per surface flush as it gets
144 // implemented in GL drivers.
145 if (has_implicit_external_sync_) {
146 EGLSyncKHR fence = InsertFence();
147 if (!fence)
148 return false;
149
150 EGLDisplay display = GetDisplay();
151 WaitForFence(display, fence);
152 eglDestroySyncKHR(display, fence);
153 } else if (ozone_surface_->IsUniversalDisplayLinkDevice()) {
154 glFinish();
155 }
156
133 return ozone_surface_->OnSwapBuffers(); 157 return ozone_surface_->OnSwapBuffers();
134 } 158 }
135 bool ScheduleOverlayPlane(int z_order, 159 bool ScheduleOverlayPlane(int z_order,
136 OverlayTransform transform, 160 OverlayTransform transform,
137 GLImage* image, 161 GLImage* image,
138 const Rect& bounds_rect, 162 const Rect& bounds_rect,
139 const RectF& crop_rect) override { 163 const RectF& crop_rect) override {
140 return image->ScheduleOverlayPlane( 164 return image->ScheduleOverlayPlane(
141 widget_, z_order, transform, bounds_rect, crop_rect); 165 widget_, z_order, transform, bounds_rect, crop_rect);
142 } 166 }
143 bool IsOffscreen() override { return false; } 167 bool IsOffscreen() override { return false; }
144 VSyncProvider* GetVSyncProvider() override { return vsync_provider_.get(); } 168 VSyncProvider* GetVSyncProvider() override { return vsync_provider_.get(); }
145 bool SupportsPostSubBuffer() override { return true; } 169 bool SupportsPostSubBuffer() override { return true; }
146 bool PostSubBuffer(int x, int y, int width, int height) override { 170 bool PostSubBuffer(int x, int y, int width, int height) override {
147 // The actual sub buffer handling is handled at higher layers. 171 // The actual sub buffer handling is handled at higher layers.
148 SwapBuffers(); 172 SwapBuffers();
149 return true; 173 return true;
150 } 174 }
151 bool SwapBuffersAsync(const SwapCompletionCallback& callback) override { 175 bool SwapBuffersAsync(const SwapCompletionCallback& callback) override {
152 if (!Flush()) 176 glFlush();
153 return false; 177 // TODO: the following should be replaced by a per surface flush as it gets
178 // implemented in GL drivers.
179 if (has_implicit_external_sync_) {
180 // If last swap failed, don't try to schedule new ones.
181 if (!last_swap_buffers_result_) {
182 last_swap_buffers_result_ = true;
183 return false;
184 }
185
186 EGLSyncKHR fence = InsertFence();
187 if (!fence)
188 return false;
189
190 base::Closure fence_wait_task =
191 base::Bind(&WaitForFence, GetDisplay(), fence);
192
193 base::Closure fence_retired_callback =
194 base::Bind(&GLSurfaceOzoneSurfaceless::FenceRetired,
195 weak_factory_.GetWeakPtr(), fence, callback);
196
197 base::WorkerPool::PostTaskAndReply(FROM_HERE, fence_wait_task,
198 fence_retired_callback, false);
199 return true;
200 } else if (ozone_surface_->IsUniversalDisplayLinkDevice()) {
201 glFinish();
202 }
154 return ozone_surface_->OnSwapBuffersAsync(callback); 203 return ozone_surface_->OnSwapBuffersAsync(callback);
155 } 204 }
156 bool PostSubBufferAsync(int x, 205 bool PostSubBufferAsync(int x,
157 int y, 206 int y,
158 int width, 207 int width,
159 int height, 208 int height,
160 const SwapCompletionCallback& callback) override { 209 const SwapCompletionCallback& callback) override {
161 return SwapBuffersAsync(callback); 210 return SwapBuffersAsync(callback);
162 } 211 }
163 212
164 protected: 213 protected:
165 ~GLSurfaceOzoneSurfaceless() override { 214 ~GLSurfaceOzoneSurfaceless() override {
166 Destroy(); // EGL surface must be destroyed before SurfaceOzone 215 Destroy(); // EGL surface must be destroyed before SurfaceOzone
167 } 216 }
168 217
169 bool Flush() { 218 EGLSyncKHR InsertFence() {
170 glFlush(); 219 const EGLint attrib_list[] = {EGL_SYNC_CONDITION_KHR,
171 // TODO: crbug.com/462360 the following should be replaced by a per surface 220 EGL_SYNC_PRIOR_COMMANDS_IMPLICIT_EXTERNAL_ARM,
172 // flush as it gets implemented in GL drivers. 221 EGL_NONE};
173 if (has_implicit_external_sync_) { 222 return eglCreateSyncKHR(GetDisplay(), EGL_SYNC_FENCE_KHR, attrib_list);
174 const EGLint attrib_list[] = { 223 }
175 EGL_SYNC_CONDITION_KHR, 224
176 EGL_SYNC_PRIOR_COMMANDS_IMPLICIT_EXTERNAL_ARM, 225 void FenceRetired(EGLSyncKHR fence, const SwapCompletionCallback& callback) {
177 EGL_NONE}; 226 eglDestroySyncKHR(GetDisplay(), fence);
178 EGLSyncKHR fence = 227 last_swap_buffers_result_ = ozone_surface_->OnSwapBuffersAsync(callback);
179 eglCreateSyncKHR(GetDisplay(), EGL_SYNC_FENCE_KHR, attrib_list);
180 if (fence) {
181 // TODO(dbehr): piman@ suggests we could improve here by moving
182 // following wait to right before drmModePageFlip crbug.com/456417.
183 eglClientWaitSyncKHR(GetDisplay(), fence,
184 EGL_SYNC_FLUSH_COMMANDS_BIT_KHR, EGL_FOREVER_KHR);
185 eglDestroySyncKHR(GetDisplay(), fence);
186 } else {
187 return false;
188 }
189 } else if (ozone_surface_->IsUniversalDisplayLinkDevice()) {
190 glFinish();
191 }
192 return true;
193 } 228 }
194 229
195 // The native surface. Deleting this is allowed to free the EGLNativeWindow. 230 // The native surface. Deleting this is allowed to free the EGLNativeWindow.
196 scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface_; 231 scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface_;
197 AcceleratedWidget widget_; 232 AcceleratedWidget widget_;
198 scoped_ptr<VSyncProvider> vsync_provider_; 233 scoped_ptr<VSyncProvider> vsync_provider_;
199 bool has_implicit_external_sync_; 234 bool has_implicit_external_sync_;
235 bool last_swap_buffers_result_;
236
237 base::WeakPtrFactory<GLSurfaceOzoneSurfaceless> weak_factory_;
238
200 DISALLOW_COPY_AND_ASSIGN(GLSurfaceOzoneSurfaceless); 239 DISALLOW_COPY_AND_ASSIGN(GLSurfaceOzoneSurfaceless);
201 }; 240 };
202 241
203 // This provides surface-like semantics implemented through surfaceless. 242 // This provides surface-like semantics implemented through surfaceless.
204 // A framebuffer is bound automatically. 243 // A framebuffer is bound automatically.
205 class GL_EXPORT GLSurfaceOzoneSurfacelessSurfaceImpl 244 class GL_EXPORT GLSurfaceOzoneSurfacelessSurfaceImpl
206 : public GLSurfaceOzoneSurfaceless { 245 : public GLSurfaceOzoneSurfaceless {
207 public: 246 public:
208 GLSurfaceOzoneSurfacelessSurfaceImpl( 247 GLSurfaceOzoneSurfacelessSurfaceImpl(
209 scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface, 248 scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface,
(...skipping 252 matching lines...) Expand 10 before | Expand all | Expand 10 after
462 NOTREACHED(); 501 NOTREACHED();
463 return NULL; 502 return NULL;
464 } 503 }
465 } 504 }
466 505
467 EGLNativeDisplayType GetPlatformDefaultEGLNativeDisplay() { 506 EGLNativeDisplayType GetPlatformDefaultEGLNativeDisplay() {
468 return ui::SurfaceFactoryOzone::GetInstance()->GetNativeDisplay(); 507 return ui::SurfaceFactoryOzone::GetInstance()->GetNativeDisplay();
469 } 508 }
470 509
471 } // namespace gfx 510 } // namespace gfx
OLDNEW
« no previous file with comments | « ui/gl/gl_surface_glx.cc ('k') | ui/gl/gpu_timing.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698