• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2019 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 // entry_points_wgl.cpp: Implements the exported WGL functions.
7 
8 #include "entry_points_wgl.h"
9 
10 #include "common/debug.h"
11 #include "common/event_tracer.h"
12 #include "common/utilities.h"
13 #include "common/version.h"
14 #include "libANGLE/Context.h"
15 #include "libANGLE/Display.h"
16 #include "libANGLE/EGLSync.h"
17 #include "libANGLE/Surface.h"
18 #include "libANGLE/Texture.h"
19 #include "libANGLE/Thread.h"
20 #include "libANGLE/entry_points_utils.h"
21 #include "libANGLE/queryutils.h"
22 #include "libANGLE/validationEGL.h"
23 #include "libGL/proc_table_wgl.h"
24 #include "libGLESv2/global_state.h"
25 
26 using namespace wgl;
27 using namespace egl;
28 
29 namespace
30 {
31 
CompareProc(const ProcEntry & a,const char * b)32 bool CompareProc(const ProcEntry &a, const char *b)
33 {
34     return strcmp(a.first, b) < 0;
35 }
36 
ClipConfigs(const std::vector<const Config * > & filteredConfigs,EGLConfig * output_configs,EGLint config_size,EGLint * num_config)37 void ClipConfigs(const std::vector<const Config *> &filteredConfigs,
38                  EGLConfig *output_configs,
39                  EGLint config_size,
40                  EGLint *num_config)
41 {
42     EGLint result_size = static_cast<EGLint>(filteredConfigs.size());
43     if (output_configs)
44     {
45         result_size = std::max(std::min(result_size, config_size), 0);
46         for (EGLint i = 0; i < result_size; i++)
47         {
48             output_configs[i] = const_cast<Config *>(filteredConfigs[i]);
49         }
50     }
51     *num_config = result_size;
52 }
53 }  // anonymous namespace
54 
55 extern "C" {
56 
57 // WGL 1.0
wglChoosePixelFormat(HDC hDc,const PIXELFORMATDESCRIPTOR * pPfd)58 int GL_APIENTRY wglChoosePixelFormat(HDC hDc, const PIXELFORMATDESCRIPTOR *pPfd)
59 {
60     UNIMPLEMENTED();
61     return 1;
62 }
63 
wglDescribePixelFormat(HDC hdc,int ipfd,UINT cjpfd,PIXELFORMATDESCRIPTOR * ppfd)64 int GL_APIENTRY wglDescribePixelFormat(HDC hdc, int ipfd, UINT cjpfd, PIXELFORMATDESCRIPTOR *ppfd)
65 {
66     UNIMPLEMENTED();
67     if (ppfd)
68     {
69         ppfd->dwFlags      = ppfd->dwFlags | PFD_DRAW_TO_WINDOW;
70         ppfd->dwFlags      = ppfd->dwFlags | PFD_SUPPORT_OPENGL;
71         ppfd->dwFlags      = ppfd->dwFlags | PFD_GENERIC_ACCELERATED;
72         ppfd->dwFlags      = ppfd->dwFlags | PFD_DOUBLEBUFFER;
73         ppfd->iPixelType   = PFD_TYPE_RGBA;
74         ppfd->cColorBits   = 24;
75         ppfd->cRedBits     = 8;
76         ppfd->cGreenBits   = 8;
77         ppfd->cBlueBits    = 8;
78         ppfd->cAlphaBits   = 8;
79         ppfd->cDepthBits   = 24;
80         ppfd->cStencilBits = 8;
81         ppfd->nVersion     = 1;
82     }
83     return 1;
84 }
85 
wglGetEnhMetaFilePixelFormat(HENHMETAFILE hemf,UINT cbBuffer,PIXELFORMATDESCRIPTOR * ppfd)86 UINT GL_APIENTRY wglGetEnhMetaFilePixelFormat(HENHMETAFILE hemf,
87                                               UINT cbBuffer,
88                                               PIXELFORMATDESCRIPTOR *ppfd)
89 {
90     UNIMPLEMENTED();
91     return 1u;
92 }
93 
wglGetPixelFormat(HDC hdc)94 int GL_APIENTRY wglGetPixelFormat(HDC hdc)
95 {
96     UNIMPLEMENTED();
97     return 1;
98 }
99 
wglSetPixelFormat(HDC hdc,int ipfd,const PIXELFORMATDESCRIPTOR * ppfd)100 BOOL GL_APIENTRY wglSetPixelFormat(HDC hdc, int ipfd, const PIXELFORMATDESCRIPTOR *ppfd)
101 {
102     UNIMPLEMENTED();
103     return TRUE;
104 }
105 
wglSwapBuffers(HDC hdc)106 BOOL GL_APIENTRY wglSwapBuffers(HDC hdc)
107 {
108     Thread *thread        = egl::GetCurrentThread();
109     egl::Display *display = egl::Display::GetExistingDisplayFromNativeDisplay(hdc);
110 
111     ANGLE_EGL_TRY_RETURN(thread, display->getWGLSurface()->swap(thread->getContext()),
112                          "wglSwapBuffers", display->getWGLSurface(), FALSE);
113     return TRUE;
114 }
115 
wglCopyContext(HGLRC hglrcSrc,HGLRC hglrcDst,UINT mask)116 BOOL GL_APIENTRY wglCopyContext(HGLRC hglrcSrc, HGLRC hglrcDst, UINT mask)
117 {
118     UNIMPLEMENTED();
119     return TRUE;
120 }
121 
wglCreateContext(HDC hDc)122 HGLRC GL_APIENTRY wglCreateContext(HDC hDc)
123 {
124     Thread *thread = egl::GetCurrentThread();
125 
126     std::vector<EGLAttrib> displayAttributes;
127     displayAttributes.push_back(EGL_PLATFORM_ANGLE_TYPE_ANGLE);
128     GLenum platformType = EGL_PLATFORM_ANGLE_TYPE_DEFAULT_ANGLE;
129     displayAttributes.push_back(platformType);
130     displayAttributes.push_back(EGL_NONE);
131 
132     const auto &attribMapDisplay = AttributeMap::CreateFromAttribArray(displayAttributes.data());
133 
134     egl::Display *display = egl::Display::GetDisplayFromNativeDisplay(hDc, attribMapDisplay);
135 
136     ANGLE_EGL_TRY_RETURN(thread, display->initialize(), "wglCreateContext", display, nullptr);
137 
138     thread->setAPI(EGL_OPENGL_API);
139 
140     // Default config
141     const EGLint configAttributes[] = {EGL_NONE};
142 
143     // Choose config
144     EGLint configCount;
145     EGLConfig config;
146     AttributeMap attribMapConfig = AttributeMap::CreateFromIntArray(configAttributes);
147     ClipConfigs(display->chooseConfig(attribMapConfig), &config, 1, &configCount);
148 
149     Config *configuration = static_cast<Config *>(config);
150 
151     // Initialize surface
152     std::vector<EGLint> surfaceAttributes;
153     surfaceAttributes.push_back(EGL_NONE);
154     surfaceAttributes.push_back(EGL_NONE);
155     AttributeMap surfAttributes = AttributeMap::CreateFromIntArray(&surfaceAttributes[0]);
156 
157     // Create first window surface
158     egl::Surface *surface = nullptr;
159     ANGLE_EGL_TRY_RETURN(
160         thread,
161         display->createWindowSurface(configuration, WindowFromDC(hDc), surfAttributes, &surface),
162         "wglCreateContext", display, nullptr);
163 
164     // Initialize context
165     EGLint contextAttibutes[] = {EGL_CONTEXT_CLIENT_VERSION, 4, EGL_CONTEXT_MINOR_VERSION, 6,
166                                  EGL_NONE};
167 
168     gl::Context *sharedGLContext = static_cast<gl::Context *>(nullptr);
169     AttributeMap ctxAttributes   = AttributeMap::CreateFromIntArray(contextAttibutes);
170 
171     gl::Context *context = nullptr;
172 
173     ANGLE_EGL_TRY_RETURN(thread,
174                          display->createContext(configuration, sharedGLContext, EGL_OPENGL_API,
175                                                 ctxAttributes, &context),
176                          "wglCreateContext", display, nullptr);
177 
178     return reinterpret_cast<HGLRC>(context);
179 }
180 
wglCreateLayerContext(HDC hDc,int level)181 HGLRC GL_APIENTRY wglCreateLayerContext(HDC hDc, int level)
182 {
183     UNIMPLEMENTED();
184     return nullptr;
185 }
186 
wglDeleteContext(HGLRC oldContext)187 BOOL GL_APIENTRY wglDeleteContext(HGLRC oldContext)
188 {
189     UNIMPLEMENTED();
190     return FALSE;
191 }
192 
wglDescribeLayerPlane(HDC hDc,int pixelFormat,int layerPlane,UINT nBytes,LAYERPLANEDESCRIPTOR * plpd)193 BOOL GL_APIENTRY wglDescribeLayerPlane(HDC hDc,
194                                        int pixelFormat,
195                                        int layerPlane,
196                                        UINT nBytes,
197                                        LAYERPLANEDESCRIPTOR *plpd)
198 {
199     UNIMPLEMENTED();
200     return FALSE;
201 }
202 
wglGetCurrentContext()203 HGLRC GL_APIENTRY wglGetCurrentContext()
204 {
205     UNIMPLEMENTED();
206     return nullptr;
207 }
208 
wglGetCurrentDC()209 HDC GL_APIENTRY wglGetCurrentDC()
210 {
211     UNIMPLEMENTED();
212     return nullptr;
213 }
214 
215 int GL_APIENTRY
wglGetLayerPaletteEntries(HDC hdc,int iLayerPlane,int iStart,int cEntries,COLORREF * pcr)216 wglGetLayerPaletteEntries(HDC hdc, int iLayerPlane, int iStart, int cEntries, COLORREF *pcr)
217 {
218     UNIMPLEMENTED();
219     return 0;
220 }
221 
wglGetProcAddress(LPCSTR lpszProc)222 PROC GL_APIENTRY wglGetProcAddress(LPCSTR lpszProc)
223 {
224     ANGLE_SCOPED_GLOBAL_LOCK();
225     FUNC_EVENT("const char *procname = \"%s\"", lpszProc);
226     egl::Thread *thread = egl::GetCurrentThread();
227 
228     ProcEntry *entry =
229         std::lower_bound(&g_procTable[0], &g_procTable[g_numProcs], lpszProc, CompareProc);
230 
231     thread->setSuccess();
232 
233     if (entry == &g_procTable[g_numProcs] || strcmp(entry->first, lpszProc) != 0)
234     {
235         return nullptr;
236     }
237 
238     return entry->second;
239 }
240 
wglMakeCurrent(HDC hDc,HGLRC newContext)241 BOOL GL_APIENTRY wglMakeCurrent(HDC hDc, HGLRC newContext)
242 {
243     Thread *thread        = egl::GetCurrentThread();
244     egl::Display *display = egl::Display::GetExistingDisplayFromNativeDisplay(hDc);
245     const gl::Context *context =
246         GetContextIfValid(display, reinterpret_cast<gl::Context *>(newContext));
247 
248     // If display or context are invalid, make thread's current rendering context not current
249     if (!context)
250     {
251         gl::Context *oldContext = thread->getContext();
252         if (oldContext)
253         {
254             ANGLE_EGL_TRY_RETURN(thread, oldContext->unMakeCurrent(display), "wglMakeCurrent",
255                                  GetContextIfValid(display, oldContext), EGL_FALSE);
256         }
257         SetContextCurrent(thread, nullptr);
258         return TRUE;
259     }
260 
261     egl::Surface *surface        = display->getWGLSurface();
262     Surface *previousDraw        = thread->getCurrentDrawSurface();
263     Surface *previousRead        = thread->getCurrentReadSurface();
264     gl::Context *previousContext = thread->getContext();
265 
266     if (previousDraw != surface || previousRead != surface || previousContext != context)
267     {
268         ANGLE_EGL_TRY_RETURN(
269             thread,
270             display->makeCurrent(thread, surface, surface, const_cast<gl::Context *>(context)),
271             "wglMakeCurrent", GetContextIfValid(display, context), EGL_FALSE);
272 
273         SetContextCurrent(thread, const_cast<gl::Context *>(context));
274     }
275 
276     return TRUE;
277 }
278 
wglRealizeLayerPalette(HDC hdc,int iLayerPlane,BOOL bRealize)279 BOOL GL_APIENTRY wglRealizeLayerPalette(HDC hdc, int iLayerPlane, BOOL bRealize)
280 {
281     UNIMPLEMENTED();
282     return FALSE;
283 }
284 
285 int GL_APIENTRY
wglSetLayerPaletteEntries(HDC hdc,int iLayerPlane,int iStart,int cEntries,const COLORREF * pcr)286 wglSetLayerPaletteEntries(HDC hdc, int iLayerPlane, int iStart, int cEntries, const COLORREF *pcr)
287 {
288     UNIMPLEMENTED();
289     return 0;
290 }
291 
wglShareLists(HGLRC hrcSrvShare,HGLRC hrcSrvSource)292 BOOL GL_APIENTRY wglShareLists(HGLRC hrcSrvShare, HGLRC hrcSrvSource)
293 {
294     UNIMPLEMENTED();
295     return FALSE;
296 }
297 
wglSwapLayerBuffers(HDC hdc,UINT fuFlags)298 BOOL GL_APIENTRY wglSwapLayerBuffers(HDC hdc, UINT fuFlags)
299 {
300     UNIMPLEMENTED();
301     return FALSE;
302 }
303 
wglUseFontBitmapsA(HDC hDC,DWORD first,DWORD count,DWORD listBase)304 BOOL GL_APIENTRY wglUseFontBitmapsA(HDC hDC, DWORD first, DWORD count, DWORD listBase)
305 {
306     UNIMPLEMENTED();
307     return FALSE;
308 }
309 
wglUseFontBitmapsW(HDC hDC,DWORD first,DWORD count,DWORD listBase)310 BOOL GL_APIENTRY wglUseFontBitmapsW(HDC hDC, DWORD first, DWORD count, DWORD listBase)
311 {
312     UNIMPLEMENTED();
313     return FALSE;
314 }
315 
wglUseFontOutlinesA(HDC hDC,DWORD first,DWORD count,DWORD listBase,FLOAT deviation,FLOAT extrusion,int format,LPGLYPHMETRICSFLOAT lpgmf)316 BOOL GL_APIENTRY wglUseFontOutlinesA(HDC hDC,
317                                      DWORD first,
318                                      DWORD count,
319                                      DWORD listBase,
320                                      FLOAT deviation,
321                                      FLOAT extrusion,
322                                      int format,
323                                      LPGLYPHMETRICSFLOAT lpgmf)
324 {
325     UNIMPLEMENTED();
326     return FALSE;
327 }
328 
wglUseFontOutlinesW(HDC hDC,DWORD first,DWORD count,DWORD listBase,FLOAT deviation,FLOAT extrusion,int format,LPGLYPHMETRICSFLOAT lpgmf)329 BOOL GL_APIENTRY wglUseFontOutlinesW(HDC hDC,
330                                      DWORD first,
331                                      DWORD count,
332                                      DWORD listBase,
333                                      FLOAT deviation,
334                                      FLOAT extrusion,
335                                      int format,
336                                      LPGLYPHMETRICSFLOAT lpgmf)
337 {
338     UNIMPLEMENTED();
339     return FALSE;
340 }
341 
342 }  // extern "C"
343