xref: /aosp_15_r20/external/angle/src/libGLESv2/egl_ext_stubs.cpp (revision 8975f5c5ed3d1c378011245431ada316dfb6f244)
1 //
2 // Copyright 2020 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 // egl_ext_stubs.cpp: Stubs for EXT extension entry points.
7 //
8 
9 #include "libGLESv2/egl_ext_stubs_autogen.h"
10 
11 #include "libANGLE/Device.h"
12 #include "libANGLE/Display.h"
13 #include "libANGLE/EGLSync.h"
14 #include "libANGLE/Surface.h"
15 #include "libANGLE/Thread.h"
16 #include "libANGLE/entry_points_utils.h"
17 #include "libANGLE/queryutils.h"
18 #include "libANGLE/renderer/DisplayImpl.h"
19 #include "libANGLE/validationEGL.h"
20 #include "libANGLE/validationEGL_autogen.h"
21 #include "libGLESv2/global_state.h"
22 
23 namespace egl
24 {
ClientWaitSyncKHR(Thread * thread,Display * display,SyncID syncID,EGLint flags,EGLTimeKHR timeout)25 EGLint ClientWaitSyncKHR(Thread *thread,
26                          Display *display,
27                          SyncID syncID,
28                          EGLint flags,
29                          EGLTimeKHR timeout)
30 {
31     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglClientWaitSyncKHR",
32                                           GetDisplayIfValid(display), EGL_FALSE);
33     gl::Context *currentContext = thread->getContext();
34     EGLint syncStatus           = EGL_FALSE;
35     Sync *sync                  = display->getSync(syncID);
36     ANGLE_EGL_TRY_RETURN(thread,
37                          sync->clientWait(display, currentContext, flags, timeout, &syncStatus),
38                          "eglClientWaitSyncKHR", GetSyncIfValid(display, syncID), EGL_FALSE);
39 
40     // When performing CPU wait through UnlockedTailCall we need to handle any error conditions
41     if (egl::Display::GetCurrentThreadUnlockedTailCall()->any())
42     {
43         auto handleErrorStatus = [thread, display, syncID](void *result) {
44             EGLint *eglResult = static_cast<EGLint *>(result);
45             ASSERT(eglResult);
46             if (*eglResult == EGL_FALSE)
47             {
48                 thread->setError(egl::Error(EGL_BAD_ALLOC), "eglClientWaitSyncKHR",
49                                  GetSyncIfValid(display, syncID));
50             }
51             else
52             {
53                 thread->setSuccess();
54             }
55         };
56         egl::Display::GetCurrentThreadUnlockedTailCall()->add(handleErrorStatus);
57     }
58     else
59     {
60         thread->setSuccess();
61     }
62     return syncStatus;
63 }
64 
CreateImageKHR(Thread * thread,Display * display,gl::ContextID contextID,EGLenum target,EGLClientBuffer buffer,const AttributeMap & attributes)65 EGLImageKHR CreateImageKHR(Thread *thread,
66                            Display *display,
67                            gl::ContextID contextID,
68                            EGLenum target,
69                            EGLClientBuffer buffer,
70                            const AttributeMap &attributes)
71 {
72     gl::Context *context = display->getContext(contextID);
73 
74     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglCreateImageKHR",
75                                           GetDisplayIfValid(display), EGL_NO_IMAGE);
76 
77     Image *image = nullptr;
78     ANGLE_EGL_TRY_RETURN(thread, display->createImage(context, target, buffer, attributes, &image),
79                          "", GetDisplayIfValid(display), EGL_NO_IMAGE);
80 
81     thread->setSuccess();
82     return reinterpret_cast<EGLImage>(static_cast<uintptr_t>(image->id().value));
83 }
84 
CreateNativeClientBufferANDROID(Thread * thread,const AttributeMap & attribMap)85 EGLClientBuffer CreateNativeClientBufferANDROID(Thread *thread, const AttributeMap &attribMap)
86 {
87     EGLClientBuffer eglClientBuffer = nullptr;
88     ANGLE_EGL_TRY_RETURN(thread,
89                          egl::Display::CreateNativeClientBuffer(attribMap, &eglClientBuffer),
90                          "eglCreateNativeClientBufferANDROID", nullptr, nullptr);
91 
92     thread->setSuccess();
93     return eglClientBuffer;
94 }
95 
CreatePlatformPixmapSurfaceEXT(Thread * thread,Display * display,Config * configPacked,void * native_pixmap,const AttributeMap & attributes)96 EGLSurface CreatePlatformPixmapSurfaceEXT(Thread *thread,
97                                           Display *display,
98                                           Config *configPacked,
99                                           void *native_pixmap,
100                                           const AttributeMap &attributes)
101 {
102     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
103                                           "eglCreatePlatformPixmapSurfaceEXT",
104                                           GetDisplayIfValid(display), EGL_NO_SURFACE);
105     thread->setError(EGL_BAD_DISPLAY, "eglCreatePlatformPixmapSurfaceEXT",
106                      GetDisplayIfValid(display), "CreatePlatformPixmapSurfaceEXT unimplemented.");
107     return EGL_NO_SURFACE;
108 }
109 
CreatePlatformWindowSurfaceEXT(Thread * thread,Display * display,Config * configPacked,void * native_window,const AttributeMap & attributes)110 EGLSurface CreatePlatformWindowSurfaceEXT(Thread *thread,
111                                           Display *display,
112                                           Config *configPacked,
113                                           void *native_window,
114                                           const AttributeMap &attributes)
115 {
116     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
117                                           "eglCreatePlatformWindowSurfaceEXT",
118                                           GetDisplayIfValid(display), EGL_NO_SURFACE);
119     Surface *surface = nullptr;
120 
121     // In X11, eglCreatePlatformWindowSurfaceEXT expects the native_window argument to be a pointer
122     // to a Window while the EGLNativeWindowType for X11 is its actual value.
123     // https://www.khronos.org/registry/EGL/extensions/KHR/EGL_KHR_platform_x11.txt
124     void *actualNativeWindow =
125         display->getImplementation()->getWindowSystem() == angle::NativeWindowSystem::X11
126             ? *reinterpret_cast<void **>(native_window)
127             : native_window;
128     EGLNativeWindowType nativeWindow = reinterpret_cast<EGLNativeWindowType>(actualNativeWindow);
129 
130     ANGLE_EGL_TRY_RETURN(
131         thread, display->createWindowSurface(configPacked, nativeWindow, attributes, &surface),
132         "eglCreatePlatformWindowSurfaceEXT", GetDisplayIfValid(display), EGL_NO_SURFACE);
133 
134     return reinterpret_cast<EGLSurface>(static_cast<uintptr_t>(surface->id().value));
135 }
136 
CreateStreamKHR(Thread * thread,Display * display,const AttributeMap & attributes)137 EGLStreamKHR CreateStreamKHR(Thread *thread, Display *display, const AttributeMap &attributes)
138 {
139     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglCreateStreamKHR",
140                                           GetDisplayIfValid(display), EGL_NO_STREAM_KHR);
141     Stream *stream;
142     ANGLE_EGL_TRY_RETURN(thread, display->createStream(attributes, &stream), "eglCreateStreamKHR",
143                          GetDisplayIfValid(display), EGL_NO_STREAM_KHR);
144 
145     thread->setSuccess();
146     return static_cast<EGLStreamKHR>(stream);
147 }
148 
CreateSyncKHR(Thread * thread,Display * display,EGLenum type,const AttributeMap & attributes)149 EGLSyncKHR CreateSyncKHR(Thread *thread,
150                          Display *display,
151                          EGLenum type,
152                          const AttributeMap &attributes)
153 {
154     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglCreateSyncKHR",
155                                           GetDisplayIfValid(display), EGL_NO_SYNC);
156     egl::Sync *syncObject = nullptr;
157     ANGLE_EGL_TRY_RETURN(thread,
158                          display->createSync(thread->getContext(), type, attributes, &syncObject),
159                          "eglCreateSyncKHR", GetDisplayIfValid(display), EGL_NO_SYNC);
160 
161     thread->setSuccess();
162     return reinterpret_cast<EGLSync>(static_cast<uintptr_t>(syncObject->id().value));
163 }
164 
DebugMessageControlKHR(Thread * thread,EGLDEBUGPROCKHR callback,const AttributeMap & attributes)165 EGLint DebugMessageControlKHR(Thread *thread,
166                               EGLDEBUGPROCKHR callback,
167                               const AttributeMap &attributes)
168 {
169     Debug *debug = GetDebug();
170     debug->setCallback(callback, attributes);
171 
172     thread->setSuccess();
173     return EGL_SUCCESS;
174 }
175 
DestroyImageKHR(Thread * thread,Display * display,egl::ImageID imageID)176 EGLBoolean DestroyImageKHR(Thread *thread, Display *display, egl::ImageID imageID)
177 {
178     Image *img = display->getImage(imageID);
179 
180     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglDestroyImageKHR",
181                                           GetDisplayIfValid(display), EGL_FALSE);
182     display->destroyImage(img);
183 
184     thread->setSuccess();
185     return EGL_TRUE;
186 }
187 
DestroyStreamKHR(Thread * thread,Display * display,Stream * streamObject)188 EGLBoolean DestroyStreamKHR(Thread *thread, Display *display, Stream *streamObject)
189 {
190     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglDestroyStreamKHR",
191                                           GetDisplayIfValid(display), EGL_FALSE);
192     display->destroyStream(streamObject);
193 
194     thread->setSuccess();
195     return EGL_TRUE;
196 }
197 
DestroySyncKHR(Thread * thread,Display * display,SyncID syncID)198 EGLBoolean DestroySyncKHR(Thread *thread, Display *display, SyncID syncID)
199 {
200     Sync *sync = display->getSync(syncID);
201     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglDestroySync",
202                                           GetDisplayIfValid(display), EGL_FALSE);
203     display->destroySync(sync);
204 
205     thread->setSuccess();
206     return EGL_TRUE;
207 }
208 
DupNativeFenceFDANDROID(Thread * thread,Display * display,SyncID syncID)209 EGLint DupNativeFenceFDANDROID(Thread *thread, Display *display, SyncID syncID)
210 {
211     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
212                                           "eglDupNativeFenceFDANDROID", GetDisplayIfValid(display),
213                                           EGL_NO_NATIVE_FENCE_FD_ANDROID);
214     EGLint result    = EGL_NO_NATIVE_FENCE_FD_ANDROID;
215     Sync *syncObject = display->getSync(syncID);
216     ANGLE_EGL_TRY_RETURN(thread, syncObject->dupNativeFenceFD(display, &result),
217                          "eglDupNativeFenceFDANDROID", GetSyncIfValid(display, syncID),
218                          EGL_NO_NATIVE_FENCE_FD_ANDROID);
219 
220     thread->setSuccess();
221     return result;
222 }
223 
GetNativeClientBufferANDROID(Thread * thread,const struct AHardwareBuffer * buffer)224 EGLClientBuffer GetNativeClientBufferANDROID(Thread *thread, const struct AHardwareBuffer *buffer)
225 {
226     thread->setSuccess();
227     return egl::Display::GetNativeClientBuffer(buffer);
228 }
229 
GetPlatformDisplayEXT(Thread * thread,EGLenum platform,void * native_display,const AttributeMap & attribMap)230 EGLDisplay GetPlatformDisplayEXT(Thread *thread,
231                                  EGLenum platform,
232                                  void *native_display,
233                                  const AttributeMap &attribMap)
234 {
235     switch (platform)
236     {
237         case EGL_PLATFORM_ANGLE_ANGLE:
238         case EGL_PLATFORM_GBM_KHR:
239         case EGL_PLATFORM_WAYLAND_EXT:
240         case EGL_PLATFORM_SURFACELESS_MESA:
241         {
242             return egl::Display::GetDisplayFromNativeDisplay(
243                 platform, gl::bitCast<EGLNativeDisplayType>(native_display), attribMap);
244         }
245         case EGL_PLATFORM_DEVICE_EXT:
246         {
247             Device *eglDevice = static_cast<Device *>(native_display);
248             return egl::Display::GetDisplayFromDevice(eglDevice, attribMap);
249         }
250         default:
251         {
252             UNREACHABLE();
253             return EGL_NO_DISPLAY;
254         }
255     }
256 }
257 
GetSyncAttribKHR(Thread * thread,Display * display,SyncID syncObject,EGLint attribute,EGLint * value)258 EGLBoolean GetSyncAttribKHR(Thread *thread,
259                             Display *display,
260                             SyncID syncObject,
261                             EGLint attribute,
262                             EGLint *value)
263 {
264     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglGetSyncAttrib",
265                                           GetDisplayIfValid(display), EGL_FALSE);
266     ANGLE_EGL_TRY_RETURN(thread, GetSyncAttrib(display, syncObject, attribute, value),
267                          "eglGetSyncAttrib", GetSyncIfValid(display, syncObject), EGL_FALSE);
268 
269     thread->setSuccess();
270     return EGL_TRUE;
271 }
272 
LabelObjectKHR(Thread * thread,Display * display,ObjectType objectTypePacked,EGLObjectKHR object,EGLLabelKHR label)273 EGLint LabelObjectKHR(Thread *thread,
274                       Display *display,
275                       ObjectType objectTypePacked,
276                       EGLObjectKHR object,
277                       EGLLabelKHR label)
278 {
279     LabeledObject *labeledObject =
280         GetLabeledObjectIfValid(thread, display, objectTypePacked, object);
281     ASSERT(labeledObject != nullptr);
282     labeledObject->setLabel(label);
283 
284     thread->setSuccess();
285     return EGL_SUCCESS;
286 }
287 
PostSubBufferNV(Thread * thread,Display * display,SurfaceID surfaceID,EGLint x,EGLint y,EGLint width,EGLint height)288 EGLBoolean PostSubBufferNV(Thread *thread,
289                            Display *display,
290                            SurfaceID surfaceID,
291                            EGLint x,
292                            EGLint y,
293                            EGLint width,
294                            EGLint height)
295 {
296     Surface *eglSurface = display->getSurface(surfaceID);
297 
298     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglPostSubBufferNV",
299                                           GetDisplayIfValid(display), EGL_FALSE);
300     Error error = eglSurface->postSubBuffer(thread->getContext(), x, y, width, height);
301     if (error.isError())
302     {
303         thread->setError(error, "eglPostSubBufferNV", GetSurfaceIfValid(display, surfaceID));
304         return EGL_FALSE;
305     }
306 
307     thread->setSuccess();
308     return EGL_TRUE;
309 }
310 
PresentationTimeANDROID(Thread * thread,Display * display,SurfaceID surfaceID,EGLnsecsANDROID time)311 EGLBoolean PresentationTimeANDROID(Thread *thread,
312                                    Display *display,
313                                    SurfaceID surfaceID,
314                                    EGLnsecsANDROID time)
315 {
316     Surface *eglSurface = display->getSurface(surfaceID);
317 
318     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
319                                           "eglPresentationTimeANDROID", GetDisplayIfValid(display),
320                                           EGL_FALSE);
321     ANGLE_EGL_TRY_RETURN(thread, eglSurface->setPresentationTime(time),
322                          "eglPresentationTimeANDROID", GetSurfaceIfValid(display, surfaceID),
323                          EGL_FALSE);
324 
325     return EGL_TRUE;
326 }
327 
GetCompositorTimingSupportedANDROID(Thread * thread,Display * display,SurfaceID surfaceID,CompositorTiming nameInternal)328 EGLBoolean GetCompositorTimingSupportedANDROID(Thread *thread,
329                                                Display *display,
330                                                SurfaceID surfaceID,
331                                                CompositorTiming nameInternal)
332 {
333     Surface *eglSurface = display->getSurface(surfaceID);
334 
335     thread->setSuccess();
336     return eglSurface->getSupportedCompositorTimings().test(nameInternal);
337 }
338 
GetCompositorTimingANDROID(Thread * thread,Display * display,SurfaceID surfaceID,EGLint numTimestamps,const EGLint * names,EGLnsecsANDROID * values)339 EGLBoolean GetCompositorTimingANDROID(Thread *thread,
340                                       Display *display,
341                                       SurfaceID surfaceID,
342                                       EGLint numTimestamps,
343                                       const EGLint *names,
344                                       EGLnsecsANDROID *values)
345 {
346     Surface *eglSurface = display->getSurface(surfaceID);
347 
348     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
349                                           "eglGetCompositorTimingANDROIDD",
350                                           GetDisplayIfValid(display), EGL_FALSE);
351     ANGLE_EGL_TRY_RETURN(thread, eglSurface->getCompositorTiming(numTimestamps, names, values),
352                          "eglGetCompositorTimingANDROIDD", GetSurfaceIfValid(display, surfaceID),
353                          EGL_FALSE);
354 
355     thread->setSuccess();
356     return EGL_TRUE;
357 }
358 
GetNextFrameIdANDROID(Thread * thread,Display * display,SurfaceID surfaceID,EGLuint64KHR * frameId)359 EGLBoolean GetNextFrameIdANDROID(Thread *thread,
360                                  Display *display,
361                                  SurfaceID surfaceID,
362                                  EGLuint64KHR *frameId)
363 {
364     Surface *eglSurface = display->getSurface(surfaceID);
365 
366     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
367                                           "eglGetNextFrameIdANDROID", GetDisplayIfValid(display),
368                                           EGL_FALSE);
369     ANGLE_EGL_TRY_RETURN(thread, eglSurface->getNextFrameId(frameId), "eglGetNextFrameIdANDROID",
370                          GetSurfaceIfValid(display, surfaceID), EGL_FALSE);
371 
372     thread->setSuccess();
373     return EGL_TRUE;
374 }
375 
GetFrameTimestampSupportedANDROID(Thread * thread,Display * display,SurfaceID surfaceID,Timestamp timestampInternal)376 EGLBoolean GetFrameTimestampSupportedANDROID(Thread *thread,
377                                              Display *display,
378                                              SurfaceID surfaceID,
379                                              Timestamp timestampInternal)
380 {
381     Surface *eglSurface = display->getSurface(surfaceID);
382 
383     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
384                                           "eglQueryTimestampSupportedANDROID",
385                                           GetDisplayIfValid(display), EGL_FALSE);
386     thread->setSuccess();
387     return eglSurface->getSupportedTimestamps().test(timestampInternal);
388 }
389 
GetFrameTimestampsANDROID(Thread * thread,Display * display,SurfaceID surfaceID,EGLuint64KHR frameId,EGLint numTimestamps,const EGLint * timestamps,EGLnsecsANDROID * values)390 EGLBoolean GetFrameTimestampsANDROID(Thread *thread,
391                                      Display *display,
392                                      SurfaceID surfaceID,
393                                      EGLuint64KHR frameId,
394                                      EGLint numTimestamps,
395                                      const EGLint *timestamps,
396                                      EGLnsecsANDROID *values)
397 {
398     Surface *eglSurface = display->getSurface(surfaceID);
399 
400     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
401                                           "eglGetFrameTimestampsANDROID",
402                                           GetDisplayIfValid(display), EGL_FALSE);
403     ANGLE_EGL_TRY_RETURN(
404         thread, eglSurface->getFrameTimestamps(frameId, numTimestamps, timestamps, values),
405         "eglGetFrameTimestampsANDROID", GetSurfaceIfValid(display, surfaceID), EGL_FALSE);
406 
407     thread->setSuccess();
408     return EGL_TRUE;
409 }
410 
QueryDebugKHR(Thread * thread,EGLint attribute,EGLAttrib * value)411 EGLBoolean QueryDebugKHR(Thread *thread, EGLint attribute, EGLAttrib *value)
412 {
413     Debug *debug = GetDebug();
414     switch (attribute)
415     {
416         case EGL_DEBUG_MSG_CRITICAL_KHR:
417         case EGL_DEBUG_MSG_ERROR_KHR:
418         case EGL_DEBUG_MSG_WARN_KHR:
419         case EGL_DEBUG_MSG_INFO_KHR:
420             *value = debug->isMessageTypeEnabled(FromEGLenum<MessageType>(attribute)) ? EGL_TRUE
421                                                                                       : EGL_FALSE;
422             break;
423         case EGL_DEBUG_CALLBACK_KHR:
424             *value = reinterpret_cast<EGLAttrib>(debug->getCallback());
425             break;
426 
427         default:
428             UNREACHABLE();
429     }
430 
431     thread->setSuccess();
432     return EGL_TRUE;
433 }
434 
QueryDeviceAttribEXT(Thread * thread,Device * dev,EGLint attribute,EGLAttrib * value)435 EGLBoolean QueryDeviceAttribEXT(Thread *thread, Device *dev, EGLint attribute, EGLAttrib *value)
436 {
437     ANGLE_EGL_TRY_RETURN(thread, dev->getAttribute(attribute, value), "eglQueryDeviceAttribEXT",
438                          GetDeviceIfValid(dev), EGL_FALSE);
439 
440     thread->setSuccess();
441     return EGL_TRUE;
442 }
443 
QueryDeviceStringEXT(Thread * thread,Device * dev,EGLint name)444 const char *QueryDeviceStringEXT(Thread *thread, Device *dev, EGLint name)
445 {
446     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, dev->getOwningDisplay()->prepareForCall(),
447                                           "eglQueryDeviceStringEXT",
448                                           GetDisplayIfValid(dev->getOwningDisplay()), EGL_FALSE);
449     const char *result;
450     switch (name)
451     {
452         case EGL_EXTENSIONS:
453             result = dev->getExtensionString().c_str();
454             break;
455         case EGL_DRM_DEVICE_FILE_EXT:
456         case EGL_DRM_RENDER_NODE_FILE_EXT:
457             result = dev->getDeviceString(name).c_str();
458             break;
459         default:
460             thread->setError(EglBadDevice(), "eglQueryDeviceStringEXT", GetDeviceIfValid(dev));
461             return nullptr;
462     }
463 
464     thread->setSuccess();
465     return result;
466 }
467 
QueryDisplayAttribEXT(Thread * thread,Display * display,EGLint attribute,EGLAttrib * value)468 EGLBoolean QueryDisplayAttribEXT(Thread *thread,
469                                  Display *display,
470                                  EGLint attribute,
471                                  EGLAttrib *value)
472 {
473     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
474                                           "eglQueryDisplayAttribEXT", GetDisplayIfValid(display),
475                                           EGL_FALSE);
476     *value = display->queryAttrib(attribute);
477     thread->setSuccess();
478     return EGL_TRUE;
479 }
480 
QueryStreamKHR(Thread * thread,Display * display,Stream * streamObject,EGLenum attribute,EGLint * value)481 EGLBoolean QueryStreamKHR(Thread *thread,
482                           Display *display,
483                           Stream *streamObject,
484                           EGLenum attribute,
485                           EGLint *value)
486 {
487     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglQueryStreamKHR",
488                                           GetDisplayIfValid(display), EGL_FALSE);
489     switch (attribute)
490     {
491         case EGL_STREAM_STATE_KHR:
492             *value = streamObject->getState();
493             break;
494         case EGL_CONSUMER_LATENCY_USEC_KHR:
495             *value = streamObject->getConsumerLatency();
496             break;
497         case EGL_CONSUMER_ACQUIRE_TIMEOUT_USEC_KHR:
498             *value = streamObject->getConsumerAcquireTimeout();
499             break;
500         default:
501             UNREACHABLE();
502     }
503 
504     thread->setSuccess();
505     return EGL_TRUE;
506 }
507 
QueryStreamu64KHR(Thread * thread,Display * display,Stream * streamObject,EGLenum attribute,EGLuint64KHR * value)508 EGLBoolean QueryStreamu64KHR(Thread *thread,
509                              Display *display,
510                              Stream *streamObject,
511                              EGLenum attribute,
512                              EGLuint64KHR *value)
513 {
514     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglQueryStreamu64KHR",
515                                           GetDisplayIfValid(display), EGL_FALSE);
516     switch (attribute)
517     {
518         case EGL_PRODUCER_FRAME_KHR:
519             *value = streamObject->getProducerFrame();
520             break;
521         case EGL_CONSUMER_FRAME_KHR:
522             *value = streamObject->getConsumerFrame();
523             break;
524         default:
525             UNREACHABLE();
526     }
527 
528     thread->setSuccess();
529     return EGL_TRUE;
530 }
531 
QuerySurfacePointerANGLE(Thread * thread,Display * display,SurfaceID surfaceID,EGLint attribute,void ** value)532 EGLBoolean QuerySurfacePointerANGLE(Thread *thread,
533                                     Display *display,
534                                     SurfaceID surfaceID,
535                                     EGLint attribute,
536                                     void **value)
537 {
538     Surface *eglSurface = display->getSurface(surfaceID);
539 
540     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
541                                           "eglQuerySurfacePointerANGLE", GetDisplayIfValid(display),
542                                           EGL_FALSE);
543     Error error = eglSurface->querySurfacePointerANGLE(attribute, value);
544     if (error.isError())
545     {
546         thread->setError(error, "eglQuerySurfacePointerANGLE",
547                          GetSurfaceIfValid(display, surfaceID));
548         return EGL_FALSE;
549     }
550 
551     thread->setSuccess();
552     return EGL_TRUE;
553 }
554 
SetBlobCacheFuncsANDROID(Thread * thread,Display * display,EGLSetBlobFuncANDROID set,EGLGetBlobFuncANDROID get)555 void SetBlobCacheFuncsANDROID(Thread *thread,
556                               Display *display,
557                               EGLSetBlobFuncANDROID set,
558                               EGLGetBlobFuncANDROID get)
559 {
560     ANGLE_EGL_TRY_PREPARE_FOR_CALL(thread, display->prepareForCall(), "eglSetBlobCacheFuncsANDROID",
561                                    GetDisplayIfValid(display));
562     thread->setSuccess();
563     display->setBlobCacheFuncs(set, get);
564 }
565 
SignalSyncKHR(Thread * thread,Display * display,SyncID syncID,EGLenum mode)566 EGLBoolean SignalSyncKHR(Thread *thread, Display *display, SyncID syncID, EGLenum mode)
567 {
568     gl::Context *currentContext = thread->getContext();
569     Sync *syncObject            = display->getSync(syncID);
570     ANGLE_EGL_TRY_RETURN(thread, syncObject->signal(display, currentContext, mode),
571                          "eglSignalSyncKHR", GetSyncIfValid(display, syncID), EGL_FALSE);
572 
573     thread->setSuccess();
574     return EGL_TRUE;
575 }
576 
StreamAttribKHR(Thread * thread,Display * display,Stream * streamObject,EGLenum attribute,EGLint value)577 EGLBoolean StreamAttribKHR(Thread *thread,
578                            Display *display,
579                            Stream *streamObject,
580                            EGLenum attribute,
581                            EGLint value)
582 {
583     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglStreamAttribKHR",
584                                           GetDisplayIfValid(display), EGL_FALSE);
585     switch (attribute)
586     {
587         case EGL_CONSUMER_LATENCY_USEC_KHR:
588             streamObject->setConsumerLatency(value);
589             break;
590         case EGL_CONSUMER_ACQUIRE_TIMEOUT_USEC_KHR:
591             streamObject->setConsumerAcquireTimeout(value);
592             break;
593         default:
594             UNREACHABLE();
595     }
596 
597     thread->setSuccess();
598     return EGL_TRUE;
599 }
600 
StreamConsumerAcquireKHR(Thread * thread,Display * display,Stream * streamObject)601 EGLBoolean StreamConsumerAcquireKHR(Thread *thread, Display *display, Stream *streamObject)
602 {
603     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
604                                           "eglStreamConsumerAcquireKHR", GetDisplayIfValid(display),
605                                           EGL_FALSE);
606     ANGLE_EGL_TRY_RETURN(thread, streamObject->consumerAcquire(thread->getContext()),
607                          "eglStreamConsumerAcquireKHR", GetStreamIfValid(display, streamObject),
608                          EGL_FALSE);
609     thread->setSuccess();
610     return EGL_TRUE;
611 }
612 
StreamConsumerGLTextureExternalKHR(Thread * thread,Display * display,Stream * streamObject)613 EGLBoolean StreamConsumerGLTextureExternalKHR(Thread *thread,
614                                               Display *display,
615                                               Stream *streamObject)
616 {
617     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
618                                           "eglStreamConsumerGLTextureExternalKHR",
619                                           GetDisplayIfValid(display), EGL_FALSE);
620     ANGLE_EGL_TRY_RETURN(
621         thread, streamObject->createConsumerGLTextureExternal(AttributeMap(), thread->getContext()),
622         "eglStreamConsumerGLTextureExternalKHR", GetStreamIfValid(display, streamObject),
623         EGL_FALSE);
624     thread->setSuccess();
625     return EGL_TRUE;
626 }
627 
StreamConsumerGLTextureExternalAttribsNV(Thread * thread,Display * display,Stream * streamObject,const AttributeMap & attributes)628 EGLBoolean StreamConsumerGLTextureExternalAttribsNV(Thread *thread,
629                                                     Display *display,
630                                                     Stream *streamObject,
631                                                     const AttributeMap &attributes)
632 {
633     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
634                                           "eglStreamConsumerGLTextureExternalAttribsNV",
635                                           GetDisplayIfValid(display), EGL_FALSE);
636 
637     gl::Context *context = gl::GetValidGlobalContext();
638     ANGLE_EGL_TRY_RETURN(thread, streamObject->createConsumerGLTextureExternal(attributes, context),
639                          "eglStreamConsumerGLTextureExternalAttribsNV",
640                          GetStreamIfValid(display, streamObject), EGL_FALSE);
641     thread->setSuccess();
642     return EGL_TRUE;
643 }
644 
StreamConsumerReleaseKHR(Thread * thread,Display * display,Stream * streamObject)645 EGLBoolean StreamConsumerReleaseKHR(Thread *thread, Display *display, Stream *streamObject)
646 {
647     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
648                                           "eglStreamConsumerReleaseKHR", GetDisplayIfValid(display),
649                                           EGL_FALSE);
650 
651     gl::Context *context = gl::GetValidGlobalContext();
652     ANGLE_EGL_TRY_RETURN(thread, streamObject->consumerRelease(context),
653                          "eglStreamConsumerReleaseKHR", GetStreamIfValid(display, streamObject),
654                          EGL_FALSE);
655     thread->setSuccess();
656     return EGL_TRUE;
657 }
658 
SwapBuffersWithDamageKHR(Thread * thread,Display * display,SurfaceID surfaceID,const EGLint * rects,EGLint n_rects)659 EGLBoolean SwapBuffersWithDamageKHR(Thread *thread,
660                                     Display *display,
661                                     SurfaceID surfaceID,
662                                     const EGLint *rects,
663                                     EGLint n_rects)
664 {
665     Surface *eglSurface = display->getSurface(surfaceID);
666 
667     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
668                                           "eglSwapBuffersWithDamageKHR", GetDisplayIfValid(display),
669                                           EGL_FALSE);
670     ANGLE_EGL_TRY_RETURN(thread, eglSurface->swapWithDamage(thread->getContext(), rects, n_rects),
671                          "eglSwapBuffersWithDamageKHR", GetSurfaceIfValid(display, surfaceID),
672                          EGL_FALSE);
673 
674     thread->setSuccess();
675     return EGL_TRUE;
676 }
677 
PrepareSwapBuffersANGLE(Thread * thread,Display * display,SurfaceID surfaceID)678 EGLBoolean PrepareSwapBuffersANGLE(Thread *thread, Display *display, SurfaceID surfaceID)
679 {
680     Surface *eglSurface = display->getSurface(surfaceID);
681 
682     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
683                                           "eglPrepareSwapBuffersANGLE", GetDisplayIfValid(display),
684                                           EGL_FALSE);
685     ANGLE_EGL_TRY_RETURN(thread, eglSurface->prepareSwap(thread->getContext()),
686                          "eglPrepareSwapBuffersANGLE", eglSurface, EGL_FALSE);
687 
688     thread->setSuccess();
689     return EGL_TRUE;
690 }
691 
WaitSyncKHR(Thread * thread,Display * display,SyncID syncID,EGLint flags)692 EGLint WaitSyncKHR(Thread *thread, Display *display, SyncID syncID, EGLint flags)
693 {
694     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglWaitSync",
695                                           GetDisplayIfValid(display), EGL_FALSE);
696     gl::Context *currentContext = thread->getContext();
697     Sync *syncObject            = display->getSync(syncID);
698     ANGLE_EGL_TRY_RETURN(thread, syncObject->serverWait(display, currentContext, flags),
699                          "eglWaitSync", GetSyncIfValid(display, syncID), EGL_FALSE);
700 
701     thread->setSuccess();
702     return EGL_TRUE;
703 }
704 
CreateDeviceANGLE(Thread * thread,EGLint device_type,void * native_device,const EGLAttrib * attrib_list)705 EGLDeviceEXT CreateDeviceANGLE(Thread *thread,
706                                EGLint device_type,
707                                void *native_device,
708                                const EGLAttrib *attrib_list)
709 {
710     Device *device = nullptr;
711     ANGLE_EGL_TRY_RETURN(thread, Device::CreateDevice(device_type, native_device, &device),
712                          "eglCreateDeviceANGLE", GetThreadIfValid(thread), EGL_NO_DEVICE_EXT);
713 
714     thread->setSuccess();
715     return device;
716 }
717 
ReleaseDeviceANGLE(Thread * thread,Device * dev)718 EGLBoolean ReleaseDeviceANGLE(Thread *thread, Device *dev)
719 {
720     SafeDelete(dev);
721 
722     thread->setSuccess();
723     return EGL_TRUE;
724 }
725 
CreateStreamProducerD3DTextureANGLE(Thread * thread,Display * display,Stream * streamObject,const AttributeMap & attributes)726 EGLBoolean CreateStreamProducerD3DTextureANGLE(Thread *thread,
727                                                Display *display,
728                                                Stream *streamObject,
729                                                const AttributeMap &attributes)
730 {
731     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
732                                           "eglCreateStreamProducerD3DTextureANGLE",
733                                           GetDisplayIfValid(display), EGL_FALSE);
734     ANGLE_EGL_TRY_RETURN(thread, streamObject->createProducerD3D11Texture(attributes),
735                          "eglCreateStreamProducerD3DTextureANGLE",
736                          GetStreamIfValid(display, streamObject), EGL_FALSE);
737     thread->setSuccess();
738     return EGL_TRUE;
739 }
740 
StreamPostD3DTextureANGLE(Thread * thread,Display * display,Stream * streamObject,void * texture,const AttributeMap & attributes)741 EGLBoolean StreamPostD3DTextureANGLE(Thread *thread,
742                                      Display *display,
743                                      Stream *streamObject,
744                                      void *texture,
745                                      const AttributeMap &attributes)
746 {
747     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
748                                           "eglStreamPostD3DTextureANGLE",
749                                           GetDisplayIfValid(display), EGL_FALSE);
750     ANGLE_EGL_TRY_RETURN(thread, streamObject->postD3D11Texture(texture, attributes),
751                          "eglStreamPostD3DTextureANGLE", GetStreamIfValid(display, streamObject),
752                          EGL_FALSE);
753     thread->setSuccess();
754     return EGL_TRUE;
755 }
756 
GetMscRateANGLE(Thread * thread,Display * display,SurfaceID surfaceID,EGLint * numerator,EGLint * denominator)757 EGLBoolean GetMscRateANGLE(Thread *thread,
758                            Display *display,
759                            SurfaceID surfaceID,
760                            EGLint *numerator,
761                            EGLint *denominator)
762 {
763     Surface *eglSurface = display->getSurface(surfaceID);
764 
765     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglGetMscRateANGLE",
766                                           GetDisplayIfValid(display), EGL_FALSE);
767     ANGLE_EGL_TRY_RETURN(thread, eglSurface->getMscRate(numerator, denominator),
768                          "eglGetMscRateANGLE", GetSurfaceIfValid(display, surfaceID), EGL_FALSE);
769 
770     thread->setSuccess();
771     return EGL_TRUE;
772 }
773 
GetSyncValuesCHROMIUM(Thread * thread,Display * display,SurfaceID surfaceID,EGLuint64KHR * ust,EGLuint64KHR * msc,EGLuint64KHR * sbc)774 EGLBoolean GetSyncValuesCHROMIUM(Thread *thread,
775                                  Display *display,
776                                  SurfaceID surfaceID,
777                                  EGLuint64KHR *ust,
778                                  EGLuint64KHR *msc,
779                                  EGLuint64KHR *sbc)
780 {
781     Surface *eglSurface = display->getSurface(surfaceID);
782 
783     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
784                                           "eglGetSyncValuesCHROMIUM", GetDisplayIfValid(display),
785                                           EGL_FALSE);
786     ANGLE_EGL_TRY_RETURN(thread, eglSurface->getSyncValues(ust, msc, sbc),
787                          "eglGetSyncValuesCHROMIUM", GetSurfaceIfValid(display, surfaceID),
788                          EGL_FALSE);
789 
790     thread->setSuccess();
791     return EGL_TRUE;
792 }
793 
ProgramCacheGetAttribANGLE(Thread * thread,Display * display,EGLenum attrib)794 EGLint ProgramCacheGetAttribANGLE(Thread *thread, Display *display, EGLenum attrib)
795 {
796     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
797                                           "eglProgramCacheGetAttribANGLE",
798                                           GetDisplayIfValid(display), 0);
799     thread->setSuccess();
800     return display->programCacheGetAttrib(attrib);
801 }
802 
ProgramCacheQueryANGLE(Thread * thread,Display * display,EGLint index,void * key,EGLint * keysize,void * binary,EGLint * binarysize)803 void ProgramCacheQueryANGLE(Thread *thread,
804                             Display *display,
805                             EGLint index,
806                             void *key,
807                             EGLint *keysize,
808                             void *binary,
809                             EGLint *binarysize)
810 {
811     ANGLE_EGL_TRY_PREPARE_FOR_CALL(thread, display->prepareForCall(), "eglProgramCacheQueryANGLE",
812                                    GetDisplayIfValid(display));
813     ANGLE_EGL_TRY(thread, display->programCacheQuery(index, key, keysize, binary, binarysize),
814                   "eglProgramCacheQueryANGLE", GetDisplayIfValid(display));
815 
816     thread->setSuccess();
817 }
818 
ProgramCachePopulateANGLE(Thread * thread,Display * display,const void * key,EGLint keysize,const void * binary,EGLint binarysize)819 void ProgramCachePopulateANGLE(Thread *thread,
820                                Display *display,
821                                const void *key,
822                                EGLint keysize,
823                                const void *binary,
824                                EGLint binarysize)
825 {
826     ANGLE_EGL_TRY_PREPARE_FOR_CALL(thread, display->prepareForCall(),
827                                    "eglProgramCachePopulateANGLE", GetDisplayIfValid(display));
828     ANGLE_EGL_TRY(thread, display->programCachePopulate(key, keysize, binary, binarysize),
829                   "eglProgramCachePopulateANGLE", GetDisplayIfValid(display));
830 
831     thread->setSuccess();
832 }
833 
ProgramCacheResizeANGLE(Thread * thread,Display * display,EGLint limit,EGLint mode)834 EGLint ProgramCacheResizeANGLE(Thread *thread, Display *display, EGLint limit, EGLint mode)
835 {
836     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
837                                           "eglProgramCacheResizeANGLE", GetDisplayIfValid(display),
838                                           0);
839     thread->setSuccess();
840     return display->programCacheResize(limit, mode);
841 }
842 
QueryStringiANGLE(Thread * thread,Display * display,EGLint name,EGLint index)843 const char *QueryStringiANGLE(Thread *thread, Display *display, EGLint name, EGLint index)
844 {
845     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglQueryStringiANGLE",
846                                           GetDisplayIfValid(display), nullptr);
847     thread->setSuccess();
848     return display->queryStringi(name, index);
849 }
850 
SwapBuffersWithFrameTokenANGLE(Thread * thread,Display * display,SurfaceID surfaceID,EGLFrameTokenANGLE frametoken)851 EGLBoolean SwapBuffersWithFrameTokenANGLE(Thread *thread,
852                                           Display *display,
853                                           SurfaceID surfaceID,
854                                           EGLFrameTokenANGLE frametoken)
855 {
856     Surface *eglSurface = display->getSurface(surfaceID);
857 
858     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
859                                           "eglSwapBuffersWithFrameTokenANGLE",
860                                           GetDisplayIfValid(display), EGL_FALSE);
861     ANGLE_EGL_TRY_RETURN(thread, eglSurface->swapWithFrameToken(thread->getContext(), frametoken),
862                          "eglSwapBuffersWithFrameTokenANGLE", GetDisplayIfValid(display),
863                          EGL_FALSE);
864 
865     thread->setSuccess();
866     return EGL_TRUE;
867 }
868 
ReleaseHighPowerGPUANGLE(Thread * thread,Display * display,gl::ContextID contextID)869 void ReleaseHighPowerGPUANGLE(Thread *thread, Display *display, gl::ContextID contextID)
870 {
871     gl::Context *context = display->getContext(contextID);
872     ANGLE_EGL_TRY_PREPARE_FOR_CALL(thread, display->prepareForCall(), "eglReleaseHighPowerGPUANGLE",
873                                    GetDisplayIfValid(display));
874     ANGLE_EGL_TRY(thread, context->releaseHighPowerGPU(), "eglReleaseHighPowerGPUANGLE",
875                   GetDisplayIfValid(display));
876 
877     thread->setSuccess();
878 }
879 
ReacquireHighPowerGPUANGLE(Thread * thread,Display * display,gl::ContextID contextID)880 void ReacquireHighPowerGPUANGLE(Thread *thread, Display *display, gl::ContextID contextID)
881 {
882     gl::Context *context = display->getContext(contextID);
883     ANGLE_EGL_TRY_PREPARE_FOR_CALL(thread, display->prepareForCall(),
884                                    "eglReacquireHighPowerGPUANGLE", GetDisplayIfValid(display));
885     ANGLE_EGL_TRY(thread, context->reacquireHighPowerGPU(), "eglReacquireHighPowerGPUANGLE",
886                   GetDisplayIfValid(display));
887 
888     thread->setSuccess();
889 }
890 
HandleGPUSwitchANGLE(Thread * thread,Display * display)891 void HandleGPUSwitchANGLE(Thread *thread, Display *display)
892 {
893     ANGLE_EGL_TRY_PREPARE_FOR_CALL(thread, display->prepareForCall(), "eglHandleGPUSwitchANGLE",
894                                    GetDisplayIfValid(display));
895     ANGLE_EGL_TRY(thread, display->handleGPUSwitch(), "eglHandleGPUSwitchANGLE",
896                   GetDisplayIfValid(display));
897 
898     thread->setSuccess();
899 }
900 
ForceGPUSwitchANGLE(Thread * thread,Display * display,EGLint gpuIDHigh,EGLint gpuIDLow)901 void ForceGPUSwitchANGLE(Thread *thread, Display *display, EGLint gpuIDHigh, EGLint gpuIDLow)
902 {
903     ANGLE_EGL_TRY_PREPARE_FOR_CALL(thread, display->prepareForCall(), "eglForceGPUSwitchANGLE",
904                                    GetDisplayIfValid(display));
905     ANGLE_EGL_TRY(thread, display->forceGPUSwitch(gpuIDHigh, gpuIDLow), "eglForceGPUSwitchANGLE",
906                   GetDisplayIfValid(display));
907 
908     thread->setSuccess();
909 }
910 
WaitUntilWorkScheduledANGLE(Thread * thread,Display * display)911 void WaitUntilWorkScheduledANGLE(Thread *thread, Display *display)
912 {
913     ANGLE_EGL_TRY_PREPARE_FOR_CALL(thread, display->prepareForCall(),
914                                    "eglWaitUntilWorkScheduledANGLE", GetDisplayIfValid(display));
915     ANGLE_EGL_TRY(thread, display->waitUntilWorkScheduled(), "eglWaitUntilWorkScheduledANGLE",
916                   GetDisplayIfValid(display));
917 
918     thread->setSuccess();
919 }
920 
QueryDisplayAttribANGLE(Thread * thread,Display * display,EGLint attribute,EGLAttrib * value)921 EGLBoolean QueryDisplayAttribANGLE(Thread *thread,
922                                    Display *display,
923                                    EGLint attribute,
924                                    EGLAttrib *value)
925 {
926     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
927                                           "eglQueryDisplayAttribEXT", GetDisplayIfValid(display),
928                                           EGL_FALSE);
929     *value = display->queryAttrib(attribute);
930     thread->setSuccess();
931     return EGL_TRUE;
932 }
933 
LockSurfaceKHR(Thread * thread,egl::Display * display,SurfaceID surfaceID,const AttributeMap & attributes)934 EGLBoolean LockSurfaceKHR(Thread *thread,
935                           egl::Display *display,
936                           SurfaceID surfaceID,
937                           const AttributeMap &attributes)
938 {
939     Surface *surface = display->getSurface(surfaceID);
940 
941     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglLockSurfaceKHR",
942                                           GetDisplayIfValid(display), EGL_FALSE);
943     ANGLE_EGL_TRY_RETURN(thread, surface->lockSurfaceKHR(display, attributes), "eglLockSurfaceKHR",
944                          GetSurfaceIfValid(display, surfaceID), EGL_FALSE);
945     thread->setSuccess();
946     return EGL_TRUE;
947 }
948 
UnlockSurfaceKHR(Thread * thread,egl::Display * display,SurfaceID surfaceID)949 EGLBoolean UnlockSurfaceKHR(Thread *thread, egl::Display *display, SurfaceID surfaceID)
950 {
951     Surface *surface = display->getSurface(surfaceID);
952 
953     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglUnlockSurfaceKHR",
954                                           GetDisplayIfValid(display), EGL_FALSE);
955     ANGLE_EGL_TRY_RETURN(thread, surface->unlockSurfaceKHR(display), "eglQuerySurface64KHR",
956                          GetSurfaceIfValid(display, surfaceID), EGL_FALSE);
957     thread->setSuccess();
958     return EGL_TRUE;
959 }
960 
QuerySurface64KHR(Thread * thread,egl::Display * display,SurfaceID surfaceID,EGLint attribute,EGLAttribKHR * value)961 EGLBoolean QuerySurface64KHR(Thread *thread,
962                              egl::Display *display,
963                              SurfaceID surfaceID,
964                              EGLint attribute,
965                              EGLAttribKHR *value)
966 {
967     Surface *surface = display->getSurface(surfaceID);
968 
969     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(), "eglQuerySurface64KHR",
970                                           GetDisplayIfValid(display), EGL_FALSE);
971     ANGLE_EGL_TRY_RETURN(
972         thread, QuerySurfaceAttrib64KHR(display, thread->getContext(), surface, attribute, value),
973         "eglQuerySurface64KHR", GetSurfaceIfValid(display, surfaceID), EGL_FALSE);
974     thread->setSuccess();
975     return EGL_TRUE;
976 }
977 
ExportVkImageANGLE(Thread * thread,egl::Display * display,egl::ImageID imageID,void * vk_image,void * vk_image_create_info)978 EGLBoolean ExportVkImageANGLE(Thread *thread,
979                               egl::Display *display,
980                               egl::ImageID imageID,
981                               void *vk_image,
982                               void *vk_image_create_info)
983 {
984     Image *image = display->getImage(imageID);
985 
986     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
987                                           "eglExportVkImageANGLE", GetDisplayIfValid(display),
988                                           EGL_FALSE);
989     ANGLE_EGL_TRY_RETURN(thread, image->exportVkImage(vk_image, vk_image_create_info),
990                          "eglExportVkImageANGLE", GetImageIfValid(display, imageID), EGL_FALSE);
991 
992     thread->setSuccess();
993     return EGL_TRUE;
994 }
995 
SetDamageRegionKHR(Thread * thread,egl::Display * display,SurfaceID surfaceID,EGLint * rects,EGLint n_rects)996 EGLBoolean SetDamageRegionKHR(Thread *thread,
997                               egl::Display *display,
998                               SurfaceID surfaceID,
999                               EGLint *rects,
1000                               EGLint n_rects)
1001 {
1002     Surface *surface = display->getSurface(surfaceID);
1003 
1004     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
1005                                           "eglSetDamageRegionKHR", GetDisplayIfValid(display),
1006                                           EGL_FALSE);
1007     surface->setDamageRegion(rects, n_rects);
1008 
1009     thread->setSuccess();
1010     return EGL_TRUE;
1011 }
1012 
QueryDmaBufFormatsEXT(Thread * thread,egl::Display * display,EGLint max_formats,EGLint * formats,EGLint * num_formats)1013 EGLBoolean QueryDmaBufFormatsEXT(Thread *thread,
1014                                  egl::Display *display,
1015                                  EGLint max_formats,
1016                                  EGLint *formats,
1017                                  EGLint *num_formats)
1018 {
1019     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
1020                                           "eglQueryDmaBufFormatsEXT", GetDisplayIfValid(display),
1021                                           EGL_FALSE);
1022     ANGLE_EGL_TRY_RETURN(thread, display->queryDmaBufFormats(max_formats, formats, num_formats),
1023                          "eglQueryDmaBufFormatsEXT", GetDisplayIfValid(display), EGL_FALSE);
1024     thread->setSuccess();
1025     return EGL_TRUE;
1026 }
1027 
QueryDmaBufModifiersEXT(Thread * thread,egl::Display * display,EGLint format,EGLint max_modifiers,EGLuint64KHR * modifiers,EGLBoolean * external_only,EGLint * num_modifiers)1028 EGLBoolean QueryDmaBufModifiersEXT(Thread *thread,
1029                                    egl::Display *display,
1030                                    EGLint format,
1031                                    EGLint max_modifiers,
1032                                    EGLuint64KHR *modifiers,
1033                                    EGLBoolean *external_only,
1034                                    EGLint *num_modifiers)
1035 {
1036     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
1037                                           "eglQueryDmaBufModifiersEXT", GetDisplayIfValid(display),
1038                                           EGL_FALSE);
1039     ANGLE_EGL_TRY_RETURN(thread,
1040                          display->queryDmaBufModifiers(format, max_modifiers, modifiers,
1041                                                        external_only, num_modifiers),
1042                          "eglQueryDmaBufModifiersEXT", GetDisplayIfValid(display), EGL_FALSE);
1043     thread->setSuccess();
1044     return EGL_TRUE;
1045 }
1046 
CopyMetalSharedEventANGLE(Thread * thread,Display * display,SyncID syncID)1047 void *CopyMetalSharedEventANGLE(Thread *thread, Display *display, SyncID syncID)
1048 {
1049     ANGLE_EGL_TRY_PREPARE_FOR_CALL_RETURN(thread, display->prepareForCall(),
1050                                           "eglCopyMetalSharedEventANGLE",
1051                                           GetDisplayIfValid(display), nullptr);
1052     void *result     = nullptr;
1053     Sync *syncObject = display->getSync(syncID);
1054     ANGLE_EGL_TRY_RETURN(thread, syncObject->copyMetalSharedEventANGLE(display, &result),
1055                          "eglCopyMetalSharedEventANGLE", GetSyncIfValid(display, syncID), nullptr);
1056 
1057     thread->setSuccess();
1058     return result;
1059 }
1060 
AcquireExternalContextANGLE(Thread * thread,egl::Display * display,SurfaceID drawAndReadPacked)1061 void AcquireExternalContextANGLE(Thread *thread, egl::Display *display, SurfaceID drawAndReadPacked)
1062 {
1063     Surface *eglSurface = display->getSurface(drawAndReadPacked);
1064 
1065     ANGLE_EGL_TRY_PREPARE_FOR_CALL(thread, display->prepareForCall(),
1066                                    "eglAcquireExternalContextANGLE", GetDisplayIfValid(display));
1067     ANGLE_EGL_TRY(thread, thread->getContext()->acquireExternalContext(eglSurface),
1068                   "eglAcquireExternalContextANGLE", GetDisplayIfValid(display));
1069 
1070     thread->setSuccess();
1071 }
1072 
ReleaseExternalContextANGLE(Thread * thread,egl::Display * display)1073 void ReleaseExternalContextANGLE(Thread *thread, egl::Display *display)
1074 {
1075     ANGLE_EGL_TRY_PREPARE_FOR_CALL(thread, display->prepareForCall(),
1076                                    "eglReleaseExternalContextANGLE", GetDisplayIfValid(display));
1077     ANGLE_EGL_TRY(thread, thread->getContext()->releaseExternalContext(),
1078                   "eglReleaseExternalContextANGLE", GetDisplayIfValid(display));
1079 
1080     thread->setSuccess();
1081 }
1082 
SetValidationEnabledANGLE(Thread * thread,EGLBoolean validationState)1083 void SetValidationEnabledANGLE(Thread *thread, EGLBoolean validationState)
1084 {
1085     SetEGLValidationEnabled(validationState != EGL_FALSE);
1086     thread->setSuccess();
1087 }
1088 
1089 }  // namespace egl
1090