*/
#include <stdbool.h>
+#include <stdint.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include "egl_dri2.h"
#include "egl_dri2_fallbacks.h"
+#include "loader.h"
static EGLBoolean
dri2_x11_swap_interval(_EGLDriver *drv, _EGLDisplay *disp, _EGLSurface *surf,
static void
swrastCreateDrawable(struct dri2_egl_display * dri2_dpy,
- struct dri2_egl_surface * dri2_surf,
- int depth)
+ struct dri2_egl_surface * dri2_surf)
{
uint32_t mask;
const uint32_t function = GXcopy;
uint32_t valgc[2];
-
+
/* create GC's */
dri2_surf->gc = xcb_generate_id(dri2_dpy->conn);
mask = XCB_GC_FUNCTION;
valgc[0] = function;
valgc[1] = False;
xcb_create_gc(dri2_dpy->conn, dri2_surf->swapgc, dri2_surf->drawable, mask, valgc);
- dri2_surf->depth = depth;
- switch (depth) {
+ switch (dri2_surf->depth) {
case 32:
case 24:
dri2_surf->bytes_per_pixel = 4;
dri2_surf->bytes_per_pixel = 0;
break;
default:
- _eglLog(_EGL_WARNING, "unsupported depth %d", depth);
+ _eglLog(_EGL_WARNING, "unsupported depth %d", dri2_surf->depth);
}
}
dri2_surf->drawable, screen->root,
dri2_surf->base.Width, dri2_surf->base.Height);
} else {
+ if (!drawable) {
+ _eglError(EGL_BAD_NATIVE_WINDOW, "dri2_create_surface");
+ goto cleanup_surf;
+ }
dri2_surf->drawable = drawable;
}
if (dri2_dpy->dri2) {
- dri2_surf->dri_drawable =
- (*dri2_dpy->dri2->createNewDrawable) (dri2_dpy->dri_screen,
- type == EGL_WINDOW_BIT ?
- dri2_conf->dri_double_config :
- dri2_conf->dri_single_config,
- dri2_surf);
+ const __DRIconfig *config =
+ dri2_get_dri_config(dri2_conf, type, dri2_surf->base.GLColorspace);
+
+ dri2_surf->dri_drawable =
+ (*dri2_dpy->dri2->createNewDrawable)(dri2_dpy->dri_screen, config,
+ dri2_surf);
} else {
assert(dri2_dpy->swrast);
dri2_surf->dri_drawable =
_eglError(EGL_BAD_ALLOC, "dri2->createNewDrawable");
goto cleanup_pixmap;
}
-
- if (dri2_dpy->dri2) {
- xcb_dri2_create_drawable (dri2_dpy->conn, dri2_surf->drawable);
- } else {
- swrastCreateDrawable(dri2_dpy, dri2_surf, _eglGetConfigKey(conf, EGL_BUFFER_SIZE));
- }
if (type != EGL_PBUFFER_BIT) {
cookie = xcb_get_geometry (dri2_dpy->conn, dri2_surf->drawable);
dri2_surf->base.Width = reply->width;
dri2_surf->base.Height = reply->height;
+ dri2_surf->depth = reply->depth;
free(reply);
}
+ if (dri2_dpy->dri2) {
+ xcb_dri2_create_drawable (dri2_dpy->conn, dri2_surf->drawable);
+ } else {
+ if (type == EGL_PBUFFER_BIT) {
+ dri2_surf->depth = _eglGetConfigKey(conf, EGL_BUFFER_SIZE);
+ }
+ swrastCreateDrawable(dri2_dpy, dri2_surf);
+ }
+
/* we always copy the back buffer to front */
dri2_surf->base.PostSubBufferSupportedNV = EGL_TRUE;
return EGL_FALSE;
}
- driver_name = xcb_dri2_connect_driver_name (connect);
- dri2_dpy->driver_name =
- strndup(driver_name,
- xcb_dri2_connect_driver_name_length(connect));
-
device_name = xcb_dri2_connect_device_name (connect);
dri2_dpy->device_name =
strndup(device_name,
xcb_dri2_connect_device_name_length(connect));
+ dri2_dpy->fd = loader_open_device(dri2_dpy->device_name);
+ if (dri2_dpy->fd == -1) {
+ _eglLog(_EGL_WARNING,
+ "DRI2: could not open %s (%s)", dri2_dpy->device_name,
+ strerror(errno));
+ free(dri2_dpy->device_name);
+ free(connect);
+ return EGL_FALSE;
+ }
+
+ driver_name = xcb_dri2_connect_driver_name (connect);
+ dri2_dpy->driver_name =
+ strndup(driver_name,
+ xcb_dri2_connect_driver_name_length(connect));
+
if (dri2_dpy->device_name == NULL || dri2_dpy->driver_name == NULL) {
+ close(dri2_dpy->fd);
free(dri2_dpy->device_name);
free(dri2_dpy->driver_name);
free(connect);
}
}
-static _EGLImage*
-dri2_x11_swrast_create_image_khr(_EGLDriver *drv, _EGLDisplay *disp,
- _EGLContext *ctx, EGLenum target,
- EGLClientBuffer buffer,
- const EGLint *attr_list)
-{
- return NULL;
-}
-
static EGLBoolean
dri2_x11_get_sync_values(_EGLDisplay *display, _EGLSurface *surface,
EGLuint64KHR *ust, EGLuint64KHR *msc,
.create_pixmap_surface = dri2_x11_create_pixmap_surface,
.create_pbuffer_surface = dri2_x11_create_pbuffer_surface,
.destroy_surface = dri2_x11_destroy_surface,
- .create_image = dri2_x11_swrast_create_image_khr,
+ .create_image = dri2_fallback_create_image_khr,
.swap_interval = dri2_fallback_swap_interval,
.swap_buffers = dri2_x11_swap_buffers,
.swap_buffers_region = dri2_fallback_swap_buffers_region,
goto cleanup_conn;
dri2_dpy->swrast_loader_extension.base.name = __DRI_SWRAST_LOADER;
- dri2_dpy->swrast_loader_extension.base.version = __DRI_SWRAST_LOADER_VERSION;
+ dri2_dpy->swrast_loader_extension.base.version = 2;
dri2_dpy->swrast_loader_extension.getDrawableInfo = swrastGetDrawableInfo;
dri2_dpy->swrast_loader_extension.putImage = swrastPutImage;
dri2_dpy->swrast_loader_extension.getImage = swrastGetImage;
goto cleanup_configs;
}
- /* we're supporting EGL 1.4 */
- disp->VersionMajor = 1;
- disp->VersionMinor = 4;
-
/* Fill vtbl last to prevent accidentally calling virtual function during
* initialization.
*/
dri2_dpy->screen = DefaultScreen(dpy);
}
- if (xcb_connection_has_error(dri2_dpy->conn)) {
+ if (!dri2_dpy->conn || xcb_connection_has_error(dri2_dpy->conn)) {
_eglLog(_EGL_WARNING, "DRI2: xcb_connect failed");
goto cleanup_dpy;
}
- if (dri2_dpy->conn) {
- if (!dri2_x11_connect(dri2_dpy))
- goto cleanup_conn;
- }
+ if (!dri2_x11_connect(dri2_dpy))
+ goto cleanup_conn;
if (!dri2_load_driver(disp))
- goto cleanup_conn;
+ goto cleanup_fd;
-#ifdef O_CLOEXEC
- dri2_dpy->fd = open(dri2_dpy->device_name, O_RDWR | O_CLOEXEC);
- if (dri2_dpy->fd == -1 && errno == EINVAL)
-#endif
- {
- dri2_dpy->fd = open(dri2_dpy->device_name, O_RDWR);
- if (dri2_dpy->fd != -1)
- fcntl(dri2_dpy->fd, F_SETFD, fcntl(dri2_dpy->fd, F_GETFD) |
- FD_CLOEXEC);
- }
- if (dri2_dpy->fd == -1) {
- _eglLog(_EGL_WARNING,
- "DRI2: could not open %s (%s)", dri2_dpy->device_name,
- strerror(errno));
+ if (!dri2_x11_local_authenticate(disp))
goto cleanup_driver;
- }
-
- if (dri2_dpy->conn) {
- if (!dri2_x11_local_authenticate(disp))
- goto cleanup_fd;
- }
if (dri2_dpy->dri2_minor >= 1) {
dri2_dpy->dri2_loader_extension.base.name = __DRI_DRI2_LOADER;
dri2_dpy->invalidate_available = (dri2_dpy->dri2_minor >= 3);
if (!dri2_create_screen(disp))
- goto cleanup_fd;
+ goto cleanup_driver;
dri2_x11_setup_swap_interval(dri2_dpy);
- if (dri2_dpy->conn) {
- if (!dri2_x11_add_configs_for_visuals(dri2_dpy, disp))
- goto cleanup_configs;
- }
-
disp->Extensions.KHR_image_pixmap = EGL_TRUE;
disp->Extensions.NOK_swap_region = EGL_TRUE;
disp->Extensions.NOK_texture_from_pixmap = EGL_TRUE;
disp->Extensions.WL_bind_wayland_display = EGL_TRUE;
#endif
- if (dri2_dpy->conn) {
- if (!dri2_x11_add_configs_for_visuals(dri2_dpy, disp))
- goto cleanup_configs;
- }
-
- /* we're supporting EGL 1.4 */
- disp->VersionMajor = 1;
- disp->VersionMinor = 4;
+ if (!dri2_x11_add_configs_for_visuals(dri2_dpy, disp))
+ goto cleanup_configs;
/* Fill vtbl last to prevent accidentally calling virtual function during
* initialization.
cleanup_configs:
_eglCleanupDisplay(disp);
dri2_dpy->core->destroyScreen(dri2_dpy->dri_screen);
- cleanup_fd:
- close(dri2_dpy->fd);
cleanup_driver:
dlclose(dri2_dpy->driver);
+ cleanup_fd:
+ close(dri2_dpy->fd);
cleanup_conn:
if (disp->PlatformDisplay == NULL)
xcb_disconnect(dri2_dpy->conn);