blob: d86e80b9705f6e34ed1c9b8e8b710f08336ecd63 [file] [log] [blame]
Nicolas Capens0bac2852016-05-07 06:09:58 -04001// Copyright 2016 The SwiftShader Authors. All Rights Reserved.
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15// main.cpp: DLL entry point and management of thread-local data.
16
17#include "main.h"
18
19#include "libEGL.hpp"
20#include "Context.hpp"
Nicolas Capens31c07a32017-06-13 23:44:13 -040021#include "Surface.hpp"
Chris Forbes1aae88c2018-09-11 17:31:52 -070022#include "Display.h"
Nicolas Capens0bac2852016-05-07 06:09:58 -040023
24#include "resource.h"
25#include "Common/Thread.hpp"
26#include "Common/SharedLibrary.hpp"
27#include "common/debug.h"
28
29#include <EGL/eglext.h>
30
31static sw::Thread::LocalStorageKey currentTLS = TLS_OUT_OF_INDEXES;
32
33#if !defined(_MSC_VER)
34#define CONSTRUCTOR __attribute__((constructor))
35#define DESTRUCTOR __attribute__((destructor))
36#else
37#define CONSTRUCTOR
38#define DESTRUCTOR
39#endif
40
Nicolas Capensaf93a422016-06-12 16:11:25 -040041namespace egl
42{
David Rim10bcdb42018-04-06 17:48:41 +090043void releaseCurrent(void *storage)
44{
45 // This pthread destructor is called after the TLS is already reset to NULL,
46 // so we can't call EGL functions here to do the cleanup.
47
48 Current *current = (Current*)storage;
49
50 if(current)
51 {
52 if(current->drawSurface)
53 {
54 current->drawSurface->release();
55 }
56
57 if(current->readSurface)
58 {
59 current->readSurface->release();
60 }
61
62 if(current->context)
63 {
64 current->context->release();
65 }
66
67 free(current);
68 }
69}
70
Nicolas Capens420b64d2017-07-07 17:01:16 -040071Current *attachThread()
Nicolas Capens0bac2852016-05-07 06:09:58 -040072{
73 TRACE("()");
74
Nicolas Capens420b64d2017-07-07 17:01:16 -040075 if(currentTLS == TLS_OUT_OF_INDEXES)
Nicolas Capens0bac2852016-05-07 06:09:58 -040076 {
David Rim10bcdb42018-04-06 17:48:41 +090077 currentTLS = sw::Thread::allocateLocalStorageKey(releaseCurrent);
Nicolas Capens0bac2852016-05-07 06:09:58 -040078 }
Nicolas Capens420b64d2017-07-07 17:01:16 -040079
Nicolas Capens4ad365b2017-09-12 16:39:42 -040080 Current *current = (Current*)sw::Thread::allocateLocalStorage(currentTLS, sizeof(Current));
Nicolas Capens420b64d2017-07-07 17:01:16 -040081
82 current->error = EGL_SUCCESS;
83 current->API = EGL_OPENGL_ES_API;
84 current->context = nullptr;
85 current->drawSurface = nullptr;
86 current->readSurface = nullptr;
87
88 return current;
Nicolas Capens0bac2852016-05-07 06:09:58 -040089}
90
Nicolas Capensaf93a422016-06-12 16:11:25 -040091void detachThread()
Nicolas Capens0bac2852016-05-07 06:09:58 -040092{
93 TRACE("()");
94
Nicolas Capenscc5c7d92016-06-13 14:35:11 -040095 eglMakeCurrent(EGL_NO_DISPLAY, EGL_NO_CONTEXT, EGL_NO_SURFACE, EGL_NO_SURFACE);
96
Nicolas Capens4ad365b2017-09-12 16:39:42 -040097 sw::Thread::freeLocalStorage(currentTLS);
Nicolas Capens0bac2852016-05-07 06:09:58 -040098}
99
Nicolas Capensaf93a422016-06-12 16:11:25 -0400100CONSTRUCTOR void attachProcess()
Nicolas Capens0bac2852016-05-07 06:09:58 -0400101{
102 TRACE("()");
103
104 #if !defined(ANGLE_DISABLE_TRACE) && defined(TRACE_OUTPUT_FILE)
105 FILE *debug = fopen(TRACE_OUTPUT_FILE, "rt");
106
107 if(debug)
108 {
109 fclose(debug);
110 debug = fopen(TRACE_OUTPUT_FILE, "wt"); // Erase
111 fclose(debug);
112 }
113 #endif
114
Nicolas Capensaf93a422016-06-12 16:11:25 -0400115 attachThread();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400116}
117
Nicolas Capensaf93a422016-06-12 16:11:25 -0400118DESTRUCTOR void detachProcess()
Nicolas Capens0bac2852016-05-07 06:09:58 -0400119{
120 TRACE("()");
121
Nicolas Capensaf93a422016-06-12 16:11:25 -0400122 detachThread();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400123 sw::Thread::freeLocalStorageKey(currentTLS);
124}
Nicolas Capensaf93a422016-06-12 16:11:25 -0400125}
Nicolas Capens0bac2852016-05-07 06:09:58 -0400126
127#if defined(_WIN32)
Alexis Hetu8e942eb2017-03-16 10:53:01 -0400128#ifdef DEBUGGER_WAIT_DIALOG
Nicolas Capens0bac2852016-05-07 06:09:58 -0400129static INT_PTR CALLBACK DebuggerWaitDialogProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
130{
131 RECT rect;
132
133 switch(uMsg)
134 {
135 case WM_INITDIALOG:
136 GetWindowRect(GetDesktopWindow(), &rect);
137 SetWindowPos(hwnd, HWND_TOP, rect.right / 2, rect.bottom / 2, 0, 0, SWP_NOSIZE);
138 SetTimer(hwnd, 1, 100, NULL);
139 return TRUE;
140 case WM_COMMAND:
141 if(LOWORD(wParam) == IDCANCEL)
142 {
143 EndDialog(hwnd, 0);
144 }
145 break;
146 case WM_TIMER:
147 if(IsDebuggerPresent())
148 {
149 EndDialog(hwnd, 0);
150 }
151 }
152
153 return FALSE;
154}
155
156static void WaitForDebugger(HINSTANCE instance)
157{
158 if(!IsDebuggerPresent())
159 {
160 HRSRC dialog = FindResource(instance, MAKEINTRESOURCE(IDD_DIALOG1), RT_DIALOG);
161 DLGTEMPLATE *dialogTemplate = (DLGTEMPLATE*)LoadResource(instance, dialog);
162 DialogBoxIndirect(instance, dialogTemplate, NULL, DebuggerWaitDialogProc);
163 }
164}
Alexis Hetue97a31e2016-11-14 14:10:47 -0500165#endif
Nicolas Capens0bac2852016-05-07 06:09:58 -0400166
167extern "C" BOOL WINAPI DllMain(HINSTANCE instance, DWORD reason, LPVOID reserved)
168{
169 switch(reason)
170 {
171 case DLL_PROCESS_ATTACH:
Alexis Hetu38182312017-03-16 11:46:16 -0400172 #ifdef DEBUGGER_WAIT_DIALOG
Nicolas Capense43cda52019-03-19 00:16:20 -0400173 {
174 char disable_debugger_wait_dialog[] = "0";
175 GetEnvironmentVariable("SWIFTSHADER_DISABLE_DEBUGGER_WAIT_DIALOG", disable_debugger_wait_dialog, sizeof(disable_debugger_wait_dialog));
176
177 if(disable_debugger_wait_dialog[0] != '1')
178 {
179 WaitForDebugger(instance);
180 }
181 }
Nicolas Capens0bac2852016-05-07 06:09:58 -0400182 #endif
Nicolas Capensaf93a422016-06-12 16:11:25 -0400183 egl::attachProcess();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400184 break;
185 case DLL_THREAD_ATTACH:
Nicolas Capensaf93a422016-06-12 16:11:25 -0400186 egl::attachThread();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400187 break;
188 case DLL_THREAD_DETACH:
Nicolas Capensaf93a422016-06-12 16:11:25 -0400189 egl::detachThread();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400190 break;
191 case DLL_PROCESS_DETACH:
Nicolas Capensaf93a422016-06-12 16:11:25 -0400192 egl::detachProcess();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400193 break;
194 default:
195 break;
196 }
197
198 return TRUE;
199}
200#endif
201
202namespace egl
203{
Nicolas Capensaf93a422016-06-12 16:11:25 -0400204static Current *getCurrent(void)
Nicolas Capens0bac2852016-05-07 06:09:58 -0400205{
206 Current *current = (Current*)sw::Thread::getLocalStorage(currentTLS);
207
208 if(!current)
209 {
Nicolas Capens420b64d2017-07-07 17:01:16 -0400210 current = attachThread();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400211 }
212
Nicolas Capens420b64d2017-07-07 17:01:16 -0400213 return current;
Nicolas Capens0bac2852016-05-07 06:09:58 -0400214}
215
216void setCurrentError(EGLint error)
217{
Nicolas Capensaf93a422016-06-12 16:11:25 -0400218 Current *current = getCurrent();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400219
220 current->error = error;
221}
222
223EGLint getCurrentError()
224{
Nicolas Capensaf93a422016-06-12 16:11:25 -0400225 Current *current = getCurrent();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400226
227 return current->error;
228}
229
230void setCurrentAPI(EGLenum API)
231{
Nicolas Capensaf93a422016-06-12 16:11:25 -0400232 Current *current = getCurrent();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400233
234 current->API = API;
235}
236
237EGLenum getCurrentAPI()
238{
Nicolas Capensaf93a422016-06-12 16:11:25 -0400239 Current *current = getCurrent();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400240
241 return current->API;
242}
243
Nicolas Capens0bac2852016-05-07 06:09:58 -0400244void setCurrentContext(egl::Context *ctx)
245{
Nicolas Capensaf93a422016-06-12 16:11:25 -0400246 Current *current = getCurrent();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400247
248 if(ctx)
249 {
250 ctx->addRef();
251 }
252
253 if(current->context)
254 {
255 current->context->release();
256 }
257
258 current->context = ctx;
259}
260
Nicolas Capens506cc5e2017-07-24 11:30:55 -0400261NO_SANITIZE_FUNCTION egl::Context *getCurrentContext()
Nicolas Capens0bac2852016-05-07 06:09:58 -0400262{
Nicolas Capensaf93a422016-06-12 16:11:25 -0400263 Current *current = getCurrent();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400264
265 return current->context;
266}
267
268void setCurrentDrawSurface(egl::Surface *surface)
269{
Nicolas Capensaf93a422016-06-12 16:11:25 -0400270 Current *current = getCurrent();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400271
272 if(surface)
273 {
274 surface->addRef();
275 }
276
277 if(current->drawSurface)
278 {
279 current->drawSurface->release();
280 }
281
282 current->drawSurface = surface;
283}
284
285egl::Surface *getCurrentDrawSurface()
286{
Nicolas Capensaf93a422016-06-12 16:11:25 -0400287 Current *current = getCurrent();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400288
289 return current->drawSurface;
290}
291
292void setCurrentReadSurface(egl::Surface *surface)
293{
Nicolas Capensaf93a422016-06-12 16:11:25 -0400294 Current *current = getCurrent();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400295
296 if(surface)
297 {
298 surface->addRef();
299 }
300
301 if(current->readSurface)
302 {
303 current->readSurface->release();
304 }
305
306 current->readSurface = surface;
307}
308
309egl::Surface *getCurrentReadSurface()
310{
Nicolas Capensaf93a422016-06-12 16:11:25 -0400311 Current *current = getCurrent();
Nicolas Capens0bac2852016-05-07 06:09:58 -0400312
313 return current->readSurface;
314}
315
316void error(EGLint errorCode)
317{
318 egl::setCurrentError(errorCode);
319
320 if(errorCode != EGL_SUCCESS)
321 {
322 switch(errorCode)
323 {
324 case EGL_NOT_INITIALIZED: TRACE("\t! Error generated: not initialized\n"); break;
325 case EGL_BAD_ACCESS: TRACE("\t! Error generated: bad access\n"); break;
326 case EGL_BAD_ALLOC: TRACE("\t! Error generated: bad alloc\n"); break;
327 case EGL_BAD_ATTRIBUTE: TRACE("\t! Error generated: bad attribute\n"); break;
328 case EGL_BAD_CONFIG: TRACE("\t! Error generated: bad config\n"); break;
329 case EGL_BAD_CONTEXT: TRACE("\t! Error generated: bad context\n"); break;
330 case EGL_BAD_CURRENT_SURFACE: TRACE("\t! Error generated: bad current surface\n"); break;
331 case EGL_BAD_DISPLAY: TRACE("\t! Error generated: bad display\n"); break;
332 case EGL_BAD_MATCH: TRACE("\t! Error generated: bad match\n"); break;
333 case EGL_BAD_NATIVE_PIXMAP: TRACE("\t! Error generated: bad native pixmap\n"); break;
334 case EGL_BAD_NATIVE_WINDOW: TRACE("\t! Error generated: bad native window\n"); break;
335 case EGL_BAD_PARAMETER: TRACE("\t! Error generated: bad parameter\n"); break;
336 case EGL_BAD_SURFACE: TRACE("\t! Error generated: bad surface\n"); break;
337 case EGL_CONTEXT_LOST: TRACE("\t! Error generated: context lost\n"); break;
338 default: TRACE("\t! Error generated: <0x%X>\n", errorCode); break;
339 }
340 }
341}
Chris Forbes1aae88c2018-09-11 17:31:52 -0700342
343sw::MutexLock *getDisplayLock(EGLDisplay dpy)
344{
345 auto display = Display::get(dpy);
346 if (!display) return nullptr;
347 return display->getLock();
348}
Nicolas Capens0bac2852016-05-07 06:09:58 -0400349}
350
351namespace egl
352{
353EGLint GetError(void);
354EGLDisplay GetDisplay(EGLNativeDisplayType display_id);
355EGLBoolean Initialize(EGLDisplay dpy, EGLint *major, EGLint *minor);
356EGLBoolean Terminate(EGLDisplay dpy);
357const char *QueryString(EGLDisplay dpy, EGLint name);
358EGLBoolean GetConfigs(EGLDisplay dpy, EGLConfig *configs, EGLint config_size, EGLint *num_config);
359EGLBoolean ChooseConfig(EGLDisplay dpy, const EGLint *attrib_list, EGLConfig *configs, EGLint config_size, EGLint *num_config);
360EGLBoolean GetConfigAttrib(EGLDisplay dpy, EGLConfig config, EGLint attribute, EGLint *value);
361EGLSurface CreateWindowSurface(EGLDisplay dpy, EGLConfig config, EGLNativeWindowType window, const EGLint *attrib_list);
362EGLSurface CreatePbufferSurface(EGLDisplay dpy, EGLConfig config, const EGLint *attrib_list);
363EGLSurface CreatePixmapSurface(EGLDisplay dpy, EGLConfig config, EGLNativePixmapType pixmap, const EGLint *attrib_list);
364EGLBoolean DestroySurface(EGLDisplay dpy, EGLSurface surface);
365EGLBoolean QuerySurface(EGLDisplay dpy, EGLSurface surface, EGLint attribute, EGLint *value);
366EGLBoolean BindAPI(EGLenum api);
367EGLenum QueryAPI(void);
368EGLBoolean WaitClient(void);
369EGLBoolean ReleaseThread(void);
370EGLSurface CreatePbufferFromClientBuffer(EGLDisplay dpy, EGLenum buftype, EGLClientBuffer buffer, EGLConfig config, const EGLint *attrib_list);
371EGLBoolean SurfaceAttrib(EGLDisplay dpy, EGLSurface surface, EGLint attribute, EGLint value);
372EGLBoolean BindTexImage(EGLDisplay dpy, EGLSurface surface, EGLint buffer);
373EGLBoolean ReleaseTexImage(EGLDisplay dpy, EGLSurface surface, EGLint buffer);
374EGLBoolean SwapInterval(EGLDisplay dpy, EGLint interval);
375EGLContext CreateContext(EGLDisplay dpy, EGLConfig config, EGLContext share_context, const EGLint *attrib_list);
376EGLBoolean DestroyContext(EGLDisplay dpy, EGLContext ctx);
377EGLBoolean MakeCurrent(EGLDisplay dpy, EGLSurface draw, EGLSurface read, EGLContext ctx);
378EGLContext GetCurrentContext(void);
379EGLSurface GetCurrentSurface(EGLint readdraw);
380EGLDisplay GetCurrentDisplay(void);
381EGLBoolean QueryContext(EGLDisplay dpy, EGLContext ctx, EGLint attribute, EGLint *value);
382EGLBoolean WaitGL(void);
383EGLBoolean WaitNative(EGLint engine);
384EGLBoolean SwapBuffers(EGLDisplay dpy, EGLSurface surface);
385EGLBoolean CopyBuffers(EGLDisplay dpy, EGLSurface surface, EGLNativePixmapType target);
386EGLImageKHR CreateImageKHR(EGLDisplay dpy, EGLContext ctx, EGLenum target, EGLClientBuffer buffer, const EGLint *attrib_list);
Nicolas Capens48908cb2018-01-08 13:07:14 -0500387EGLImageKHR CreateImage(EGLDisplay dpy, EGLContext ctx, EGLenum target, EGLClientBuffer buffer, const EGLAttrib *attrib_list);
Nicolas Capens0bac2852016-05-07 06:09:58 -0400388EGLBoolean DestroyImageKHR(EGLDisplay dpy, EGLImageKHR image);
389EGLDisplay GetPlatformDisplayEXT(EGLenum platform, void *native_display, const EGLint *attrib_list);
Nicolas Capens48908cb2018-01-08 13:07:14 -0500390EGLDisplay GetPlatformDisplay(EGLenum platform, void *native_display, const EGLAttrib *attrib_list);
Nicolas Capens0bac2852016-05-07 06:09:58 -0400391EGLSurface CreatePlatformWindowSurfaceEXT(EGLDisplay dpy, EGLConfig config, void *native_window, const EGLint *attrib_list);
Nicolas Capens48908cb2018-01-08 13:07:14 -0500392EGLSurface CreatePlatformWindowSurface(EGLDisplay dpy, EGLConfig config, void *native_window, const EGLAttrib *attrib_list);
Nicolas Capens0bac2852016-05-07 06:09:58 -0400393EGLSurface CreatePlatformPixmapSurfaceEXT(EGLDisplay dpy, EGLConfig config, void *native_pixmap, const EGLint *attrib_list);
Nicolas Capens48908cb2018-01-08 13:07:14 -0500394EGLSurface CreatePlatformPixmapSurface(EGLDisplay dpy, EGLConfig config, void *native_pixmap, const EGLAttrib *attrib_list);
Nicolas Capens0bac2852016-05-07 06:09:58 -0400395EGLSyncKHR CreateSyncKHR(EGLDisplay dpy, EGLenum type, const EGLint *attrib_list);
Nicolas Capens48908cb2018-01-08 13:07:14 -0500396EGLSyncKHR CreateSync(EGLDisplay dpy, EGLenum type, const EGLAttrib *attrib_list);
Nicolas Capens0bac2852016-05-07 06:09:58 -0400397EGLBoolean DestroySyncKHR(EGLDisplay dpy, EGLSyncKHR sync);
398EGLint ClientWaitSyncKHR(EGLDisplay dpy, EGLSyncKHR sync, EGLint flags, EGLTimeKHR timeout);
399EGLBoolean GetSyncAttribKHR(EGLDisplay dpy, EGLSyncKHR sync, EGLint attribute, EGLint *value);
Nicolas Capens48908cb2018-01-08 13:07:14 -0500400EGLBoolean GetSyncAttrib(EGLDisplay dpy, EGLSyncKHR sync, EGLint attribute, EGLAttrib *value);
Nicolas Capens0bac2852016-05-07 06:09:58 -0400401__eglMustCastToProperFunctionPointerType GetProcAddress(const char *procname);
402}
403
404extern "C"
405{
406EGLAPI EGLint EGLAPIENTRY eglGetError(void)
407{
408 return egl::GetError();
409}
410
411EGLAPI EGLDisplay EGLAPIENTRY eglGetDisplay(EGLNativeDisplayType display_id)
412{
413 return egl::GetDisplay(display_id);
414}
415
416EGLAPI EGLBoolean EGLAPIENTRY eglInitialize(EGLDisplay dpy, EGLint *major, EGLint *minor)
417{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700418 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400419 return egl::Initialize(dpy, major, minor);
420}
421
422EGLAPI EGLBoolean EGLAPIENTRY eglTerminate(EGLDisplay dpy)
423{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700424 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400425 return egl::Terminate(dpy);
426}
427
428EGLAPI const char *EGLAPIENTRY eglQueryString(EGLDisplay dpy, EGLint name)
429{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700430 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400431 return egl::QueryString(dpy, name);
432}
433
434EGLAPI EGLBoolean EGLAPIENTRY eglGetConfigs(EGLDisplay dpy, EGLConfig *configs, EGLint config_size, EGLint *num_config)
435{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700436 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400437 return egl::GetConfigs(dpy, configs, config_size, num_config);
438}
439
440EGLAPI EGLBoolean EGLAPIENTRY eglChooseConfig(EGLDisplay dpy, const EGLint *attrib_list, EGLConfig *configs, EGLint config_size, EGLint *num_config)
441{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700442 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400443 return egl::ChooseConfig(dpy, attrib_list, configs, config_size, num_config);
444}
445
446EGLAPI EGLBoolean EGLAPIENTRY eglGetConfigAttrib(EGLDisplay dpy, EGLConfig config, EGLint attribute, EGLint *value)
447{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700448 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400449 return egl::GetConfigAttrib(dpy, config, attribute, value);
450}
451
452EGLAPI EGLSurface EGLAPIENTRY eglCreateWindowSurface(EGLDisplay dpy, EGLConfig config, EGLNativeWindowType window, const EGLint *attrib_list)
453{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700454 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400455 return egl::CreateWindowSurface(dpy, config, window, attrib_list);
456}
457
458EGLAPI EGLSurface EGLAPIENTRY eglCreatePbufferSurface(EGLDisplay dpy, EGLConfig config, const EGLint *attrib_list)
459{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700460 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400461 return egl::CreatePbufferSurface(dpy, config, attrib_list);
462}
463
464EGLAPI EGLSurface EGLAPIENTRY eglCreatePixmapSurface(EGLDisplay dpy, EGLConfig config, EGLNativePixmapType pixmap, const EGLint *attrib_list)
465{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700466 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400467 return egl::CreatePixmapSurface(dpy, config, pixmap, attrib_list);
468}
469
470EGLAPI EGLBoolean EGLAPIENTRY eglDestroySurface(EGLDisplay dpy, EGLSurface surface)
471{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700472 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400473 return egl::DestroySurface(dpy, surface);
474}
475
476EGLAPI EGLBoolean EGLAPIENTRY eglQuerySurface(EGLDisplay dpy, EGLSurface surface, EGLint attribute, EGLint *value)
477{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700478 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400479 return egl::QuerySurface(dpy, surface, attribute, value);
480}
481
482EGLAPI EGLBoolean EGLAPIENTRY eglBindAPI(EGLenum api)
483{
484 return egl::BindAPI(api);
485}
486
487EGLAPI EGLenum EGLAPIENTRY eglQueryAPI(void)
488{
489 return egl::QueryAPI();
490}
491
492EGLAPI EGLBoolean EGLAPIENTRY eglWaitClient(void)
493{
494 return egl::WaitClient();
495}
496
497EGLAPI EGLBoolean EGLAPIENTRY eglReleaseThread(void)
498{
499 return egl::ReleaseThread();
500}
501
502EGLAPI EGLSurface EGLAPIENTRY eglCreatePbufferFromClientBuffer(EGLDisplay dpy, EGLenum buftype, EGLClientBuffer buffer, EGLConfig config, const EGLint *attrib_list)
503{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700504 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400505 return egl::CreatePbufferFromClientBuffer(dpy, buftype, buffer, config, attrib_list);
506}
507
508EGLAPI EGLBoolean EGLAPIENTRY eglSurfaceAttrib(EGLDisplay dpy, EGLSurface surface, EGLint attribute, EGLint value)
509{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700510 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400511 return egl::SurfaceAttrib(dpy, surface, attribute, value);
512}
513
514EGLAPI EGLBoolean EGLAPIENTRY eglBindTexImage(EGLDisplay dpy, EGLSurface surface, EGLint buffer)
515{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700516 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400517 return egl::BindTexImage(dpy, surface, buffer);
518}
519
520EGLAPI EGLBoolean EGLAPIENTRY eglReleaseTexImage(EGLDisplay dpy, EGLSurface surface, EGLint buffer)
521{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700522 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400523 return egl::ReleaseTexImage(dpy, surface, buffer);
524}
525
526EGLAPI EGLBoolean EGLAPIENTRY eglSwapInterval(EGLDisplay dpy, EGLint interval)
527{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700528 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400529 return egl::SwapInterval(dpy, interval);
530}
531
532EGLAPI EGLContext EGLAPIENTRY eglCreateContext(EGLDisplay dpy, EGLConfig config, EGLContext share_context, const EGLint *attrib_list)
533{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700534 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400535 return egl::CreateContext(dpy, config, share_context, attrib_list);
536}
537
538EGLAPI EGLBoolean EGLAPIENTRY eglDestroyContext(EGLDisplay dpy, EGLContext ctx)
539{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700540 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400541 return egl::DestroyContext(dpy, ctx);
542}
543
544EGLAPI EGLBoolean EGLAPIENTRY eglMakeCurrent(EGLDisplay dpy, EGLSurface draw, EGLSurface read, EGLContext ctx)
545{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700546 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400547 return egl::MakeCurrent(dpy, draw, read, ctx);
548}
549
550EGLAPI EGLContext EGLAPIENTRY eglGetCurrentContext(void)
551{
552 return egl::GetCurrentContext();
553}
554
555EGLAPI EGLSurface EGLAPIENTRY eglGetCurrentSurface(EGLint readdraw)
556{
557 return egl::GetCurrentSurface(readdraw);
558}
559
560EGLAPI EGLDisplay EGLAPIENTRY eglGetCurrentDisplay(void)
561{
562 return egl::GetCurrentDisplay();
563}
564
565EGLAPI EGLBoolean EGLAPIENTRY eglQueryContext(EGLDisplay dpy, EGLContext ctx, EGLint attribute, EGLint *value)
566{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700567 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400568 return egl::QueryContext(dpy, ctx, attribute, value);
569}
570
571EGLAPI EGLBoolean EGLAPIENTRY eglWaitGL(void)
572{
573 return egl::WaitClient();
574}
575
576EGLAPI EGLBoolean EGLAPIENTRY eglWaitNative(EGLint engine)
577{
578 return egl::WaitNative(engine);
579}
580
581EGLAPI EGLBoolean EGLAPIENTRY eglSwapBuffers(EGLDisplay dpy, EGLSurface surface)
582{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700583 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400584 return egl::SwapBuffers(dpy, surface);
585}
586
587EGLAPI EGLBoolean EGLAPIENTRY eglCopyBuffers(EGLDisplay dpy, EGLSurface surface, EGLNativePixmapType target)
588{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700589 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400590 return egl::CopyBuffers(dpy, surface, target);
591}
592
593EGLAPI EGLImageKHR EGLAPIENTRY eglCreateImageKHR(EGLDisplay dpy, EGLContext ctx, EGLenum target, EGLClientBuffer buffer, const EGLint *attrib_list)
594{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700595 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400596 return egl::CreateImageKHR(dpy, ctx, target, buffer, attrib_list);
597}
598
Nicolas Capens48908cb2018-01-08 13:07:14 -0500599EGLAPI EGLImageKHR EGLAPIENTRY eglCreateImage(EGLDisplay dpy, EGLContext ctx, EGLenum target, EGLClientBuffer buffer, const EGLAttrib *attrib_list)
600{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700601 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens48908cb2018-01-08 13:07:14 -0500602 return egl::CreateImage(dpy, ctx, target, buffer, attrib_list);
603}
604
Nicolas Capens0bac2852016-05-07 06:09:58 -0400605EGLAPI EGLBoolean EGLAPIENTRY eglDestroyImageKHR(EGLDisplay dpy, EGLImageKHR image)
606{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700607 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400608 return egl::DestroyImageKHR(dpy, image);
609}
610
Nicolas Capens48908cb2018-01-08 13:07:14 -0500611EGLAPI EGLBoolean EGLAPIENTRY eglDestroyImage(EGLDisplay dpy, EGLImageKHR image)
612{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700613 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens48908cb2018-01-08 13:07:14 -0500614 return egl::DestroyImageKHR(dpy, image);
615}
616
Nicolas Capens0bac2852016-05-07 06:09:58 -0400617EGLAPI EGLDisplay EGLAPIENTRY eglGetPlatformDisplayEXT(EGLenum platform, void *native_display, const EGLint *attrib_list)
618{
619 return egl::GetPlatformDisplayEXT(platform, native_display, attrib_list);
620}
621
Nicolas Capens48908cb2018-01-08 13:07:14 -0500622EGLAPI EGLDisplay EGLAPIENTRY eglGetPlatformDisplay(EGLenum platform, void *native_display, const EGLAttrib *attrib_list)
623{
624 return egl::GetPlatformDisplay(platform, native_display, attrib_list);
625}
626
Nicolas Capens0bac2852016-05-07 06:09:58 -0400627EGLAPI EGLSurface EGLAPIENTRY eglCreatePlatformWindowSurfaceEXT(EGLDisplay dpy, EGLConfig config, void *native_window, const EGLint *attrib_list)
628{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700629 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400630 return egl::CreatePlatformWindowSurfaceEXT(dpy, config, native_window, attrib_list);
631}
632
Nicolas Capens48908cb2018-01-08 13:07:14 -0500633EGLAPI EGLSurface EGLAPIENTRY eglCreatePlatformWindowSurface(EGLDisplay dpy, EGLConfig config, void *native_window, const EGLAttrib *attrib_list)
634{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700635 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens48908cb2018-01-08 13:07:14 -0500636 return egl::CreatePlatformWindowSurface(dpy, config, native_window, attrib_list);
637}
638
Nicolas Capens0bac2852016-05-07 06:09:58 -0400639EGLAPI EGLSurface EGLAPIENTRY eglCreatePlatformPixmapSurfaceEXT(EGLDisplay dpy, EGLConfig config, void *native_pixmap, const EGLint *attrib_list)
640{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700641 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400642 return egl::CreatePlatformPixmapSurfaceEXT(dpy, config, native_pixmap, attrib_list);
643}
644
Nicolas Capens48908cb2018-01-08 13:07:14 -0500645EGLAPI EGLSurface EGLAPIENTRY eglCreatePlatformPixmapSurface(EGLDisplay dpy, EGLConfig config, void *native_pixmap, const EGLAttrib *attrib_list)
646{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700647 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens48908cb2018-01-08 13:07:14 -0500648 return egl::CreatePlatformPixmapSurface(dpy, config, native_pixmap, attrib_list);
649}
650
Nicolas Capens0bac2852016-05-07 06:09:58 -0400651EGLAPI EGLSyncKHR EGLAPIENTRY eglCreateSyncKHR(EGLDisplay dpy, EGLenum type, const EGLint *attrib_list)
652{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700653 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400654 return egl::CreateSyncKHR(dpy, type, attrib_list);
655}
656
Nicolas Capens48908cb2018-01-08 13:07:14 -0500657EGLAPI EGLSyncKHR EGLAPIENTRY eglCreateSync(EGLDisplay dpy, EGLenum type, const EGLAttrib *attrib_list)
658{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700659 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens48908cb2018-01-08 13:07:14 -0500660 return egl::CreateSync(dpy, type, attrib_list);
661}
662
Nicolas Capens0bac2852016-05-07 06:09:58 -0400663EGLAPI EGLBoolean EGLAPIENTRY eglDestroySyncKHR(EGLDisplay dpy, EGLSyncKHR sync)
664{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700665 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400666 return egl::DestroySyncKHR(dpy, sync);
667}
668
Nicolas Capens48908cb2018-01-08 13:07:14 -0500669EGLAPI EGLBoolean EGLAPIENTRY eglDestroySync(EGLDisplay dpy, EGLSyncKHR sync)
670{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700671 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens48908cb2018-01-08 13:07:14 -0500672 return egl::DestroySyncKHR(dpy, sync);
673}
674
Nicolas Capens0bac2852016-05-07 06:09:58 -0400675EGLAPI EGLint EGLAPIENTRY eglClientWaitSyncKHR(EGLDisplay dpy, EGLSyncKHR sync, EGLint flags, EGLTimeKHR timeout)
676{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700677 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400678 return egl::ClientWaitSyncKHR(dpy, sync, flags, timeout);
679}
680
Nicolas Capens48908cb2018-01-08 13:07:14 -0500681EGLAPI EGLint EGLAPIENTRY eglClientWaitSync(EGLDisplay dpy, EGLSyncKHR sync, EGLint flags, EGLTimeKHR timeout)
682{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700683 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens48908cb2018-01-08 13:07:14 -0500684 return egl::ClientWaitSyncKHR(dpy, sync, flags, timeout);
685}
686
Nicolas Capens0bac2852016-05-07 06:09:58 -0400687EGLAPI EGLBoolean EGLAPIENTRY eglGetSyncAttribKHR(EGLDisplay dpy, EGLSyncKHR sync, EGLint attribute, EGLint *value)
688{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700689 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens0bac2852016-05-07 06:09:58 -0400690 return egl::GetSyncAttribKHR(dpy, sync, attribute, value);
691}
692
Nicolas Capens48908cb2018-01-08 13:07:14 -0500693EGLAPI EGLBoolean EGLAPIENTRY eglGetSyncAttrib(EGLDisplay dpy, EGLSyncKHR sync, EGLint attribute, EGLAttrib *value)
694{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700695 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens48908cb2018-01-08 13:07:14 -0500696 return egl::GetSyncAttrib(dpy, sync, attribute, value);
697}
698
699EGLAPI EGLint EGLAPIENTRY eglWaitSyncKHR(EGLDisplay dpy, EGLSyncKHR sync, EGLint flags)
700{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700701 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens48908cb2018-01-08 13:07:14 -0500702 return egl::ClientWaitSyncKHR(dpy, sync, flags, EGL_FOREVER_KHR);
703}
704
705EGLAPI EGLBoolean EGLAPIENTRY eglWaitSync(EGLDisplay dpy, EGLSync sync, EGLint flags)
706{
Chris Forbes1aae88c2018-09-11 17:31:52 -0700707 LockGuard lock(egl::getDisplayLock(dpy));
Nicolas Capens48908cb2018-01-08 13:07:14 -0500708 return egl::ClientWaitSyncKHR(dpy, sync, flags, EGL_FOREVER_KHR);
709}
710
Nicolas Capens0bac2852016-05-07 06:09:58 -0400711EGLAPI __eglMustCastToProperFunctionPointerType EGLAPIENTRY eglGetProcAddress(const char *procname)
712{
713 return egl::GetProcAddress(procname);
714}
715}
716
717LibEGLexports::LibEGLexports()
718{
719 this->eglGetError = egl::GetError;
720 this->eglGetDisplay = egl::GetDisplay;
721 this->eglInitialize = egl::Initialize;
722 this->eglTerminate = egl::Terminate;
723 this->eglQueryString = egl::QueryString;
724 this->eglGetConfigs = egl::GetConfigs;
725 this->eglChooseConfig = egl::ChooseConfig;
726 this->eglGetConfigAttrib = egl::GetConfigAttrib;
727 this->eglCreateWindowSurface = egl::CreateWindowSurface;
728 this->eglCreatePbufferSurface = egl::CreatePbufferSurface;
729 this->eglCreatePixmapSurface = egl::CreatePixmapSurface;
730 this->eglDestroySurface = egl::DestroySurface;
731 this->eglQuerySurface = egl::QuerySurface;
732 this->eglBindAPI = egl::BindAPI;
733 this->eglQueryAPI = egl::QueryAPI;
734 this->eglWaitClient = egl::WaitClient;
735 this->eglReleaseThread = egl::ReleaseThread;
736 this->eglCreatePbufferFromClientBuffer = egl::CreatePbufferFromClientBuffer;
737 this->eglSurfaceAttrib = egl::SurfaceAttrib;
738 this->eglBindTexImage = egl::BindTexImage;
739 this->eglReleaseTexImage = egl::ReleaseTexImage;
740 this->eglSwapInterval = egl::SwapInterval;
741 this->eglCreateContext = egl::CreateContext;
742 this->eglDestroyContext = egl::DestroyContext;
743 this->eglMakeCurrent = egl::MakeCurrent;
744 this->eglGetCurrentContext = egl::GetCurrentContext;
745 this->eglGetCurrentSurface = egl::GetCurrentSurface;
746 this->eglGetCurrentDisplay = egl::GetCurrentDisplay;
747 this->eglQueryContext = egl::QueryContext;
748 this->eglWaitGL = egl::WaitGL;
749 this->eglWaitNative = egl::WaitNative;
750 this->eglSwapBuffers = egl::SwapBuffers;
751 this->eglCopyBuffers = egl::CopyBuffers;
752 this->eglCreateImageKHR = egl::CreateImageKHR;
753 this->eglDestroyImageKHR = egl::DestroyImageKHR;
754 this->eglGetProcAddress = egl::GetProcAddress;
755 this->eglCreateSyncKHR = egl::CreateSyncKHR;
756 this->eglDestroySyncKHR = egl::DestroySyncKHR;
757 this->eglClientWaitSyncKHR = egl::ClientWaitSyncKHR;
758 this->eglGetSyncAttribKHR = egl::GetSyncAttribKHR;
759
760 this->clientGetCurrentContext = egl::getCurrentContext;
761}
762
Alexis Hetu2a0def72018-05-14 08:16:05 -0400763extern "C" EGLAPI LibEGLexports *libEGL_swiftshader()
Nicolas Capens0bac2852016-05-07 06:09:58 -0400764{
765 static LibEGLexports libEGL;
766 return &libEGL;
767}
768
Nicolas Capens5e1520f2018-07-03 16:13:28 -0400769LibGLES_CM libGLES_CM;
770LibGLESv2 libGLESv2;