• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2002 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6 
7 // Surface.cpp: Implements the egl::Surface class, representing a drawing surface
8 // such as the client area of a window, including any back buffers.
9 // Implements EGLSurface and related functionality. [EGL 1.4] section 2.2 page 3.
10 
11 #include "libANGLE/Surface.h"
12 
13 #include <EGL/eglext.h>
14 
15 #include "libANGLE/Config.h"
16 #include "libANGLE/Context.h"
17 #include "libANGLE/Display.h"
18 #include "libANGLE/Framebuffer.h"
19 #include "libANGLE/Texture.h"
20 #include "libANGLE/Thread.h"
21 #include "libANGLE/formatutils.h"
22 #include "libANGLE/renderer/EGLImplFactory.h"
23 #include "libANGLE/trace.h"
24 
25 namespace egl
26 {
27 namespace
28 {
29 angle::SubjectIndex kSurfaceImplSubjectIndex = 0;
30 }  // namespace
31 
SurfaceState(const egl::Config * configIn,const AttributeMap & attributesIn)32 SurfaceState::SurfaceState(const egl::Config *configIn, const AttributeMap &attributesIn)
33     : label(nullptr),
34       config((configIn != nullptr) ? new egl::Config(*configIn) : nullptr),
35       attributes(attributesIn),
36       timestampsEnabled(false),
37       directComposition(false)
38 {
39     directComposition = attributes.get(EGL_DIRECT_COMPOSITION_ANGLE, EGL_FALSE) == EGL_TRUE;
40 }
41 
~SurfaceState()42 SurfaceState::~SurfaceState()
43 {
44     delete config;
45 }
46 
Surface(EGLint surfaceType,const egl::Config * config,const AttributeMap & attributes,EGLenum buftype)47 Surface::Surface(EGLint surfaceType,
48                  const egl::Config *config,
49                  const AttributeMap &attributes,
50                  EGLenum buftype)
51     : FramebufferAttachmentObject(),
52       mState(config, attributes),
53       mImplementation(nullptr),
54       mRefCount(0),
55       mDestroyed(false),
56       mType(surfaceType),
57       mBuftype(buftype),
58       mPostSubBufferRequested(false),
59       mLargestPbuffer(false),
60       mGLColorspace(EGL_GL_COLORSPACE_LINEAR),
61       mVGAlphaFormat(EGL_VG_ALPHA_FORMAT_NONPRE),
62       mVGColorspace(EGL_VG_COLORSPACE_sRGB),
63       mMipmapTexture(false),
64       mMipmapLevel(0),
65       mHorizontalResolution(EGL_UNKNOWN),
66       mVerticalResolution(EGL_UNKNOWN),
67       mMultisampleResolve(EGL_MULTISAMPLE_RESOLVE_DEFAULT),
68       mFixedSize(false),
69       mFixedWidth(0),
70       mFixedHeight(0),
71       mTextureFormat(TextureFormat::NoTexture),
72       mTextureTarget(EGL_NO_TEXTURE),
73       // FIXME: Determine actual pixel aspect ratio
74       mPixelAspectRatio(static_cast<EGLint>(1.0 * EGL_DISPLAY_SCALING)),
75       mRenderBuffer(EGL_BACK_BUFFER),
76       mSwapBehavior(EGL_NONE),
77       mOrientation(0),
78       mTexture(nullptr),
79       mColorFormat(config->renderTargetFormat),
80       mDSFormat(config->depthStencilFormat),
81       mInitState(gl::InitState::Initialized),
82       mImplObserverBinding(this, kSurfaceImplSubjectIndex)
83 {
84     mPostSubBufferRequested =
85         (attributes.get(EGL_POST_SUB_BUFFER_SUPPORTED_NV, EGL_FALSE) == EGL_TRUE);
86     mFlexibleSurfaceCompatibilityRequested =
87         (attributes.get(EGL_FLEXIBLE_SURFACE_COMPATIBILITY_SUPPORTED_ANGLE, EGL_FALSE) == EGL_TRUE);
88 
89     if (mType == EGL_PBUFFER_BIT)
90     {
91         mLargestPbuffer = (attributes.get(EGL_LARGEST_PBUFFER, EGL_FALSE) == EGL_TRUE);
92     }
93 
94     mGLColorspace =
95         static_cast<EGLenum>(attributes.get(EGL_GL_COLORSPACE, EGL_GL_COLORSPACE_LINEAR));
96     mVGAlphaFormat =
97         static_cast<EGLenum>(attributes.get(EGL_VG_ALPHA_FORMAT, EGL_VG_ALPHA_FORMAT_NONPRE));
98     mVGColorspace = static_cast<EGLenum>(attributes.get(EGL_VG_COLORSPACE, EGL_VG_COLORSPACE_sRGB));
99     mMipmapTexture = (attributes.get(EGL_MIPMAP_TEXTURE, EGL_FALSE) == EGL_TRUE);
100 
101     mRobustResourceInitialization =
102         (attributes.get(EGL_ROBUST_RESOURCE_INITIALIZATION_ANGLE, EGL_FALSE) == EGL_TRUE);
103     if (mRobustResourceInitialization)
104     {
105         mInitState = gl::InitState::MayNeedInit;
106     }
107 
108     mFixedSize = (attributes.get(EGL_FIXED_SIZE_ANGLE, EGL_FALSE) == EGL_TRUE);
109     if (mFixedSize)
110     {
111         mFixedWidth  = static_cast<size_t>(attributes.get(EGL_WIDTH, 0));
112         mFixedHeight = static_cast<size_t>(attributes.get(EGL_HEIGHT, 0));
113     }
114 
115     if (mType != EGL_WINDOW_BIT)
116     {
117         mTextureFormat = attributes.getAsPackedEnum(EGL_TEXTURE_FORMAT, TextureFormat::NoTexture);
118         mTextureTarget = static_cast<EGLenum>(attributes.get(EGL_TEXTURE_TARGET, EGL_NO_TEXTURE));
119     }
120 
121     mOrientation = static_cast<EGLint>(attributes.get(EGL_SURFACE_ORIENTATION_ANGLE, 0));
122 
123     mTextureOffset.x = static_cast<int>(mState.attributes.get(EGL_TEXTURE_OFFSET_X_ANGLE, 0));
124     mTextureOffset.y = static_cast<int>(mState.attributes.get(EGL_TEXTURE_OFFSET_Y_ANGLE, 0));
125 }
126 
~Surface()127 Surface::~Surface() {}
128 
getAttachmentImpl() const129 rx::FramebufferAttachmentObjectImpl *Surface::getAttachmentImpl() const
130 {
131     return mImplementation;
132 }
133 
destroyImpl(const Display * display)134 Error Surface::destroyImpl(const Display *display)
135 {
136     if (mImplementation)
137     {
138         mImplementation->destroy(display);
139     }
140 
141     ASSERT(!mTexture);
142 
143     SafeDelete(mImplementation);
144 
145     delete this;
146     return NoError();
147 }
148 
postSwap(const gl::Context * context)149 void Surface::postSwap(const gl::Context *context)
150 {
151     if (mRobustResourceInitialization && mSwapBehavior != EGL_BUFFER_PRESERVED)
152     {
153         mInitState = gl::InitState::MayNeedInit;
154         onStateChange(angle::SubjectMessage::SubjectChanged);
155     }
156 
157     context->onPostSwap();
158 }
159 
initialize(const Display * display)160 Error Surface::initialize(const Display *display)
161 {
162     GLenum overrideRenderTargetFormat = mState.config->renderTargetFormat;
163 
164     // To account for color space differences, override the renderTargetFormat with the
165     // non-linear format. If no suitable non-linear format was found, return
166     // EGL_BAD_MATCH error
167     if (!gl::ColorspaceFormatOverride(mGLColorspace, &overrideRenderTargetFormat))
168     {
169         return egl::EglBadMatch();
170     }
171 
172     // If an override is required update mState.config as well
173     if (mState.config->renderTargetFormat != overrideRenderTargetFormat)
174     {
175         egl::Config *overrideConfig        = new egl::Config(*(mState.config));
176         overrideConfig->renderTargetFormat = overrideRenderTargetFormat;
177         delete mState.config;
178         mState.config = overrideConfig;
179 
180         mColorFormat = gl::Format(mState.config->renderTargetFormat);
181         mDSFormat    = gl::Format(mState.config->depthStencilFormat);
182     }
183 
184     ANGLE_TRY(mImplementation->initialize(display));
185 
186     // Initialized here since impl is nullptr in the constructor.
187     // Must happen after implementation initialize for Android.
188     mSwapBehavior = mImplementation->getSwapBehavior();
189 
190     if (mBuftype == EGL_IOSURFACE_ANGLE)
191     {
192         GLenum internalFormat =
193             static_cast<GLenum>(mState.attributes.get(EGL_TEXTURE_INTERNAL_FORMAT_ANGLE));
194         GLenum type  = static_cast<GLenum>(mState.attributes.get(EGL_TEXTURE_TYPE_ANGLE));
195         mColorFormat = gl::Format(internalFormat, type);
196     }
197     if (mBuftype == EGL_D3D_TEXTURE_ANGLE)
198     {
199         const angle::Format *colorFormat = mImplementation->getD3DTextureColorFormat();
200         ASSERT(colorFormat != nullptr);
201         GLenum internalFormat = colorFormat->fboImplementationInternalFormat;
202         mColorFormat          = gl::Format(internalFormat, colorFormat->componentType);
203         mGLColorspace         = EGL_GL_COLORSPACE_LINEAR;
204         if (mColorFormat.info->colorEncoding == GL_SRGB)
205         {
206             mGLColorspace = EGL_GL_COLORSPACE_SRGB;
207         }
208     }
209 
210     if (mType == EGL_WINDOW_BIT && display->getExtensions().getFrameTimestamps)
211     {
212         mState.supportedCompositorTimings = mImplementation->getSupportedCompositorTimings();
213         mState.supportedTimestamps        = mImplementation->getSupportedTimestamps();
214     }
215 
216     mImplObserverBinding.bind(mImplementation);
217 
218     return NoError();
219 }
220 
makeCurrent(const gl::Context * context)221 Error Surface::makeCurrent(const gl::Context *context)
222 {
223     ANGLE_TRY(mImplementation->makeCurrent(context));
224 
225     mRefCount++;
226     return NoError();
227 }
228 
unMakeCurrent(const gl::Context * context)229 Error Surface::unMakeCurrent(const gl::Context *context)
230 {
231     ANGLE_TRY(mImplementation->unMakeCurrent(context));
232     return releaseRef(context->getDisplay());
233 }
234 
releaseRef(const Display * display)235 Error Surface::releaseRef(const Display *display)
236 {
237     ASSERT(mRefCount > 0);
238     mRefCount--;
239     if (mRefCount == 0 && mDestroyed)
240     {
241         ASSERT(display);
242         return destroyImpl(display);
243     }
244 
245     return NoError();
246 }
247 
onDestroy(const Display * display)248 Error Surface::onDestroy(const Display *display)
249 {
250     mDestroyed = true;
251     if (mRefCount == 0)
252     {
253         return destroyImpl(display);
254     }
255     return NoError();
256 }
257 
setLabel(EGLLabelKHR label)258 void Surface::setLabel(EGLLabelKHR label)
259 {
260     mState.label = label;
261 }
262 
getLabel() const263 EGLLabelKHR Surface::getLabel() const
264 {
265     return mState.label;
266 }
267 
getType() const268 EGLint Surface::getType() const
269 {
270     return mType;
271 }
272 
swap(const gl::Context * context)273 Error Surface::swap(const gl::Context *context)
274 {
275     ANGLE_TRACE_EVENT0("gpu.angle", "egl::Surface::swap");
276 
277     context->getState().getOverlay()->onSwap();
278 
279     ANGLE_TRY(mImplementation->swap(context));
280     postSwap(context);
281     return NoError();
282 }
283 
swapWithDamage(const gl::Context * context,EGLint * rects,EGLint n_rects)284 Error Surface::swapWithDamage(const gl::Context *context, EGLint *rects, EGLint n_rects)
285 {
286     context->getState().getOverlay()->onSwap();
287 
288     ANGLE_TRY(mImplementation->swapWithDamage(context, rects, n_rects));
289     postSwap(context);
290     return NoError();
291 }
292 
swapWithFrameToken(const gl::Context * context,EGLFrameTokenANGLE frameToken)293 Error Surface::swapWithFrameToken(const gl::Context *context, EGLFrameTokenANGLE frameToken)
294 {
295     context->getState().getOverlay()->onSwap();
296 
297     ANGLE_TRY(mImplementation->swapWithFrameToken(context, frameToken));
298     postSwap(context);
299     return NoError();
300 }
301 
postSubBuffer(const gl::Context * context,EGLint x,EGLint y,EGLint width,EGLint height)302 Error Surface::postSubBuffer(const gl::Context *context,
303                              EGLint x,
304                              EGLint y,
305                              EGLint width,
306                              EGLint height)
307 {
308     if (width == 0 || height == 0)
309     {
310         return egl::NoError();
311     }
312 
313     context->getState().getOverlay()->onSwap();
314 
315     ANGLE_TRY(mImplementation->postSubBuffer(context, x, y, width, height));
316     postSwap(context);
317     return NoError();
318 }
319 
setPresentationTime(EGLnsecsANDROID time)320 Error Surface::setPresentationTime(EGLnsecsANDROID time)
321 {
322     return mImplementation->setPresentationTime(time);
323 }
324 
querySurfacePointerANGLE(EGLint attribute,void ** value)325 Error Surface::querySurfacePointerANGLE(EGLint attribute, void **value)
326 {
327     return mImplementation->querySurfacePointerANGLE(attribute, value);
328 }
329 
isPostSubBufferSupported() const330 EGLint Surface::isPostSubBufferSupported() const
331 {
332     return mPostSubBufferRequested && mImplementation->isPostSubBufferSupported();
333 }
334 
setSwapInterval(EGLint interval)335 void Surface::setSwapInterval(EGLint interval)
336 {
337     mImplementation->setSwapInterval(interval);
338 }
339 
setMipmapLevel(EGLint level)340 void Surface::setMipmapLevel(EGLint level)
341 {
342     // Level is set but ignored
343     UNIMPLEMENTED();
344     mMipmapLevel = level;
345 }
346 
setMultisampleResolve(EGLenum resolve)347 void Surface::setMultisampleResolve(EGLenum resolve)
348 {
349     // Behaviour is set but ignored
350     UNIMPLEMENTED();
351     mMultisampleResolve = resolve;
352 }
353 
setSwapBehavior(EGLenum behavior)354 void Surface::setSwapBehavior(EGLenum behavior)
355 {
356     // Behaviour is set but ignored
357     UNIMPLEMENTED();
358     mSwapBehavior = behavior;
359 }
360 
setFixedWidth(EGLint width)361 void Surface::setFixedWidth(EGLint width)
362 {
363     mFixedWidth = width;
364     mImplementation->setFixedWidth(width);
365 }
366 
setFixedHeight(EGLint height)367 void Surface::setFixedHeight(EGLint height)
368 {
369     mFixedHeight = height;
370     mImplementation->setFixedHeight(height);
371 }
372 
getConfig() const373 const Config *Surface::getConfig() const
374 {
375     return mState.config;
376 }
377 
getPixelAspectRatio() const378 EGLint Surface::getPixelAspectRatio() const
379 {
380     return mPixelAspectRatio;
381 }
382 
getRenderBuffer() const383 EGLenum Surface::getRenderBuffer() const
384 {
385     return mRenderBuffer;
386 }
387 
getSwapBehavior() const388 EGLenum Surface::getSwapBehavior() const
389 {
390     return mSwapBehavior;
391 }
392 
getTextureFormat() const393 TextureFormat Surface::getTextureFormat() const
394 {
395     return mTextureFormat;
396 }
397 
getTextureTarget() const398 EGLenum Surface::getTextureTarget() const
399 {
400     return mTextureTarget;
401 }
402 
getLargestPbuffer() const403 bool Surface::getLargestPbuffer() const
404 {
405     return mLargestPbuffer;
406 }
407 
getGLColorspace() const408 EGLenum Surface::getGLColorspace() const
409 {
410     return mGLColorspace;
411 }
412 
getVGAlphaFormat() const413 EGLenum Surface::getVGAlphaFormat() const
414 {
415     return mVGAlphaFormat;
416 }
417 
getVGColorspace() const418 EGLenum Surface::getVGColorspace() const
419 {
420     return mVGColorspace;
421 }
422 
getMipmapTexture() const423 bool Surface::getMipmapTexture() const
424 {
425     return mMipmapTexture;
426 }
427 
getMipmapLevel() const428 EGLint Surface::getMipmapLevel() const
429 {
430     return mMipmapLevel;
431 }
432 
getHorizontalResolution() const433 EGLint Surface::getHorizontalResolution() const
434 {
435     return mHorizontalResolution;
436 }
437 
getVerticalResolution() const438 EGLint Surface::getVerticalResolution() const
439 {
440     return mVerticalResolution;
441 }
442 
getMultisampleResolve() const443 EGLenum Surface::getMultisampleResolve() const
444 {
445     return mMultisampleResolve;
446 }
447 
isFixedSize() const448 EGLint Surface::isFixedSize() const
449 {
450     return mFixedSize;
451 }
452 
getWidth() const453 EGLint Surface::getWidth() const
454 {
455     return mFixedSize ? static_cast<EGLint>(mFixedWidth) : mImplementation->getWidth();
456 }
457 
getHeight() const458 EGLint Surface::getHeight() const
459 {
460     return mFixedSize ? static_cast<EGLint>(mFixedHeight) : mImplementation->getHeight();
461 }
462 
getUserWidth(const egl::Display * display,EGLint * value) const463 egl::Error Surface::getUserWidth(const egl::Display *display, EGLint *value) const
464 {
465     if (mFixedSize)
466     {
467         *value = static_cast<EGLint>(mFixedWidth);
468         return NoError();
469     }
470     else
471     {
472         return mImplementation->getUserWidth(display, value);
473     }
474 }
475 
getUserHeight(const egl::Display * display,EGLint * value) const476 egl::Error Surface::getUserHeight(const egl::Display *display, EGLint *value) const
477 {
478     if (mFixedSize)
479     {
480         *value = static_cast<EGLint>(mFixedHeight);
481         return NoError();
482     }
483     else
484     {
485         return mImplementation->getUserHeight(display, value);
486     }
487 }
488 
bindTexImage(gl::Context * context,gl::Texture * texture,EGLint buffer)489 Error Surface::bindTexImage(gl::Context *context, gl::Texture *texture, EGLint buffer)
490 {
491     ASSERT(!mTexture);
492     ANGLE_TRY(mImplementation->bindTexImage(context, texture, buffer));
493 
494     if (texture->bindTexImageFromSurface(context, this) == angle::Result::Stop)
495     {
496         return Error(EGL_BAD_SURFACE);
497     }
498     mTexture = texture;
499     mRefCount++;
500 
501     return NoError();
502 }
503 
releaseTexImage(const gl::Context * context,EGLint buffer)504 Error Surface::releaseTexImage(const gl::Context *context, EGLint buffer)
505 {
506     ASSERT(context);
507 
508     ANGLE_TRY(mImplementation->releaseTexImage(context, buffer));
509 
510     ASSERT(mTexture);
511     ANGLE_TRY(ResultToEGL(mTexture->releaseTexImageFromSurface(context)));
512 
513     return releaseTexImageFromTexture(context);
514 }
515 
getSyncValues(EGLuint64KHR * ust,EGLuint64KHR * msc,EGLuint64KHR * sbc)516 Error Surface::getSyncValues(EGLuint64KHR *ust, EGLuint64KHR *msc, EGLuint64KHR *sbc)
517 {
518     return mImplementation->getSyncValues(ust, msc, sbc);
519 }
520 
getMscRate(EGLint * numerator,EGLint * denominator)521 Error Surface::getMscRate(EGLint *numerator, EGLint *denominator)
522 {
523     return mImplementation->getMscRate(numerator, denominator);
524 }
525 
releaseTexImageFromTexture(const gl::Context * context)526 Error Surface::releaseTexImageFromTexture(const gl::Context *context)
527 {
528     ASSERT(mTexture);
529     mTexture = nullptr;
530     return releaseRef(context->getDisplay());
531 }
532 
getAttachmentSize(const gl::ImageIndex &) const533 gl::Extents Surface::getAttachmentSize(const gl::ImageIndex & /*target*/) const
534 {
535     return gl::Extents(getWidth(), getHeight(), 1);
536 }
537 
getAttachmentFormat(GLenum binding,const gl::ImageIndex & target) const538 gl::Format Surface::getAttachmentFormat(GLenum binding, const gl::ImageIndex &target) const
539 {
540     return (binding == GL_BACK ? mColorFormat : mDSFormat);
541 }
542 
getAttachmentSamples(const gl::ImageIndex & target) const543 GLsizei Surface::getAttachmentSamples(const gl::ImageIndex &target) const
544 {
545     return getConfig()->samples;
546 }
547 
isRenderable(const gl::Context * context,GLenum binding,const gl::ImageIndex & imageIndex) const548 bool Surface::isRenderable(const gl::Context *context,
549                            GLenum binding,
550                            const gl::ImageIndex &imageIndex) const
551 {
552     return true;
553 }
554 
getId() const555 GLuint Surface::getId() const
556 {
557     UNREACHABLE();
558     return 0;
559 }
560 
createDefaultFramebuffer(const gl::Context * context,egl::Surface * readSurface)561 gl::Framebuffer *Surface::createDefaultFramebuffer(const gl::Context *context,
562                                                    egl::Surface *readSurface)
563 {
564     return new gl::Framebuffer(context, this, readSurface);
565 }
566 
initState(const gl::ImageIndex &) const567 gl::InitState Surface::initState(const gl::ImageIndex & /*imageIndex*/) const
568 {
569     return mInitState;
570 }
571 
setInitState(const gl::ImageIndex &,gl::InitState initState)572 void Surface::setInitState(const gl::ImageIndex & /*imageIndex*/, gl::InitState initState)
573 {
574     mInitState = initState;
575 }
576 
setTimestampsEnabled(bool enabled)577 void Surface::setTimestampsEnabled(bool enabled)
578 {
579     mImplementation->setTimestampsEnabled(enabled);
580     mState.timestampsEnabled = enabled;
581 }
582 
isTimestampsEnabled() const583 bool Surface::isTimestampsEnabled() const
584 {
585     return mState.timestampsEnabled;
586 }
587 
getSupportedCompositorTimings() const588 const SupportedCompositorTiming &Surface::getSupportedCompositorTimings() const
589 {
590     return mState.supportedCompositorTimings;
591 }
592 
getCompositorTiming(EGLint numTimestamps,const EGLint * names,EGLnsecsANDROID * values) const593 Error Surface::getCompositorTiming(EGLint numTimestamps,
594                                    const EGLint *names,
595                                    EGLnsecsANDROID *values) const
596 {
597     return mImplementation->getCompositorTiming(numTimestamps, names, values);
598 }
599 
getNextFrameId(EGLuint64KHR * frameId) const600 Error Surface::getNextFrameId(EGLuint64KHR *frameId) const
601 {
602     return mImplementation->getNextFrameId(frameId);
603 }
604 
getSupportedTimestamps() const605 const SupportedTimestamps &Surface::getSupportedTimestamps() const
606 {
607     return mState.supportedTimestamps;
608 }
609 
getFrameTimestamps(EGLuint64KHR frameId,EGLint numTimestamps,const EGLint * timestamps,EGLnsecsANDROID * values) const610 Error Surface::getFrameTimestamps(EGLuint64KHR frameId,
611                                   EGLint numTimestamps,
612                                   const EGLint *timestamps,
613                                   EGLnsecsANDROID *values) const
614 {
615     return mImplementation->getFrameTimestamps(frameId, numTimestamps, timestamps, values);
616 }
617 
onSubjectStateChange(angle::SubjectIndex index,angle::SubjectMessage message)618 void Surface::onSubjectStateChange(angle::SubjectIndex index, angle::SubjectMessage message)
619 {
620     ASSERT(message == angle::SubjectMessage::SubjectChanged && index == kSurfaceImplSubjectIndex);
621     onStateChange(angle::SubjectMessage::ContentsChanged);
622 }
623 
WindowSurface(rx::EGLImplFactory * implFactory,const egl::Config * config,EGLNativeWindowType window,const AttributeMap & attribs)624 WindowSurface::WindowSurface(rx::EGLImplFactory *implFactory,
625                              const egl::Config *config,
626                              EGLNativeWindowType window,
627                              const AttributeMap &attribs)
628     : Surface(EGL_WINDOW_BIT, config, attribs)
629 {
630     mImplementation = implFactory->createWindowSurface(mState, window, attribs);
631 }
632 
~WindowSurface()633 WindowSurface::~WindowSurface() {}
634 
PbufferSurface(rx::EGLImplFactory * implFactory,const Config * config,const AttributeMap & attribs)635 PbufferSurface::PbufferSurface(rx::EGLImplFactory *implFactory,
636                                const Config *config,
637                                const AttributeMap &attribs)
638     : Surface(EGL_PBUFFER_BIT, config, attribs)
639 {
640     mImplementation = implFactory->createPbufferSurface(mState, attribs);
641 }
642 
PbufferSurface(rx::EGLImplFactory * implFactory,const Config * config,EGLenum buftype,EGLClientBuffer clientBuffer,const AttributeMap & attribs)643 PbufferSurface::PbufferSurface(rx::EGLImplFactory *implFactory,
644                                const Config *config,
645                                EGLenum buftype,
646                                EGLClientBuffer clientBuffer,
647                                const AttributeMap &attribs)
648     : Surface(EGL_PBUFFER_BIT, config, attribs, buftype)
649 {
650     mImplementation =
651         implFactory->createPbufferFromClientBuffer(mState, buftype, clientBuffer, attribs);
652 }
653 
~PbufferSurface()654 PbufferSurface::~PbufferSurface() {}
655 
PixmapSurface(rx::EGLImplFactory * implFactory,const Config * config,NativePixmapType nativePixmap,const AttributeMap & attribs)656 PixmapSurface::PixmapSurface(rx::EGLImplFactory *implFactory,
657                              const Config *config,
658                              NativePixmapType nativePixmap,
659                              const AttributeMap &attribs)
660     : Surface(EGL_PIXMAP_BIT, config, attribs)
661 {
662     mImplementation = implFactory->createPixmapSurface(mState, nativePixmap, attribs);
663 }
664 
~PixmapSurface()665 PixmapSurface::~PixmapSurface() {}
666 
667 // SurfaceDeleter implementation.
668 
SurfaceDeleter(const Display * display)669 SurfaceDeleter::SurfaceDeleter(const Display *display) : mDisplay(display) {}
670 
~SurfaceDeleter()671 SurfaceDeleter::~SurfaceDeleter() {}
672 
operator ()(Surface * surface)673 void SurfaceDeleter::operator()(Surface *surface)
674 {
675     ANGLE_SWALLOW_ERR(surface->onDestroy(mDisplay));
676 }
677 
678 }  // namespace egl
679