Rev 4358 | Go to most recent revision | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 4358 | Rev 5080 | ||
---|---|---|---|
1 | /* |
1 | /* |
2 | * Mesa 3-D graphics library |
2 | * Mesa 3-D graphics library |
3 | * |
3 | * |
4 | * Copyright (C) 2009-2010 Chia-I Wu |
4 | * Copyright (C) 2009-2010 Chia-I Wu |
5 | * |
5 | * |
6 | * Permission is hereby granted, free of charge, to any person obtaining a |
6 | * Permission is hereby granted, free of charge, to any person obtaining a |
7 | * copy of this software and associated documentation files (the "Software"), |
7 | * copy of this software and associated documentation files (the "Software"), |
8 | * to deal in the Software without restriction, including without limitation |
8 | * to deal in the Software without restriction, including without limitation |
9 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, |
9 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, |
10 | * and/or sell copies of the Software, and to permit persons to whom the |
10 | * and/or sell copies of the Software, and to permit persons to whom the |
11 | * Software is furnished to do so, subject to the following conditions: |
11 | * Software is furnished to do so, subject to the following conditions: |
12 | * |
12 | * |
13 | * The above copyright notice and this permission notice shall be included |
13 | * The above copyright notice and this permission notice shall be included |
14 | * in all copies or substantial portions of the Software. |
14 | * in all copies or substantial portions of the Software. |
15 | * |
15 | * |
16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL |
18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL |
19 | * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER |
19 | * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER |
20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING |
20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING |
21 | * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER |
21 | * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER |
22 | * DEALINGS IN THE SOFTWARE. |
22 | * DEALINGS IN THE SOFTWARE. |
23 | */ |
23 | */ |
24 | 24 | ||
25 | #include "egldriver.h" |
25 | #include "egldriver.h" |
26 | #include "eglcurrent.h" |
26 | #include "eglcurrent.h" |
27 | #include "egllog.h" |
27 | #include "egllog.h" |
28 | 28 | ||
29 | #include "pipe/p_screen.h" |
29 | #include "pipe/p_screen.h" |
30 | #include "util/u_memory.h" |
30 | #include "util/u_memory.h" |
31 | #include "util/u_format.h" |
31 | #include "util/u_format.h" |
32 | #include "util/u_string.h" |
32 | #include "util/u_string.h" |
33 | #include "util/u_atomic.h" |
33 | #include "util/u_atomic.h" |
34 | 34 | ||
35 | #include "egl_g3d.h" |
35 | #include "egl_g3d.h" |
36 | #include "egl_g3d_api.h" |
36 | #include "egl_g3d_api.h" |
37 | #include "egl_g3d_st.h" |
37 | #include "egl_g3d_st.h" |
38 | #include "egl_g3d_loader.h" |
38 | #include "egl_g3d_loader.h" |
39 | #include "native.h" |
39 | #include "native.h" |
40 | 40 | ||
41 | static void |
41 | static void |
42 | egl_g3d_invalid_surface(struct native_display *ndpy, |
42 | egl_g3d_invalid_surface(struct native_display *ndpy, |
43 | struct native_surface *nsurf, |
43 | struct native_surface *nsurf, |
44 | unsigned int seq_num) |
44 | unsigned int seq_num) |
45 | { |
45 | { |
46 | /* XXX not thread safe? */ |
46 | /* XXX not thread safe? */ |
47 | struct egl_g3d_surface *gsurf = egl_g3d_surface(nsurf->user_data); |
47 | struct egl_g3d_surface *gsurf = egl_g3d_surface(nsurf->user_data); |
48 | 48 | ||
49 | if (gsurf && gsurf->stfbi) |
49 | if (gsurf && gsurf->stfbi) |
50 | p_atomic_inc(&gsurf->stfbi->stamp); |
50 | p_atomic_inc(&gsurf->stfbi->stamp); |
51 | } |
51 | } |
52 | 52 | ||
53 | static struct pipe_screen * |
53 | static struct pipe_screen * |
54 | egl_g3d_new_drm_screen(struct native_display *ndpy, const char *name, int fd) |
54 | egl_g3d_new_drm_screen(struct native_display *ndpy, const char *name, int fd) |
55 | { |
55 | { |
56 | _EGLDisplay *dpy = (_EGLDisplay *) ndpy->user_data; |
56 | _EGLDisplay *dpy = (_EGLDisplay *) ndpy->user_data; |
57 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
57 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
58 | return gdpy->loader->create_drm_screen(name, fd); |
58 | return gdpy->loader->create_drm_screen(name, fd); |
59 | } |
59 | } |
60 | 60 | ||
61 | static struct pipe_screen * |
61 | static struct pipe_screen * |
62 | egl_g3d_new_sw_screen(struct native_display *ndpy, struct sw_winsys *ws) |
62 | egl_g3d_new_sw_screen(struct native_display *ndpy, struct sw_winsys *ws) |
63 | { |
63 | { |
64 | _EGLDisplay *dpy = (_EGLDisplay *) ndpy->user_data; |
64 | _EGLDisplay *dpy = (_EGLDisplay *) ndpy->user_data; |
65 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
65 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
66 | return gdpy->loader->create_sw_screen(ws); |
66 | return gdpy->loader->create_sw_screen(ws); |
67 | } |
67 | } |
68 | 68 | ||
69 | static struct pipe_resource * |
69 | static struct pipe_resource * |
70 | egl_g3d_lookup_egl_image(struct native_display *ndpy, void *egl_image) |
70 | egl_g3d_lookup_egl_image(struct native_display *ndpy, void *egl_image) |
71 | { |
71 | { |
72 | _EGLDisplay *dpy = (_EGLDisplay *) ndpy->user_data; |
72 | _EGLDisplay *dpy = (_EGLDisplay *) ndpy->user_data; |
73 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
73 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
74 | struct st_egl_image img; |
74 | struct st_egl_image img; |
75 | struct pipe_resource *resource = NULL; |
75 | struct pipe_resource *resource = NULL; |
76 | 76 | ||
77 | memset(&img, 0, sizeof(img)); |
77 | memset(&img, 0, sizeof(img)); |
78 | if (gdpy->smapi->get_egl_image(gdpy->smapi, egl_image, &img)) |
78 | if (gdpy->smapi->get_egl_image(gdpy->smapi, egl_image, &img)) |
79 | resource = img.texture; |
79 | resource = img.texture; |
80 | 80 | ||
81 | return resource; |
81 | return resource; |
82 | } |
82 | } |
83 | 83 | ||
84 | static const struct native_event_handler egl_g3d_native_event_handler = { |
84 | static const struct native_event_handler egl_g3d_native_event_handler = { |
85 | egl_g3d_invalid_surface, |
85 | egl_g3d_invalid_surface, |
86 | egl_g3d_new_drm_screen, |
86 | egl_g3d_new_drm_screen, |
87 | egl_g3d_new_sw_screen, |
87 | egl_g3d_new_sw_screen, |
88 | egl_g3d_lookup_egl_image |
88 | egl_g3d_lookup_egl_image |
89 | }; |
89 | }; |
90 | 90 | ||
91 | /** |
91 | /** |
92 | * Get the native platform. |
92 | * Get the native platform. |
93 | */ |
93 | */ |
94 | static const struct native_platform * |
94 | static const struct native_platform * |
95 | egl_g3d_get_platform(_EGLDriver *drv, _EGLPlatformType plat) |
95 | egl_g3d_get_platform(_EGLDriver *drv, _EGLPlatformType plat) |
96 | { |
96 | { |
97 | struct egl_g3d_driver *gdrv = egl_g3d_driver(drv); |
97 | struct egl_g3d_driver *gdrv = egl_g3d_driver(drv); |
98 | 98 | ||
99 | if (!gdrv->platforms[plat]) { |
99 | if (!gdrv->platforms[plat]) { |
100 | const char *plat_name = NULL; |
100 | const char *plat_name = NULL; |
101 | const struct native_platform *nplat = NULL; |
101 | const struct native_platform *nplat = NULL; |
102 | - | ||
103 | switch (plat) { |
- | |
104 | case _EGL_PLATFORM_WINDOWS: |
- | |
105 | plat_name = "Windows"; |
- | |
106 | #ifdef HAVE_GDI_BACKEND |
- | |
107 | nplat = native_get_gdi_platform(&egl_g3d_native_event_handler); |
- | |
108 | #endif |
- | |
109 | break; |
- | |
110 | case _EGL_PLATFORM_X11: |
- | |
111 | plat_name = "X11"; |
- | |
112 | #ifdef HAVE_X11_BACKEND |
- | |
113 | nplat = native_get_x11_platform(&egl_g3d_native_event_handler); |
- | |
114 | #endif |
- | |
115 | break; |
- | |
116 | case _EGL_PLATFORM_WAYLAND: |
- | |
117 | plat_name = "wayland"; |
- | |
118 | #ifdef HAVE_WAYLAND_BACKEND |
- | |
119 | nplat = native_get_wayland_platform(&egl_g3d_native_event_handler); |
- | |
120 | #endif |
- | |
121 | break; |
- | |
122 | case _EGL_PLATFORM_DRM: |
102 | |
123 | plat_name = "DRM"; |
- | |
124 | #ifdef HAVE_DRM_BACKEND |
103 | plat_name = "DRM"; |
125 | nplat = native_get_drm_platform(&egl_g3d_native_event_handler); |
- | |
126 | #endif |
- | |
127 | break; |
- | |
128 | case _EGL_PLATFORM_FBDEV: |
- | |
129 | plat_name = "FBDEV"; |
- | |
130 | #ifdef HAVE_FBDEV_BACKEND |
- | |
131 | nplat = native_get_fbdev_platform(&egl_g3d_native_event_handler); |
- | |
132 | #endif |
- | |
133 | break; |
- | |
134 | case _EGL_PLATFORM_NULL: |
- | |
135 | plat_name = "NULL"; |
- | |
136 | #ifdef HAVE_NULL_BACKEND |
- | |
137 | nplat = native_get_null_platform(&egl_g3d_native_event_handler); |
- | |
138 | #endif |
- | |
139 | break; |
- | |
140 | case _EGL_PLATFORM_ANDROID: |
- | |
141 | plat_name = "Android"; |
- | |
142 | #ifdef HAVE_ANDROID_BACKEND |
- | |
143 | nplat = native_get_android_platform(&egl_g3d_native_event_handler); |
- | |
144 | #endif |
- | |
145 | break; |
- | |
146 | default: |
- | |
147 | break; |
- | |
148 | } |
104 | nplat = native_get_drm_platform(&egl_g3d_native_event_handler); |
149 | 105 | ||
150 | if (!nplat) |
106 | if (!nplat) |
151 | _eglLog(_EGL_WARNING, "unsupported platform %s", plat_name); |
107 | _eglLog(_EGL_WARNING, "unsupported platform %s", plat_name); |
152 | 108 | ||
153 | gdrv->platforms[plat] = nplat; |
109 | gdrv->platforms[plat] = nplat; |
154 | } |
110 | } |
155 | 111 | ||
156 | return gdrv->platforms[plat]; |
112 | return gdrv->platforms[plat]; |
157 | } |
113 | } |
158 | 114 | ||
159 | #ifdef EGL_MESA_screen_surface |
115 | #ifdef EGL_MESA_screen_surface |
160 | 116 | ||
161 | static void |
117 | static void |
162 | egl_g3d_add_screens(_EGLDriver *drv, _EGLDisplay *dpy) |
118 | egl_g3d_add_screens(_EGLDriver *drv, _EGLDisplay *dpy) |
163 | { |
119 | { |
164 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
120 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
165 | const struct native_connector **native_connectors; |
121 | const struct native_connector **native_connectors; |
166 | EGLint num_connectors, i; |
122 | EGLint num_connectors, i; |
167 | 123 | ||
168 | native_connectors = |
124 | native_connectors = |
169 | gdpy->native->modeset->get_connectors(gdpy->native, &num_connectors, NULL); |
125 | gdpy->native->modeset->get_connectors(gdpy->native, &num_connectors, NULL); |
170 | if (!num_connectors) { |
126 | if (!num_connectors) { |
171 | FREE(native_connectors); |
127 | FREE(native_connectors); |
172 | return; |
128 | return; |
173 | } |
129 | } |
174 | 130 | ||
175 | for (i = 0; i < num_connectors; i++) { |
131 | for (i = 0; i < num_connectors; i++) { |
176 | const struct native_connector *nconn = native_connectors[i]; |
132 | const struct native_connector *nconn = native_connectors[i]; |
177 | struct egl_g3d_screen *gscr; |
133 | struct egl_g3d_screen *gscr; |
178 | const struct native_mode **native_modes; |
134 | const struct native_mode **native_modes; |
179 | EGLint num_modes, j; |
135 | EGLint num_modes, j; |
180 | 136 | ||
181 | /* TODO support for hotplug */ |
137 | /* TODO support for hotplug */ |
182 | native_modes = |
138 | native_modes = |
183 | gdpy->native->modeset->get_modes(gdpy->native, nconn, &num_modes); |
139 | gdpy->native->modeset->get_modes(gdpy->native, nconn, &num_modes); |
184 | if (!num_modes) { |
140 | if (!num_modes) { |
185 | FREE(native_modes); |
141 | FREE(native_modes); |
186 | continue; |
142 | continue; |
187 | } |
143 | } |
188 | 144 | ||
189 | gscr = CALLOC_STRUCT(egl_g3d_screen); |
145 | gscr = CALLOC_STRUCT(egl_g3d_screen); |
190 | if (!gscr) { |
146 | if (!gscr) { |
191 | FREE(native_modes); |
147 | FREE(native_modes); |
192 | continue; |
148 | continue; |
193 | } |
149 | } |
194 | 150 | ||
195 | _eglInitScreen(&gscr->base, dpy, num_modes); |
151 | _eglInitScreen(&gscr->base, dpy, num_modes); |
196 | for (j = 0; j < gscr->base.NumModes; j++) { |
152 | for (j = 0; j < gscr->base.NumModes; j++) { |
197 | const struct native_mode *nmode = native_modes[j]; |
153 | const struct native_mode *nmode = native_modes[j]; |
198 | _EGLMode *mode = &gscr->base.Modes[j]; |
154 | _EGLMode *mode = &gscr->base.Modes[j]; |
199 | 155 | ||
200 | mode->Width = nmode->width; |
156 | mode->Width = nmode->width; |
201 | mode->Height = nmode->height; |
157 | mode->Height = nmode->height; |
202 | mode->RefreshRate = nmode->refresh_rate; |
158 | mode->RefreshRate = nmode->refresh_rate; |
203 | mode->Optimal = EGL_FALSE; |
159 | mode->Optimal = EGL_FALSE; |
204 | mode->Interlaced = EGL_FALSE; |
160 | mode->Interlaced = EGL_FALSE; |
205 | /* no need to strdup() */ |
161 | /* no need to strdup() */ |
206 | mode->Name = nmode->desc; |
162 | mode->Name = nmode->desc; |
207 | } |
163 | } |
208 | 164 | ||
209 | gscr->native = nconn; |
165 | gscr->native = nconn; |
210 | gscr->native_modes = native_modes; |
166 | gscr->native_modes = native_modes; |
211 | 167 | ||
212 | _eglLinkScreen(&gscr->base); |
168 | _eglLinkScreen(&gscr->base); |
213 | } |
169 | } |
214 | 170 | ||
215 | FREE(native_connectors); |
171 | FREE(native_connectors); |
216 | } |
172 | } |
217 | 173 | ||
218 | #endif /* EGL_MESA_screen_surface */ |
174 | #endif /* EGL_MESA_screen_surface */ |
219 | 175 | ||
220 | /** |
176 | /** |
221 | * Initialize and validate the EGL config attributes. |
177 | * Initialize and validate the EGL config attributes. |
222 | */ |
178 | */ |
223 | static EGLBoolean |
179 | static EGLBoolean |
224 | init_config_attributes(_EGLConfig *conf, const struct native_config *nconf, |
180 | init_config_attributes(_EGLConfig *conf, const struct native_config *nconf, |
225 | EGLint api_mask, enum pipe_format depth_stencil_format, |
181 | EGLint api_mask, enum pipe_format depth_stencil_format, |
226 | EGLint preserve_buffer, EGLint max_swap_interval, |
182 | EGLint preserve_buffer, EGLint max_swap_interval, |
227 | EGLBoolean pre_alpha) |
183 | EGLBoolean pre_alpha) |
228 | { |
184 | { |
229 | uint rgba[4], depth_stencil[2], buffer_size; |
185 | uint rgba[4], depth_stencil[2], buffer_size; |
230 | EGLint surface_type; |
186 | EGLint surface_type; |
231 | EGLint i; |
187 | EGLint i; |
232 | 188 | ||
233 | /* get the color and depth/stencil component sizes */ |
189 | /* get the color and depth/stencil component sizes */ |
234 | assert(nconf->color_format != PIPE_FORMAT_NONE); |
190 | assert(nconf->color_format != PIPE_FORMAT_NONE); |
235 | buffer_size = 0; |
191 | buffer_size = 0; |
236 | for (i = 0; i < 4; i++) { |
192 | for (i = 0; i < 4; i++) { |
237 | rgba[i] = util_format_get_component_bits(nconf->color_format, |
193 | rgba[i] = util_format_get_component_bits(nconf->color_format, |
238 | UTIL_FORMAT_COLORSPACE_RGB, i); |
194 | UTIL_FORMAT_COLORSPACE_RGB, i); |
239 | buffer_size += rgba[i]; |
195 | buffer_size += rgba[i]; |
240 | } |
196 | } |
241 | for (i = 0; i < 2; i++) { |
197 | for (i = 0; i < 2; i++) { |
242 | if (depth_stencil_format != PIPE_FORMAT_NONE) { |
198 | if (depth_stencil_format != PIPE_FORMAT_NONE) { |
243 | depth_stencil[i] = |
199 | depth_stencil[i] = |
244 | util_format_get_component_bits(depth_stencil_format, |
200 | util_format_get_component_bits(depth_stencil_format, |
245 | UTIL_FORMAT_COLORSPACE_ZS, i); |
201 | UTIL_FORMAT_COLORSPACE_ZS, i); |
246 | } |
202 | } |
247 | else { |
203 | else { |
248 | depth_stencil[i] = 0; |
204 | depth_stencil[i] = 0; |
249 | } |
205 | } |
250 | } |
206 | } |
251 | 207 | ||
252 | surface_type = 0x0; |
208 | surface_type = 0x0; |
253 | /* pixmap surfaces should be EGL_SINGLE_BUFFER */ |
209 | /* pixmap surfaces should be EGL_SINGLE_BUFFER */ |
254 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_FRONT_LEFT)) { |
210 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_FRONT_LEFT)) { |
255 | if (nconf->pixmap_bit) |
211 | if (nconf->pixmap_bit) |
256 | surface_type |= EGL_PIXMAP_BIT; |
212 | surface_type |= EGL_PIXMAP_BIT; |
257 | } |
213 | } |
258 | /* the others surfaces should be EGL_BACK_BUFFER (or settable) */ |
214 | /* the others surfaces should be EGL_BACK_BUFFER (or settable) */ |
259 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_BACK_LEFT)) { |
215 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_BACK_LEFT)) { |
260 | if (nconf->window_bit) |
216 | if (nconf->window_bit) |
261 | surface_type |= EGL_WINDOW_BIT; |
217 | surface_type |= EGL_WINDOW_BIT; |
262 | #ifdef EGL_MESA_screen_surface |
218 | #ifdef EGL_MESA_screen_surface |
263 | if (nconf->scanout_bit) |
219 | if (nconf->scanout_bit) |
264 | surface_type |= EGL_SCREEN_BIT_MESA; |
220 | surface_type |= EGL_SCREEN_BIT_MESA; |
265 | #endif |
221 | #endif |
266 | surface_type |= EGL_PBUFFER_BIT; |
222 | surface_type |= EGL_PBUFFER_BIT; |
267 | } |
223 | } |
268 | 224 | ||
269 | if (preserve_buffer) |
225 | if (preserve_buffer) |
270 | surface_type |= EGL_SWAP_BEHAVIOR_PRESERVED_BIT; |
226 | surface_type |= EGL_SWAP_BEHAVIOR_PRESERVED_BIT; |
271 | 227 | ||
272 | if (pre_alpha && rgba[3]) { |
228 | if (pre_alpha && rgba[3]) { |
273 | surface_type |= EGL_VG_ALPHA_FORMAT_PRE_BIT; |
229 | surface_type |= EGL_VG_ALPHA_FORMAT_PRE_BIT; |
274 | /* st/vega does not support premultiplied alpha yet */ |
230 | /* st/vega does not support premultiplied alpha yet */ |
275 | api_mask &= ~EGL_OPENVG_BIT; |
231 | api_mask &= ~EGL_OPENVG_BIT; |
276 | } |
232 | } |
277 | 233 | ||
278 | conf->Conformant = api_mask; |
234 | conf->Conformant = api_mask; |
279 | conf->RenderableType = api_mask; |
235 | conf->RenderableType = api_mask; |
280 | 236 | ||
281 | conf->RedSize = rgba[0]; |
237 | conf->RedSize = rgba[0]; |
282 | conf->GreenSize = rgba[1]; |
238 | conf->GreenSize = rgba[1]; |
283 | conf->BlueSize = rgba[2]; |
239 | conf->BlueSize = rgba[2]; |
284 | conf->AlphaSize = rgba[3]; |
240 | conf->AlphaSize = rgba[3]; |
285 | conf->BufferSize = buffer_size; |
241 | conf->BufferSize = buffer_size; |
286 | 242 | ||
287 | conf->DepthSize = depth_stencil[0]; |
243 | conf->DepthSize = depth_stencil[0]; |
288 | conf->StencilSize = depth_stencil[1]; |
244 | conf->StencilSize = depth_stencil[1]; |
289 | 245 | ||
290 | /* st/vega will allocate the mask on demand */ |
246 | /* st/vega will allocate the mask on demand */ |
291 | if (api_mask & EGL_OPENVG_BIT) |
247 | if (api_mask & EGL_OPENVG_BIT) |
292 | conf->AlphaMaskSize = 8; |
248 | conf->AlphaMaskSize = 8; |
293 | 249 | ||
294 | conf->SurfaceType = surface_type; |
250 | conf->SurfaceType = surface_type; |
295 | 251 | ||
296 | conf->NativeRenderable = EGL_TRUE; |
252 | conf->NativeRenderable = EGL_TRUE; |
297 | if (surface_type & EGL_WINDOW_BIT) { |
253 | if (surface_type & EGL_WINDOW_BIT) { |
298 | conf->NativeVisualID = nconf->native_visual_id; |
254 | conf->NativeVisualID = nconf->native_visual_id; |
299 | conf->NativeVisualType = nconf->native_visual_type; |
255 | conf->NativeVisualType = nconf->native_visual_type; |
300 | } |
256 | } |
301 | 257 | ||
302 | if (surface_type & EGL_PBUFFER_BIT) { |
258 | if (surface_type & EGL_PBUFFER_BIT) { |
303 | conf->BindToTextureRGB = EGL_TRUE; |
259 | conf->BindToTextureRGB = EGL_TRUE; |
304 | if (rgba[3]) |
260 | if (rgba[3]) |
305 | conf->BindToTextureRGBA = EGL_TRUE; |
261 | conf->BindToTextureRGBA = EGL_TRUE; |
306 | 262 | ||
307 | conf->MaxPbufferWidth = 4096; |
263 | conf->MaxPbufferWidth = 4096; |
308 | conf->MaxPbufferHeight = 4096; |
264 | conf->MaxPbufferHeight = 4096; |
309 | conf->MaxPbufferPixels = 4096 * 4096; |
265 | conf->MaxPbufferPixels = 4096 * 4096; |
310 | } |
266 | } |
311 | 267 | ||
312 | conf->Level = nconf->level; |
268 | conf->Level = nconf->level; |
313 | 269 | ||
314 | if (nconf->transparent_rgb) { |
270 | if (nconf->transparent_rgb) { |
315 | conf->TransparentType = EGL_TRANSPARENT_RGB; |
271 | conf->TransparentType = EGL_TRANSPARENT_RGB; |
316 | conf->TransparentRedValue = nconf->transparent_rgb_values[0]; |
272 | conf->TransparentRedValue = nconf->transparent_rgb_values[0]; |
317 | conf->TransparentGreenValue = nconf->transparent_rgb_values[1]; |
273 | conf->TransparentGreenValue = nconf->transparent_rgb_values[1]; |
318 | conf->TransparentBlueValue = nconf->transparent_rgb_values[2]; |
274 | conf->TransparentBlueValue = nconf->transparent_rgb_values[2]; |
319 | } |
275 | } |
320 | 276 | ||
321 | conf->MinSwapInterval = 0; |
277 | conf->MinSwapInterval = 0; |
322 | conf->MaxSwapInterval = max_swap_interval; |
278 | conf->MaxSwapInterval = max_swap_interval; |
323 | 279 | ||
324 | return _eglValidateConfig(conf, EGL_FALSE); |
280 | return _eglValidateConfig(conf, EGL_FALSE); |
325 | } |
281 | } |
326 | 282 | ||
327 | /** |
283 | /** |
328 | * Initialize an EGL config from the native config. |
284 | * Initialize an EGL config from the native config. |
329 | */ |
285 | */ |
330 | static EGLBoolean |
286 | static EGLBoolean |
331 | egl_g3d_init_config(_EGLDriver *drv, _EGLDisplay *dpy, |
287 | egl_g3d_init_config(_EGLDriver *drv, _EGLDisplay *dpy, |
332 | _EGLConfig *conf, const struct native_config *nconf, |
288 | _EGLConfig *conf, const struct native_config *nconf, |
333 | enum pipe_format depth_stencil_format, |
289 | enum pipe_format depth_stencil_format, |
334 | int preserve_buffer, int max_swap_interval, |
290 | int preserve_buffer, int max_swap_interval, |
335 | int pre_alpha) |
291 | int pre_alpha) |
336 | { |
292 | { |
337 | struct egl_g3d_config *gconf = egl_g3d_config(conf); |
293 | struct egl_g3d_config *gconf = egl_g3d_config(conf); |
338 | EGLint buffer_mask; |
294 | EGLint buffer_mask; |
339 | EGLBoolean valid; |
295 | EGLBoolean valid; |
340 | 296 | ||
341 | buffer_mask = 0x0; |
297 | buffer_mask = 0x0; |
342 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_FRONT_LEFT)) |
298 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_FRONT_LEFT)) |
343 | buffer_mask |= ST_ATTACHMENT_FRONT_LEFT_MASK; |
299 | buffer_mask |= ST_ATTACHMENT_FRONT_LEFT_MASK; |
344 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_BACK_LEFT)) |
300 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_BACK_LEFT)) |
345 | buffer_mask |= ST_ATTACHMENT_BACK_LEFT_MASK; |
301 | buffer_mask |= ST_ATTACHMENT_BACK_LEFT_MASK; |
346 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_FRONT_RIGHT)) |
302 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_FRONT_RIGHT)) |
347 | buffer_mask |= ST_ATTACHMENT_FRONT_RIGHT_MASK; |
303 | buffer_mask |= ST_ATTACHMENT_FRONT_RIGHT_MASK; |
348 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_BACK_RIGHT)) |
304 | if (nconf->buffer_mask & (1 << NATIVE_ATTACHMENT_BACK_RIGHT)) |
349 | buffer_mask |= ST_ATTACHMENT_BACK_RIGHT_MASK; |
305 | buffer_mask |= ST_ATTACHMENT_BACK_RIGHT_MASK; |
350 | 306 | ||
351 | gconf->stvis.buffer_mask = buffer_mask; |
307 | gconf->stvis.buffer_mask = buffer_mask; |
352 | gconf->stvis.color_format = nconf->color_format; |
308 | gconf->stvis.color_format = nconf->color_format; |
353 | gconf->stvis.depth_stencil_format = depth_stencil_format; |
309 | gconf->stvis.depth_stencil_format = depth_stencil_format; |
354 | gconf->stvis.accum_format = PIPE_FORMAT_NONE; |
310 | gconf->stvis.accum_format = PIPE_FORMAT_NONE; |
355 | gconf->stvis.samples = 0; |
311 | gconf->stvis.samples = 0; |
356 | 312 | ||
357 | /* will be overridden per surface */ |
313 | /* will be overridden per surface */ |
358 | gconf->stvis.render_buffer = (buffer_mask & ST_ATTACHMENT_BACK_LEFT_MASK) ? |
314 | gconf->stvis.render_buffer = (buffer_mask & ST_ATTACHMENT_BACK_LEFT_MASK) ? |
359 | ST_ATTACHMENT_BACK_LEFT : ST_ATTACHMENT_FRONT_LEFT; |
315 | ST_ATTACHMENT_BACK_LEFT : ST_ATTACHMENT_FRONT_LEFT; |
360 | 316 | ||
361 | valid = init_config_attributes(&gconf->base, |
317 | valid = init_config_attributes(&gconf->base, |
362 | nconf, dpy->ClientAPIs, depth_stencil_format, |
318 | nconf, dpy->ClientAPIs, depth_stencil_format, |
363 | preserve_buffer, max_swap_interval, pre_alpha); |
319 | preserve_buffer, max_swap_interval, pre_alpha); |
364 | if (!valid) { |
320 | if (!valid) { |
365 | _eglLog(_EGL_DEBUG, "skip invalid config 0x%x", nconf->native_visual_id); |
321 | _eglLog(_EGL_DEBUG, "skip invalid config 0x%x", nconf->native_visual_id); |
366 | return EGL_FALSE; |
322 | return EGL_FALSE; |
367 | } |
323 | } |
368 | 324 | ||
369 | gconf->native = nconf; |
325 | gconf->native = nconf; |
370 | 326 | ||
371 | return EGL_TRUE; |
327 | return EGL_TRUE; |
372 | } |
328 | } |
373 | 329 | ||
374 | /** |
330 | /** |
375 | * Get all interested depth/stencil formats of a display. |
331 | * Get all interested depth/stencil formats of a display. |
376 | */ |
332 | */ |
377 | static EGLint |
333 | static EGLint |
378 | egl_g3d_fill_depth_stencil_formats(_EGLDisplay *dpy, |
334 | egl_g3d_fill_depth_stencil_formats(_EGLDisplay *dpy, |
379 | enum pipe_format formats[8]) |
335 | enum pipe_format formats[8]) |
380 | { |
336 | { |
381 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
337 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
382 | struct pipe_screen *screen = gdpy->native->screen; |
338 | struct pipe_screen *screen = gdpy->native->screen; |
383 | const EGLint candidates[] = { |
339 | const EGLint candidates[] = { |
384 | 1, PIPE_FORMAT_Z16_UNORM, |
340 | 1, PIPE_FORMAT_Z16_UNORM, |
385 | 1, PIPE_FORMAT_Z32_UNORM, |
341 | 1, PIPE_FORMAT_Z32_UNORM, |
386 | 2, PIPE_FORMAT_Z24_UNORM_S8_UINT, PIPE_FORMAT_S8_UINT_Z24_UNORM, |
342 | 2, PIPE_FORMAT_Z24_UNORM_S8_UINT, PIPE_FORMAT_S8_UINT_Z24_UNORM, |
387 | 2, PIPE_FORMAT_Z24X8_UNORM, PIPE_FORMAT_X8Z24_UNORM, |
343 | 2, PIPE_FORMAT_Z24X8_UNORM, PIPE_FORMAT_X8Z24_UNORM, |
388 | 0 |
344 | 0 |
389 | }; |
345 | }; |
390 | const EGLint *fmt = candidates; |
346 | const EGLint *fmt = candidates; |
391 | EGLint count; |
347 | EGLint count; |
392 | 348 | ||
393 | count = 0; |
349 | count = 0; |
394 | formats[count++] = PIPE_FORMAT_NONE; |
350 | formats[count++] = PIPE_FORMAT_NONE; |
395 | 351 | ||
396 | while (*fmt) { |
352 | while (*fmt) { |
397 | EGLint i, n = *fmt++; |
353 | EGLint i, n = *fmt++; |
398 | 354 | ||
399 | /* pick the first supported format */ |
355 | /* pick the first supported format */ |
400 | for (i = 0; i < n; i++) { |
356 | for (i = 0; i < n; i++) { |
401 | if (screen->is_format_supported(screen, fmt[i], |
357 | if (screen->is_format_supported(screen, fmt[i], |
402 | PIPE_TEXTURE_2D, 0, PIPE_BIND_DEPTH_STENCIL)) { |
358 | PIPE_TEXTURE_2D, 0, PIPE_BIND_DEPTH_STENCIL)) { |
403 | formats[count++] = fmt[i]; |
359 | formats[count++] = fmt[i]; |
404 | break; |
360 | break; |
405 | } |
361 | } |
406 | } |
362 | } |
407 | 363 | ||
408 | fmt += n; |
364 | fmt += n; |
409 | } |
365 | } |
410 | 366 | ||
411 | return count; |
367 | return count; |
412 | } |
368 | } |
413 | 369 | ||
414 | /** |
370 | /** |
415 | * Add configs to display and return the next config ID. |
371 | * Add configs to display and return the next config ID. |
416 | */ |
372 | */ |
417 | static EGLint |
373 | static EGLint |
418 | egl_g3d_add_configs(_EGLDriver *drv, _EGLDisplay *dpy, EGLint id) |
374 | egl_g3d_add_configs(_EGLDriver *drv, _EGLDisplay *dpy, EGLint id) |
419 | { |
375 | { |
420 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
376 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
421 | const struct native_config **native_configs; |
377 | const struct native_config **native_configs; |
422 | enum pipe_format depth_stencil_formats[8]; |
378 | enum pipe_format depth_stencil_formats[8]; |
423 | int num_formats, num_configs, i, j; |
379 | int num_formats, num_configs, i, j; |
424 | int preserve_buffer, max_swap_interval, premultiplied_alpha; |
380 | int preserve_buffer, max_swap_interval, premultiplied_alpha; |
425 | 381 | ||
426 | native_configs = gdpy->native->get_configs(gdpy->native, &num_configs); |
382 | native_configs = gdpy->native->get_configs(gdpy->native, &num_configs); |
427 | if (!num_configs) { |
383 | if (!num_configs) { |
428 | FREE(native_configs); |
384 | FREE(native_configs); |
429 | return id; |
385 | return id; |
430 | } |
386 | } |
431 | 387 | ||
432 | preserve_buffer = |
388 | preserve_buffer = |
433 | gdpy->native->get_param(gdpy->native, NATIVE_PARAM_PRESERVE_BUFFER); |
389 | gdpy->native->get_param(gdpy->native, NATIVE_PARAM_PRESERVE_BUFFER); |
434 | max_swap_interval = |
390 | max_swap_interval = |
435 | gdpy->native->get_param(gdpy->native, NATIVE_PARAM_MAX_SWAP_INTERVAL); |
391 | gdpy->native->get_param(gdpy->native, NATIVE_PARAM_MAX_SWAP_INTERVAL); |
436 | premultiplied_alpha = |
392 | premultiplied_alpha = |
437 | gdpy->native->get_param(gdpy->native, NATIVE_PARAM_PREMULTIPLIED_ALPHA); |
393 | gdpy->native->get_param(gdpy->native, NATIVE_PARAM_PREMULTIPLIED_ALPHA); |
438 | 394 | ||
439 | num_formats = egl_g3d_fill_depth_stencil_formats(dpy, |
395 | num_formats = egl_g3d_fill_depth_stencil_formats(dpy, |
440 | depth_stencil_formats); |
396 | depth_stencil_formats); |
441 | 397 | ||
442 | for (i = 0; i < num_configs; i++) { |
398 | for (i = 0; i < num_configs; i++) { |
443 | for (j = 0; j < num_formats; j++) { |
399 | for (j = 0; j < num_formats; j++) { |
444 | struct egl_g3d_config *gconf; |
400 | struct egl_g3d_config *gconf; |
445 | 401 | ||
446 | gconf = CALLOC_STRUCT(egl_g3d_config); |
402 | gconf = CALLOC_STRUCT(egl_g3d_config); |
447 | if (gconf) { |
403 | if (gconf) { |
448 | _eglInitConfig(&gconf->base, dpy, id); |
404 | _eglInitConfig(&gconf->base, dpy, id); |
449 | if (!egl_g3d_init_config(drv, dpy, &gconf->base, |
405 | if (!egl_g3d_init_config(drv, dpy, &gconf->base, |
450 | native_configs[i], depth_stencil_formats[j], |
406 | native_configs[i], depth_stencil_formats[j], |
451 | preserve_buffer, max_swap_interval, |
407 | preserve_buffer, max_swap_interval, |
452 | premultiplied_alpha)) { |
408 | premultiplied_alpha)) { |
453 | FREE(gconf); |
409 | FREE(gconf); |
454 | break; |
410 | break; |
455 | } |
411 | } |
456 | 412 | ||
457 | _eglLinkConfig(&gconf->base); |
413 | _eglLinkConfig(&gconf->base); |
458 | id++; |
414 | id++; |
459 | } |
415 | } |
460 | } |
416 | } |
461 | } |
417 | } |
462 | 418 | ||
463 | FREE(native_configs); |
419 | FREE(native_configs); |
464 | return id; |
420 | return id; |
465 | } |
421 | } |
466 | 422 | ||
467 | static void |
423 | static void |
468 | egl_g3d_free_config(void *conf) |
424 | egl_g3d_free_config(void *conf) |
469 | { |
425 | { |
470 | struct egl_g3d_config *gconf = egl_g3d_config((_EGLConfig *) conf); |
426 | struct egl_g3d_config *gconf = egl_g3d_config((_EGLConfig *) conf); |
471 | FREE(gconf); |
427 | FREE(gconf); |
472 | } |
428 | } |
473 | 429 | ||
474 | static void |
430 | static void |
475 | egl_g3d_free_screen(void *scr) |
431 | egl_g3d_free_screen(void *scr) |
476 | { |
432 | { |
477 | #ifdef EGL_MESA_screen_surface |
433 | #ifdef EGL_MESA_screen_surface |
478 | struct egl_g3d_screen *gscr = egl_g3d_screen((_EGLScreen *) scr); |
434 | struct egl_g3d_screen *gscr = egl_g3d_screen((_EGLScreen *) scr); |
479 | FREE(gscr->native_modes); |
435 | FREE(gscr->native_modes); |
480 | FREE(gscr); |
436 | FREE(gscr); |
481 | #endif |
437 | #endif |
482 | } |
438 | } |
483 | 439 | ||
484 | static EGLBoolean |
440 | static EGLBoolean |
485 | egl_g3d_terminate(_EGLDriver *drv, _EGLDisplay *dpy) |
441 | egl_g3d_terminate(_EGLDriver *drv, _EGLDisplay *dpy) |
486 | { |
442 | { |
487 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
443 | struct egl_g3d_display *gdpy = egl_g3d_display(dpy); |
488 | 444 | ||
489 | _eglReleaseDisplayResources(drv, dpy); |
445 | _eglReleaseDisplayResources(drv, dpy); |
490 | 446 | ||
491 | if (dpy->Configs) { |
447 | if (dpy->Configs) { |
492 | _eglDestroyArray(dpy->Configs, egl_g3d_free_config); |
448 | _eglDestroyArray(dpy->Configs, egl_g3d_free_config); |
493 | dpy->Configs = NULL; |
449 | dpy->Configs = NULL; |
494 | } |
450 | } |
495 | if (dpy->Screens) { |
451 | if (dpy->Screens) { |
496 | _eglDestroyArray(dpy->Screens, egl_g3d_free_screen); |
452 | _eglDestroyArray(dpy->Screens, egl_g3d_free_screen); |
497 | dpy->Screens = NULL; |
453 | dpy->Screens = NULL; |
498 | } |
454 | } |
499 | 455 | ||
500 | _eglCleanupDisplay(dpy); |
456 | _eglCleanupDisplay(dpy); |
501 | 457 | ||
502 | if (gdpy->smapi) |
458 | if (gdpy->smapi) |
503 | egl_g3d_destroy_st_manager(gdpy->smapi); |
459 | egl_g3d_destroy_st_manager(gdpy->smapi); |
504 | 460 | ||
505 | if (gdpy->native) |
461 | if (gdpy->native) |
506 | gdpy->native->destroy(gdpy->native); |
462 | gdpy->native->destroy(gdpy->native); |
507 | 463 | ||
508 | FREE(gdpy); |
464 | FREE(gdpy); |
509 | dpy->DriverData = NULL; |
465 | dpy->DriverData = NULL; |
510 | 466 | ||
511 | return EGL_TRUE; |
467 | return EGL_TRUE; |
512 | } |
468 | } |
513 | 469 | ||
514 | static EGLBoolean |
470 | static EGLBoolean |
515 | egl_g3d_initialize(_EGLDriver *drv, _EGLDisplay *dpy) |
471 | egl_g3d_initialize(_EGLDriver *drv, _EGLDisplay *dpy) |
516 | { |
472 | { |
517 | struct egl_g3d_driver *gdrv = egl_g3d_driver(drv); |
473 | struct egl_g3d_driver *gdrv = egl_g3d_driver(drv); |
518 | struct egl_g3d_display *gdpy; |
474 | struct egl_g3d_display *gdpy; |
519 | const struct native_platform *nplat; |
475 | const struct native_platform *nplat; |
520 | 476 | ||
521 | nplat = egl_g3d_get_platform(drv, dpy->Platform); |
477 | nplat = egl_g3d_get_platform(drv, dpy->Platform); |
522 | if (!nplat) |
478 | if (!nplat) |
523 | return EGL_FALSE; |
479 | return EGL_FALSE; |
524 | 480 | ||
525 | if (dpy->Options.TestOnly) |
481 | if (dpy->Options.TestOnly) |
526 | return EGL_TRUE; |
482 | return EGL_TRUE; |
527 | 483 | ||
528 | gdpy = CALLOC_STRUCT(egl_g3d_display); |
484 | gdpy = CALLOC_STRUCT(egl_g3d_display); |
529 | if (!gdpy) { |
485 | if (!gdpy) { |
530 | _eglError(EGL_BAD_ALLOC, "eglInitialize"); |
486 | _eglError(EGL_BAD_ALLOC, "eglInitialize"); |
531 | goto fail; |
487 | goto fail; |
532 | } |
488 | } |
533 | gdpy->loader = gdrv->loader; |
489 | gdpy->loader = gdrv->loader; |
534 | dpy->DriverData = gdpy; |
490 | dpy->DriverData = gdpy; |
535 | 491 | ||
536 | _eglLog(_EGL_INFO, "use %s for display %p", |
492 | _eglLog(_EGL_INFO, "use %s for display %p", |
537 | nplat->name, dpy->PlatformDisplay); |
493 | nplat->name, dpy->PlatformDisplay); |
538 | gdpy->native = |
494 | gdpy->native = |
539 | nplat->create_display(dpy->PlatformDisplay, dpy->Options.UseFallback); |
495 | nplat->create_display(dpy->PlatformDisplay, dpy->Options.UseFallback); |
540 | if (!gdpy->native) { |
496 | if (!gdpy->native) { |
541 | _eglError(EGL_NOT_INITIALIZED, "eglInitialize(no usable display)"); |
497 | _eglError(EGL_NOT_INITIALIZED, "eglInitialize(no usable display)"); |
542 | goto fail; |
498 | goto fail; |
543 | } |
499 | } |
544 | gdpy->native->user_data = (void *) dpy; |
500 | gdpy->native->user_data = (void *) dpy; |
545 | if (!gdpy->native->init_screen(gdpy->native)) { |
501 | if (!gdpy->native->init_screen(gdpy->native)) { |
546 | _eglError(EGL_NOT_INITIALIZED, |
502 | _eglError(EGL_NOT_INITIALIZED, |
547 | "eglInitialize(failed to initialize screen)"); |
503 | "eglInitialize(failed to initialize screen)"); |
548 | goto fail; |
504 | goto fail; |
549 | } |
505 | } |
550 | 506 | ||
551 | if (gdpy->loader->profile_masks[ST_API_OPENGL] & ST_PROFILE_DEFAULT_MASK) |
507 | if (gdpy->loader->profile_masks[ST_API_OPENGL] & ST_PROFILE_DEFAULT_MASK) |
552 | dpy->ClientAPIs |= EGL_OPENGL_BIT; |
508 | dpy->ClientAPIs |= EGL_OPENGL_BIT; |
553 | if (gdpy->loader->profile_masks[ST_API_OPENGL] & ST_PROFILE_OPENGL_ES1_MASK) |
509 | if (gdpy->loader->profile_masks[ST_API_OPENGL] & ST_PROFILE_OPENGL_ES1_MASK) |
554 | dpy->ClientAPIs |= EGL_OPENGL_ES_BIT; |
510 | dpy->ClientAPIs |= EGL_OPENGL_ES_BIT; |
555 | if (gdpy->loader->profile_masks[ST_API_OPENGL] & ST_PROFILE_OPENGL_ES2_MASK) |
511 | if (gdpy->loader->profile_masks[ST_API_OPENGL] & ST_PROFILE_OPENGL_ES2_MASK) |
556 | dpy->ClientAPIs |= EGL_OPENGL_ES2_BIT; |
512 | dpy->ClientAPIs |= EGL_OPENGL_ES2_BIT; |
557 | if (gdpy->loader->profile_masks[ST_API_OPENVG] & ST_PROFILE_DEFAULT_MASK) |
513 | if (gdpy->loader->profile_masks[ST_API_OPENVG] & ST_PROFILE_DEFAULT_MASK) |
558 | dpy->ClientAPIs |= EGL_OPENVG_BIT; |
514 | dpy->ClientAPIs |= EGL_OPENVG_BIT; |
559 | 515 | ||
560 | gdpy->smapi = egl_g3d_create_st_manager(dpy); |
516 | gdpy->smapi = egl_g3d_create_st_manager(dpy); |
561 | if (!gdpy->smapi) { |
517 | if (!gdpy->smapi) { |
562 | _eglError(EGL_NOT_INITIALIZED, |
518 | _eglError(EGL_NOT_INITIALIZED, |
563 | "eglInitialize(failed to create st manager)"); |
519 | "eglInitialize(failed to create st manager)"); |
564 | goto fail; |
520 | goto fail; |
565 | } |
521 | } |
566 | 522 | ||
567 | #ifdef EGL_MESA_screen_surface |
523 | #ifdef EGL_MESA_screen_surface |
568 | /* enable MESA_screen_surface before adding (and validating) configs */ |
524 | /* enable MESA_screen_surface before adding (and validating) configs */ |
569 | if (gdpy->native->modeset) { |
525 | if (gdpy->native->modeset) { |
570 | dpy->Extensions.MESA_screen_surface = EGL_TRUE; |
526 | dpy->Extensions.MESA_screen_surface = EGL_TRUE; |
571 | egl_g3d_add_screens(drv, dpy); |
527 | egl_g3d_add_screens(drv, dpy); |
572 | } |
528 | } |
573 | #endif |
529 | #endif |
574 | 530 | ||
575 | dpy->Extensions.KHR_image_base = EGL_TRUE; |
531 | dpy->Extensions.KHR_image_base = EGL_TRUE; |
576 | if (gdpy->native->get_param(gdpy->native, NATIVE_PARAM_USE_NATIVE_BUFFER)) |
532 | if (gdpy->native->get_param(gdpy->native, NATIVE_PARAM_USE_NATIVE_BUFFER)) |
577 | dpy->Extensions.KHR_image_pixmap = EGL_TRUE; |
533 | dpy->Extensions.KHR_image_pixmap = EGL_TRUE; |
578 | 534 | ||
579 | dpy->Extensions.KHR_reusable_sync = EGL_TRUE; |
535 | dpy->Extensions.KHR_reusable_sync = EGL_TRUE; |
580 | dpy->Extensions.KHR_fence_sync = EGL_TRUE; |
536 | dpy->Extensions.KHR_fence_sync = EGL_TRUE; |
581 | 537 | ||
582 | dpy->Extensions.KHR_surfaceless_context = EGL_TRUE; |
538 | dpy->Extensions.KHR_surfaceless_context = EGL_TRUE; |
583 | 539 | ||
584 | if (dpy->Platform == _EGL_PLATFORM_DRM) { |
540 | if (dpy->Platform == _EGL_PLATFORM_DRM) { |
585 | dpy->Extensions.MESA_drm_display = EGL_TRUE; |
541 | dpy->Extensions.MESA_drm_display = EGL_TRUE; |
586 | if (gdpy->native->buffer) |
542 | if (gdpy->native->buffer) |
587 | dpy->Extensions.MESA_drm_image = EGL_TRUE; |
543 | dpy->Extensions.MESA_drm_image = EGL_TRUE; |
588 | } |
544 | } |
589 | 545 | ||
590 | if (dpy->Platform == _EGL_PLATFORM_WAYLAND && gdpy->native->buffer) |
546 | // if (dpy->Platform == _EGL_PLATFORM_WAYLAND && gdpy->native->buffer) |
591 | dpy->Extensions.MESA_drm_image = EGL_TRUE; |
- | |
592 | - | ||
593 | #ifdef EGL_ANDROID_image_native_buffer |
- | |
594 | if (dpy->Platform == _EGL_PLATFORM_ANDROID && gdpy->native->buffer) |
- | |
595 | dpy->Extensions.ANDROID_image_native_buffer = EGL_TRUE; |
- | |
596 | #endif |
- | |
597 | - | ||
598 | #ifdef EGL_WL_bind_wayland_display |
- | |
599 | if (gdpy->native->wayland_bufmgr) |
- | |
600 | dpy->Extensions.WL_bind_wayland_display = EGL_TRUE; |
547 | // dpy->Extensions.MESA_drm_image = EGL_TRUE; |
601 | #endif |
548 | |
602 | 549 | ||
603 | if (gdpy->native->get_param(gdpy->native, NATIVE_PARAM_PRESENT_REGION) && |
550 | if (gdpy->native->get_param(gdpy->native, NATIVE_PARAM_PRESENT_REGION) && |
604 | gdpy->native->get_param(gdpy->native, NATIVE_PARAM_PRESERVE_BUFFER)) { |
551 | gdpy->native->get_param(gdpy->native, NATIVE_PARAM_PRESERVE_BUFFER)) { |
605 | #ifdef EGL_NOK_swap_region |
552 | #ifdef EGL_NOK_swap_region |
606 | dpy->Extensions.NOK_swap_region = EGL_TRUE; |
553 | dpy->Extensions.NOK_swap_region = EGL_TRUE; |
607 | #endif |
554 | #endif |
608 | dpy->Extensions.NV_post_sub_buffer = EGL_TRUE; |
555 | dpy->Extensions.NV_post_sub_buffer = EGL_TRUE; |
609 | } |
556 | } |
610 | 557 | ||
611 | if (egl_g3d_add_configs(drv, dpy, 1) == 1) { |
558 | if (egl_g3d_add_configs(drv, dpy, 1) == 1) { |
612 | _eglError(EGL_NOT_INITIALIZED, "eglInitialize(unable to add configs)"); |
559 | _eglError(EGL_NOT_INITIALIZED, "eglInitialize(unable to add configs)"); |
613 | goto fail; |
560 | goto fail; |
614 | } |
561 | } |
615 | 562 | ||
616 | dpy->VersionMajor = 1; |
563 | dpy->VersionMajor = 1; |
617 | dpy->VersionMinor = 4; |
564 | dpy->VersionMinor = 4; |
618 | 565 | ||
619 | return EGL_TRUE; |
566 | return EGL_TRUE; |
620 | 567 | ||
621 | fail: |
568 | fail: |
622 | if (gdpy) |
569 | if (gdpy) |
623 | egl_g3d_terminate(drv, dpy); |
570 | egl_g3d_terminate(drv, dpy); |
624 | return EGL_FALSE; |
571 | return EGL_FALSE; |
625 | } |
572 | } |
626 | 573 | ||
627 | static _EGLProc |
574 | static _EGLProc |
628 | egl_g3d_get_proc_address(_EGLDriver *drv, const char *procname) |
575 | egl_g3d_get_proc_address(_EGLDriver *drv, const char *procname) |
629 | { |
576 | { |
630 | struct egl_g3d_driver *gdrv = egl_g3d_driver(drv); |
577 | struct egl_g3d_driver *gdrv = egl_g3d_driver(drv); |
631 | struct st_api *stapi = NULL; |
578 | struct st_api *stapi = NULL; |
632 | 579 | ||
633 | if (procname && procname[0] == 'v' && procname[1] == 'g') |
580 | if (procname && procname[0] == 'v' && procname[1] == 'g') |
634 | stapi = gdrv->loader->get_st_api(ST_API_OPENVG); |
581 | stapi = gdrv->loader->get_st_api(ST_API_OPENVG); |
635 | else if (procname && procname[0] == 'g' && procname[1] == 'l') |
582 | else if (procname && procname[0] == 'g' && procname[1] == 'l') |
636 | stapi = gdrv->loader->get_st_api(ST_API_OPENGL); |
583 | stapi = gdrv->loader->get_st_api(ST_API_OPENGL); |
637 | 584 | ||
638 | return (_EGLProc) ((stapi) ? |
585 | return (_EGLProc) ((stapi) ? |
639 | stapi->get_proc_address(stapi, procname) : NULL); |
586 | stapi->get_proc_address(stapi, procname) : NULL); |
640 | } |
587 | } |
641 | 588 | ||
642 | _EGLDriver * |
589 | _EGLDriver * |
643 | egl_g3d_create_driver(const struct egl_g3d_loader *loader) |
590 | egl_g3d_create_driver(const struct egl_g3d_loader *loader) |
644 | { |
591 | { |
645 | struct egl_g3d_driver *gdrv; |
592 | struct egl_g3d_driver *gdrv; |
646 | 593 | ||
647 | gdrv = CALLOC_STRUCT(egl_g3d_driver); |
594 | gdrv = CALLOC_STRUCT(egl_g3d_driver); |
648 | if (!gdrv) |
595 | if (!gdrv) |
649 | return NULL; |
596 | return NULL; |
650 | 597 | ||
651 | gdrv->loader = loader; |
598 | gdrv->loader = loader; |
652 | 599 | ||
653 | egl_g3d_init_driver_api(&gdrv->base); |
600 | egl_g3d_init_driver_api(&gdrv->base); |
654 | gdrv->base.API.Initialize = egl_g3d_initialize; |
601 | gdrv->base.API.Initialize = egl_g3d_initialize; |
655 | gdrv->base.API.Terminate = egl_g3d_terminate; |
602 | gdrv->base.API.Terminate = egl_g3d_terminate; |
656 | gdrv->base.API.GetProcAddress = egl_g3d_get_proc_address; |
603 | gdrv->base.API.GetProcAddress = egl_g3d_get_proc_address; |
657 | 604 | ||
658 | /* to be filled by the caller */ |
605 | /* to be filled by the caller */ |
659 | gdrv->base.Name = NULL; |
606 | gdrv->base.Name = NULL; |
660 | gdrv->base.Unload = NULL; |
607 | gdrv->base.Unload = NULL; |
661 | 608 | ||
662 | return &gdrv->base; |
609 | return &gdrv->base; |
663 | } |
610 | } |
664 | 611 | ||
665 | void |
612 | void |
666 | egl_g3d_destroy_driver(_EGLDriver *drv) |
613 | egl_g3d_destroy_driver(_EGLDriver *drv) |
667 | { |
614 | { |
668 | struct egl_g3d_driver *gdrv = egl_g3d_driver(drv); |
615 | struct egl_g3d_driver *gdrv = egl_g3d_driver(drv); |
669 | FREE(gdrv); |
616 | FREE(gdrv); |
670 | }>>>><>><>><>><>><>><>>>>> |
617 | }>>>><>><>><>><>><>><>>>>> |