OLD | NEW |
---|---|
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/logging.h" | 7 #include "base/logging.h" |
8 #include "base/memory/ref_counted.h" | 8 #include "base/memory/ref_counted.h" |
9 #include "ui/gfx/native_widget_types.h" | 9 #include "ui/gfx/native_widget_types.h" |
10 #include "ui/gl/gl_context.h" | 10 #include "ui/gl/gl_context.h" |
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
98 | 98 |
99 DISALLOW_COPY_AND_ASSIGN(GLSurfaceOzoneEGL); | 99 DISALLOW_COPY_AND_ASSIGN(GLSurfaceOzoneEGL); |
100 }; | 100 }; |
101 | 101 |
102 class GL_EXPORT GLSurfaceOzoneSurfaceless : public SurfacelessEGL { | 102 class GL_EXPORT GLSurfaceOzoneSurfaceless : public SurfacelessEGL { |
103 public: | 103 public: |
104 GLSurfaceOzoneSurfaceless(scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface, | 104 GLSurfaceOzoneSurfaceless(scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface, |
105 AcceleratedWidget widget) | 105 AcceleratedWidget widget) |
106 : SurfacelessEGL(gfx::Size()), | 106 : SurfacelessEGL(gfx::Size()), |
107 ozone_surface_(ozone_surface.Pass()), | 107 ozone_surface_(ozone_surface.Pass()), |
108 widget_(widget) {} | 108 widget_(widget), |
109 has_implicit_external_sync_( | |
110 HasEGLExtension("EGL_ARM_implicit_external_sync")) {} | |
109 | 111 |
110 bool Initialize() override { | 112 bool Initialize() override { |
111 if (!SurfacelessEGL::Initialize()) | 113 if (!SurfacelessEGL::Initialize()) |
112 return false; | 114 return false; |
113 vsync_provider_ = ozone_surface_->CreateVSyncProvider(); | 115 vsync_provider_ = ozone_surface_->CreateVSyncProvider(); |
114 if (!vsync_provider_) | 116 if (!vsync_provider_) |
115 return false; | 117 return false; |
116 return true; | 118 return true; |
117 } | 119 } |
118 bool Resize(const gfx::Size& size) override { | 120 bool Resize(const gfx::Size& size) override { |
119 if (!ozone_surface_->ResizeNativeWindow(size)) | 121 if (!ozone_surface_->ResizeNativeWindow(size)) |
120 return false; | 122 return false; |
121 | 123 |
122 return SurfacelessEGL::Resize(size); | 124 return SurfacelessEGL::Resize(size); |
123 } | 125 } |
124 bool SwapBuffers() override { | 126 bool SwapBuffers() override { |
125 // TODO: this should be replaced by a fence when supported by the driver. | 127 if (!Flush()) |
126 glFlush(); | 128 return false; |
127 return ozone_surface_->OnSwapBuffers(); | 129 return ozone_surface_->OnSwapBuffers(); |
128 } | 130 } |
129 bool ScheduleOverlayPlane(int z_order, | 131 bool ScheduleOverlayPlane(int z_order, |
130 OverlayTransform transform, | 132 OverlayTransform transform, |
131 GLImage* image, | 133 GLImage* image, |
132 const Rect& bounds_rect, | 134 const Rect& bounds_rect, |
133 const RectF& crop_rect) override { | 135 const RectF& crop_rect) override { |
134 return image->ScheduleOverlayPlane( | 136 return image->ScheduleOverlayPlane( |
135 widget_, z_order, transform, bounds_rect, crop_rect); | 137 widget_, z_order, transform, bounds_rect, crop_rect); |
136 } | 138 } |
137 bool IsOffscreen() override { return false; } | 139 bool IsOffscreen() override { return false; } |
138 VSyncProvider* GetVSyncProvider() override { return vsync_provider_.get(); } | 140 VSyncProvider* GetVSyncProvider() override { return vsync_provider_.get(); } |
139 bool SupportsPostSubBuffer() override { return true; } | 141 bool SupportsPostSubBuffer() override { return true; } |
140 bool PostSubBuffer(int x, int y, int width, int height) override { | 142 bool PostSubBuffer(int x, int y, int width, int height) override { |
141 // The actual sub buffer handling is handled at higher layers. | 143 // The actual sub buffer handling is handled at higher layers. |
142 SwapBuffers(); | 144 SwapBuffers(); |
143 return true; | 145 return true; |
144 } | 146 } |
145 bool SwapBuffersAsync(const SwapCompletionCallback& callback) override { | 147 bool SwapBuffersAsync(const SwapCompletionCallback& callback) override { |
146 // TODO: this should be replaced by a fence when supported by the driver. | 148 if (!Flush()) |
147 glFlush(); | 149 return false; |
148 return ozone_surface_->OnSwapBuffersAsync(callback); | 150 return ozone_surface_->OnSwapBuffersAsync(callback); |
149 } | 151 } |
150 bool PostSubBufferAsync(int x, | 152 bool PostSubBufferAsync(int x, |
151 int y, | 153 int y, |
152 int width, | 154 int width, |
153 int height, | 155 int height, |
154 const SwapCompletionCallback& callback) override { | 156 const SwapCompletionCallback& callback) override { |
155 return SwapBuffersAsync(callback); | 157 return SwapBuffersAsync(callback); |
156 } | 158 } |
157 | 159 |
158 private: | 160 private: |
159 ~GLSurfaceOzoneSurfaceless() override { | 161 ~GLSurfaceOzoneSurfaceless() override { |
160 Destroy(); // EGL surface must be destroyed before SurfaceOzone | 162 Destroy(); // EGL surface must be destroyed before SurfaceOzone |
161 } | 163 } |
162 | 164 |
165 bool Flush() { | |
166 glFlush(); | |
167 // TODO: the following should be replaced by a per surface flush as it gets | |
168 // implemented in GL drivers. | |
169 if (has_implicit_external_sync_) { | |
170 const EGLint attrib_list[] = { | |
171 EGL_SYNC_CONDITION_KHR, | |
172 EGL_SYNC_PRIOR_COMMANDS_IMPLICIT_EXTERNAL_ARM, | |
173 EGL_NONE}; | |
174 EGLSyncKHR fence = | |
175 eglCreateSyncKHR(GetDisplay(), EGL_SYNC_FENCE_KHR, attrib_list); | |
176 if (fence) { | |
177 eglClientWaitSyncKHR(GetDisplay(), fence, | |
178 EGL_SYNC_FLUSH_COMMANDS_BIT_KHR, EGL_FOREVER_KHR); | |
piman
2015/02/07 01:13:17
nit: if we're doing EGL_SYNC_FLUSH_COMMANDS_BIT_KH
piman
2015/02/07 01:13:17
As a potential optimization, should we delay the C
dnicoara
2015/02/07 02:03:36
+1 for TODO and bug. I was talking to Alex about t
| |
179 eglDestroySyncKHR(GetDisplay(), fence); | |
180 } else { | |
181 return false; | |
182 } | |
183 } | |
184 return true; | |
185 } | |
186 | |
163 // The native surface. Deleting this is allowed to free the EGLNativeWindow. | 187 // The native surface. Deleting this is allowed to free the EGLNativeWindow. |
164 scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface_; | 188 scoped_ptr<ui::SurfaceOzoneEGL> ozone_surface_; |
165 AcceleratedWidget widget_; | 189 AcceleratedWidget widget_; |
166 scoped_ptr<VSyncProvider> vsync_provider_; | 190 scoped_ptr<VSyncProvider> vsync_provider_; |
167 | 191 bool has_implicit_external_sync_; |
168 DISALLOW_COPY_AND_ASSIGN(GLSurfaceOzoneSurfaceless); | 192 DISALLOW_COPY_AND_ASSIGN(GLSurfaceOzoneSurfaceless); |
169 }; | 193 }; |
170 | 194 |
171 } // namespace | 195 } // namespace |
172 | 196 |
173 // static | 197 // static |
174 bool GLSurface::InitializeOneOffInternal() { | 198 bool GLSurface::InitializeOneOffInternal() { |
175 switch (GetGLImplementation()) { | 199 switch (GetGLImplementation()) { |
176 case kGLImplementationEGLGLES2: | 200 case kGLImplementationEGLGLES2: |
177 if (!GLSurfaceEGL::InitializeOneOff()) { | 201 if (!GLSurfaceEGL::InitializeOneOff()) { |
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
257 NOTREACHED(); | 281 NOTREACHED(); |
258 return NULL; | 282 return NULL; |
259 } | 283 } |
260 } | 284 } |
261 | 285 |
262 EGLNativeDisplayType GetPlatformDefaultEGLNativeDisplay() { | 286 EGLNativeDisplayType GetPlatformDefaultEGLNativeDisplay() { |
263 return ui::SurfaceFactoryOzone::GetInstance()->GetNativeDisplay(); | 287 return ui::SurfaceFactoryOzone::GetInstance()->GetNativeDisplay(); |
264 } | 288 } |
265 | 289 |
266 } // namespace gfx | 290 } // namespace gfx |
OLD | NEW |