2 * Surface-related functions.
4 * See the eglcontext.c file for comments that also apply here.
11 #include "eglcontext.h"
12 #include "eglconfig.h"
13 #include "eglglobals.h"
16 #include "eglsurface.h"
20 * Do error check on parameters and initialize the given _EGLSurface object.
21 * \return EGL_TRUE if no errors, EGL_FALSE otherwise.
24 _eglInitSurface(_EGLDriver
*drv
, EGLDisplay dpy
,
25 _EGLSurface
*surf
, EGLint type
, EGLConfig config
,
26 const EGLint
*attrib_list
)
30 EGLint width
= 0, height
= 0, largest
= 0;
31 EGLint texFormat
= 0, texTarget
= 0, mipmapTex
= 0;
36 func
= "eglCreateWindowSurface";
39 func
= "eglCreatePixmapSurface";
42 func
= "eglCreatePBufferSurface";
44 case EGL_SCREEN_BIT_MESA
:
45 func
= "eglCreateScreenSurface";
48 _eglLog(_EGL_WARNING
, "Bad type in _eglInitSurface");
52 conf
= _eglLookupConfig(drv
, dpy
, config
);
54 _eglError(EGL_BAD_CONFIG
, func
);
59 * Parse attribute list. Different kinds of surfaces support different
62 for (i
= 0; attrib_list
&& attrib_list
[i
] != EGL_NONE
; i
++) {
63 switch (attrib_list
[i
]) {
65 if (type
== EGL_PBUFFER_BIT
|| type
== EGL_SCREEN_BIT_MESA
) {
66 width
= attrib_list
[++i
];
69 _eglError(EGL_BAD_ATTRIBUTE
, func
);
74 if (type
== EGL_PBUFFER_BIT
|| type
== EGL_SCREEN_BIT_MESA
) {
75 height
= attrib_list
[++i
];
78 _eglError(EGL_BAD_ATTRIBUTE
, func
);
82 case EGL_LARGEST_PBUFFER
:
83 if (type
== EGL_PBUFFER_BIT
) {
84 largest
= attrib_list
[++i
];
87 _eglError(EGL_BAD_ATTRIBUTE
, func
);
91 case EGL_TEXTURE_FORMAT
:
92 if (type
== EGL_PBUFFER_BIT
) {
93 texFormat
= attrib_list
[++i
];
96 _eglError(EGL_BAD_ATTRIBUTE
, func
);
100 case EGL_TEXTURE_TARGET
:
101 if (type
== EGL_PBUFFER_BIT
) {
102 texTarget
= attrib_list
[++i
];
105 _eglError(EGL_BAD_ATTRIBUTE
, func
);
109 case EGL_MIPMAP_TEXTURE
:
110 if (type
== EGL_PBUFFER_BIT
) {
111 mipmapTex
= attrib_list
[++i
];
114 _eglError(EGL_BAD_ATTRIBUTE
, func
);
119 _eglError(EGL_BAD_ATTRIBUTE
, func
);
124 if (width
<= 0 || height
<= 0) {
125 _eglError(EGL_BAD_ATTRIBUTE
, func
);
129 memset(surf
, 0, sizeof(_EGLSurface
));
133 surf
->Height
= height
;
134 surf
->TextureFormat
= texFormat
;
135 surf
->TextureTarget
= texTarget
;
136 surf
->MipmapTexture
= mipmapTex
;
137 surf
->MipmapLevel
= 0;
138 surf
->SwapInterval
= 0;
145 _eglSaveSurface(_EGLSurface
*surf
)
148 assert(!surf
->Handle
);
149 surf
->Handle
= _eglHashGenKey(_eglGlobal
.Contexts
);
150 assert(surf
->Handle
);
151 _eglHashInsert(_eglGlobal
.Surfaces
, surf
->Handle
, surf
);
156 _eglRemoveSurface(_EGLSurface
*surf
)
158 _eglHashRemove(_eglGlobal
.Surfaces
, surf
->Handle
);
163 _eglLookupSurface(EGLSurface surf
)
165 _EGLSurface
*c
= (_EGLSurface
*) _eglHashLookup(_eglGlobal
.Surfaces
, surf
);
171 _eglGetCurrentSurface(EGLint readdraw
)
173 _EGLContext
*ctx
= _eglGetCurrentContext();
177 return ctx
->DrawSurface
;
179 return ctx
->ReadSurface
;
189 _eglSwapBuffers(_EGLDriver
*drv
, EGLDisplay dpy
, EGLSurface draw
)
191 /* Basically just do error checking here. Drivers have to do the
192 * actual buffer swap.
194 _EGLContext
*context
= _eglGetCurrentContext();
195 _EGLSurface
*surface
= _eglLookupSurface(draw
);
196 if (context
&& context
->DrawSurface
!= surface
) {
197 _eglError(EGL_BAD_SURFACE
, "eglSwapBuffers");
200 if (surface
== NULL
) {
201 _eglError(EGL_BAD_SURFACE
, "eglSwapBuffers");
209 _eglCopyBuffers(_EGLDriver
*drv
, EGLDisplay dpy
, EGLSurface surface
,
210 NativePixmapType target
)
212 /* copy surface to native pixmap */
213 /* All implementation burdon for this is in the device driver */
219 _eglQuerySurface(_EGLDriver
*drv
, EGLDisplay dpy
, EGLSurface surf
,
220 EGLint attribute
, EGLint
*value
)
222 _EGLSurface
*surface
= _eglLookupSurface(surf
);
223 if (surface
== NULL
) {
224 _eglError(EGL_BAD_SURFACE
, "eglQuerySurface");
229 *value
= surface
->Width
;
232 *value
= surface
->Height
;
235 *value
= GET_CONFIG_ATTRIB(surface
->Config
, EGL_CONFIG_ID
);
237 case EGL_TEXTURE_FORMAT
:
238 /* texture attributes: only for pbuffers, no error otherwise */
239 if (surface
->Type
== EGL_PBUFFER_BIT
)
240 *value
= surface
->TextureFormat
;
242 case EGL_TEXTURE_TARGET
:
243 if (surface
->Type
== EGL_PBUFFER_BIT
)
244 *value
= surface
->TextureTarget
;
246 case EGL_MIPMAP_TEXTURE
:
247 if (surface
->Type
== EGL_PBUFFER_BIT
)
248 *value
= surface
->MipmapTexture
;
250 case EGL_MIPMAP_LEVEL
:
251 if (surface
->Type
== EGL_PBUFFER_BIT
)
252 *value
= surface
->MipmapLevel
;
254 case EGL_SURFACE_TYPE
:
255 *value
= surface
->Type
;
258 _eglError(EGL_BAD_ATTRIBUTE
, "eglQuerySurface");
265 * Example function - drivers should do a proper implementation.
268 _eglCreateWindowSurface(_EGLDriver
*drv
, EGLDisplay dpy
, EGLConfig config
,
269 NativeWindowType window
, const EGLint
*attrib_list
)
271 #if 0 /* THIS IS JUST EXAMPLE CODE */
274 surf
= (_EGLSurface
*) calloc(1, sizeof(_EGLSurface
));
276 return EGL_NO_SURFACE
;
278 if (!_eglInitSurface(drv
, dpy
, surf
, EGL_WINDOW_BIT
, config
, attrib_list
)) {
280 return EGL_NO_SURFACE
;
283 _eglSaveSurface(surf
);
287 return EGL_NO_SURFACE
;
292 * Example function - drivers should do a proper implementation.
295 _eglCreatePixmapSurface(_EGLDriver
*drv
, EGLDisplay dpy
, EGLConfig config
,
296 NativePixmapType pixmap
, const EGLint
*attrib_list
)
298 #if 0 /* THIS IS JUST EXAMPLE CODE */
301 surf
= (_EGLSurface
*) calloc(1, sizeof(_EGLSurface
));
303 return EGL_NO_SURFACE
;
305 if (!_eglInitSurface(drv
, dpy
, surf
, EGL_PIXMAP_BIT
, config
, attrib_list
)) {
307 return EGL_NO_SURFACE
;
310 _eglSaveSurface(surf
);
314 return EGL_NO_SURFACE
;
319 * Example function - drivers should do a proper implementation.
322 _eglCreatePbufferSurface(_EGLDriver
*drv
, EGLDisplay dpy
, EGLConfig config
,
323 const EGLint
*attrib_list
)
325 #if 0 /* THIS IS JUST EXAMPLE CODE */
328 surf
= (_EGLSurface
*) calloc(1, sizeof(_EGLSurface
));
330 return EGL_NO_SURFACE
;
332 if (!_eglInitSurface(drv
, dpy
, surf
, EGL_PBUFFER_BIT
, config
, attrib_list
)) {
334 return EGL_NO_SURFACE
;
337 _eglSaveSurface(surf
);
341 return EGL_NO_SURFACE
;
346 * Default fallback routine - drivers should usually override this.
349 _eglDestroySurface(_EGLDriver
*drv
, EGLDisplay dpy
, EGLSurface surface
)
351 _EGLSurface
*surf
= _eglLookupSurface(surface
);
353 _eglHashRemove(_eglGlobal
.Surfaces
, surface
);
355 surf
->DeletePending
= EGL_TRUE
;
363 _eglError(EGL_BAD_SURFACE
, "eglDestroySurface");
370 * Default fallback routine - drivers might override this.
373 _eglSurfaceAttrib(_EGLDriver
*drv
, EGLDisplay dpy
, EGLSurface surf
, EGLint attribute
, EGLint value
)
375 _EGLSurface
*surface
= _eglLookupSurface(surf
);
377 if (surface
== NULL
) {
378 _eglError(EGL_BAD_SURFACE
, "eglSurfaceAttrib");
383 case EGL_MIPMAP_LEVEL
:
384 surface
->MipmapLevel
= value
;
387 _eglError(EGL_BAD_ATTRIBUTE
, "eglSurfaceAttrib");
395 _eglBindTexImage(_EGLDriver
*drv
, EGLDisplay dpy
, EGLSurface surface
, EGLint buffer
)
403 _eglReleaseTexImage(_EGLDriver
*drv
, EGLDisplay dpy
, EGLSurface surface
, EGLint buffer
)
411 _eglSwapInterval(_EGLDriver
*drv
, EGLDisplay dpy
, EGLint interval
)
413 _EGLSurface
*surf
= _eglGetCurrentSurface(EGL_DRAW
);
415 _eglError(EGL_BAD_SURFACE
, "eglSwapInterval");
418 surf
->SwapInterval
= interval
;