wayland: Use wayland-egl instead of drm specific code
authorKristian Høgsberg <krh@bitplanet.net>
Sat, 5 Feb 2011 14:20:19 +0000 (09:20 -0500)
committerJørgen Lind <jorgen.lind@nokia.com>
Mon, 7 Feb 2011 07:21:33 +0000 (08:21 +0100)
src/plugins/platforms/wayland/qwaylanddisplay.cpp
src/plugins/platforms/wayland/qwaylanddisplay.h
src/plugins/platforms/wayland/qwaylanddrmsurface.cpp
src/plugins/platforms/wayland/qwaylanddrmsurface.h
src/plugins/platforms/wayland/wayland.pro

index 70713ec..2e30c2f 100644 (file)
@@ -50,9 +50,7 @@
 #include <fcntl.h>
 #include <stdio.h>
 
-extern "C" {
-#include <xf86drm.h>
-}
+#include <wayland-egl.h>
 
 struct wl_surface *QWaylandDisplay::createSurface()
 {
@@ -67,14 +65,6 @@ struct wl_buffer *QWaylandDisplay::createShmBuffer(int fd,
     return wl_shm_create_buffer(mShm, fd, width, height, stride, visual);
 }
 
-struct wl_buffer *QWaylandDisplay::createDrmBuffer(int name,
-                                                   int width, int height,
-                                                   uint32_t stride,
-                                                   struct wl_visual *visual)
-{
-    return wl_drm_create_buffer(mDrm, name, width, height, stride, visual);
-}
-
 struct wl_visual *QWaylandDisplay::rgbVisual()
 {
     return wl_display_get_rgb_visual(mDisplay);
@@ -90,62 +80,11 @@ struct wl_visual *QWaylandDisplay::argbPremultipliedVisual()
     return wl_display_get_premultiplied_argb_visual(mDisplay);
 }
 
-void QWaylandDisplay::drmHandleDevice(void *data,
-                                      struct wl_drm *drm, const char *device)
+struct wl_egl_display *QWaylandDisplay::nativeDisplay()
 {
-    Q_UNUSED(drm);
-    QWaylandDisplay *qwd = (QWaylandDisplay *) data;
-    drm_magic_t magic;
-
-    qwd->mDeviceName = strdup(device);
-
-    qwd->mFd = open(qwd->mDeviceName, O_RDWR);
-    if (qwd->mFd < 0) {
-        qWarning("drm open failed: %m");
-        return;
-    }
-
-    if (drmGetMagic(qwd->mFd, &magic)) {
-        qWarning("DRI2: failed to get drm magic");
-        return;
-    }
-
-    wl_drm_authenticate(qwd->mDrm, magic);
+    return mNativeEglDisplay;
 }
 
-void QWaylandDisplay::drmHandleAuthenticated(void *data, struct wl_drm *drm)
-{
-    Q_UNUSED(drm);
-    QWaylandDisplay *qwd = (QWaylandDisplay *) data;
-    EGLint major, minor;
-    const char *extensions;
-
-    qwd->mEglDisplay = eglGetDRMDisplayMESA(qwd->mFd);
-    if (qwd->mEglDisplay == NULL) {
-        qWarning("failed to create display");
-        return;
-    }
-
-    if (!eglInitialize(qwd->mEglDisplay, &major, &minor)) {
-        qWarning("failed to initialize display");
-        qwd->mEglDisplay = NULL;
-        return;
-    }
-
-    extensions = eglQueryString(qwd->mEglDisplay, EGL_EXTENSIONS);
-    if (!strstr(extensions, "EGL_KHR_surfaceless_gles2")) {
-        qWarning("EGL_KHR_surfaceless_opengles2 not available");
-        eglTerminate(qwd->mEglDisplay);
-        qwd->mEglDisplay = NULL;
-        return;
-    }
-}
-
-const struct wl_drm_listener QWaylandDisplay::drmListener = {
-    QWaylandDisplay::drmHandleDevice,
-    QWaylandDisplay::drmHandleAuthenticated
-};
-
 void QWaylandDisplay::shellHandleConfigure(void *data, struct wl_shell *shell,
                                            uint32_t time, uint32_t edges,
                                            struct wl_surface *surface,
@@ -189,9 +128,6 @@ void QWaylandDisplay::displayHandleGlobal(struct wl_display *display,
 
     if (strcmp(interface, "compositor") == 0) {
         qwd->mCompositor = wl_compositor_create(display, id);
-    } else if (strcmp(interface, "drm") == 0) {
-        qwd->mDrm = wl_drm_create(display, id);
-        wl_drm_add_listener(qwd->mDrm, &drmListener, qwd);
     } else if (strcmp(interface, "shm") == 0) {
         qwd->mShm = wl_shm_create(display, id);
     } else if (strcmp(interface, "shell") == 0) {
@@ -207,26 +143,6 @@ void QWaylandDisplay::displayHandleGlobal(struct wl_display *display,
     }
 }
 
-static void roundtripCallback(void *data)
-{
-    bool *done = (bool *) data;
-
-    *done = true;
-}
-
-static void forceRoundtrip(struct wl_display *display)
-{
-    bool done;
-
-    wl_display_sync_callback(display, roundtripCallback, &done);
-    wl_display_iterate(display, WL_DISPLAY_WRITABLE);
-    done = false;
-    while (!done)
-        wl_display_iterate(display, WL_DISPLAY_READABLE);
-}
-
-static const char *socket_name = NULL;
-
 void QWaylandDisplay::eventDispatcher(void)
 {
     wl_display_iterate(mDisplay, WL_DISPLAY_READABLE);
@@ -257,7 +173,9 @@ void QWaylandDisplay::flushRequests(void)
 QWaylandDisplay::QWaylandDisplay(void)
     : mWriteNotifier(0)
 {
-    mDisplay = wl_display_connect(socket_name);
+    EGLint major, minor;
+
+    mDisplay = wl_display_connect(NULL);
     if (mDisplay == NULL) {
         fprintf(stderr, "failed to create display: %m\n");
         return;
@@ -266,18 +184,17 @@ QWaylandDisplay::QWaylandDisplay(void)
     wl_display_add_global_listener(mDisplay,
                                    QWaylandDisplay::displayHandleGlobal, this);
 
-    /* Process connection events. */
-    wl_display_iterate(mDisplay, WL_DISPLAY_READABLE);
-    if (!mShm || !mDeviceName)
-        forceRoundtrip(mDisplay);
+    mNativeEglDisplay = wl_egl_native_display_create(mDisplay);
 
-    /* Force a roundtrip to finish the drm authentication so we
-     * initialize EGL before proceeding */
-    forceRoundtrip(mDisplay);
-    if (mEglDisplay == NULL)
-        qDebug("EGL not available");
-    else
-        qDebug("EGL initialized");
+    mEglDisplay = eglGetDisplay(mNativeEglDisplay);
+    if (mEglDisplay == NULL) {
+        qWarning("EGL not available");
+    } else {
+       if (!eglInitialize(mEglDisplay, &major, &minor)) {
+           qWarning("failed to initialize EGL display");
+           return;
+       }
+    }
 
     int fd = wl_display_get_fd(mDisplay, sourceUpdate, this);
     mReadNotifier = new QSocketNotifier(fd, QSocketNotifier::Read, this);
@@ -293,6 +210,7 @@ QWaylandDisplay::QWaylandDisplay(void)
 QWaylandDisplay::~QWaylandDisplay(void)
 {
     close(mFd);
+    eglTerminate(mEglDisplay);
     wl_display_destroy(mDisplay);
 }
 
index f179713..375a9c1 100644 (file)
@@ -71,12 +71,10 @@ public:
     struct wl_buffer *createShmBuffer(int fd, int width, int height,
                                       uint32_t stride,
                                       struct wl_visual *visual);
-    struct wl_buffer *createDrmBuffer(int name, int width, int height,
-                                      uint32_t stride,
-                                      struct wl_visual *visual);
     struct wl_visual *rgbVisual();
     struct wl_visual *argbVisual();
     struct wl_visual *argbPremultipliedVisual();
+    struct wl_egl_display *nativeDisplay();
     EGLDisplay eglDisplay() { return mEglDisplay; }
 
     void setCursor(QWaylandBuffer *buffer, int32_t x, int32_t y);
@@ -91,7 +89,6 @@ public slots:
 private:
     struct wl_display *mDisplay;
     struct wl_compositor *mCompositor;
-    struct wl_drm *mDrm;
     struct wl_shm *mShm;
     struct wl_shell *mShell;
     char *mDeviceName;
@@ -101,16 +98,13 @@ private:
     QSocketNotifier *mReadNotifier;
     QSocketNotifier *mWriteNotifier;
     EGLDisplay mEglDisplay;
+    struct wl_egl_display *mNativeEglDisplay;
 
     static void displayHandleGlobal(struct wl_display *display,
                                     uint32_t id,
                                     const char *interface,
                                     uint32_t version, void *data);
 
-    static void drmHandleDevice(void *data,
-                                struct wl_drm *drm, const char *device);
-    static void drmHandleAuthenticated(void *data, struct wl_drm *drm);
-
     static void outputHandleGeometry(void *data,
                                      struct wl_output *output,
                                      int32_t x, int32_t y,
@@ -123,7 +117,6 @@ private:
 
     static int sourceUpdate(uint32_t mask, void *data);
 
-    static const struct wl_drm_listener drmListener;
     static const struct wl_output_listener outputListener;
     static const struct wl_shell_listener shellListener;
 };
index 603c018..a9a8046 100644 (file)
 #include <QtGui/private/qpaintengine_p.h>
 
 #include <wayland-client.h>
-#include <unistd.h>
-#include <fcntl.h>
-#include <errno.h>
-#include <sys/mman.h>
+#include <wayland-egl.h>
 
 QT_BEGIN_NAMESPACE
 
@@ -66,23 +63,6 @@ QWaylandDrmBuffer::QWaylandDrmBuffer(QWaylandDisplay *display,
     , mSize(size)
 {
     struct wl_visual *visual;
-    EGLint name, stride;
-    EGLint imageAttribs[] = {
-        EGL_WIDTH,                     size.width(),
-        EGL_HEIGHT,                    size.height(),
-       EGL_DRM_BUFFER_FORMAT_MESA,     EGL_DRM_BUFFER_FORMAT_ARGB32_MESA,
-        EGL_DRM_BUFFER_USE_MESA,       EGL_DRM_BUFFER_USE_SCANOUT_MESA,
-       EGL_NONE
-    };
-
-    mImage = eglCreateDRMImageMESA(mDisplay->eglDisplay(), imageAttribs);
-
-    glGenTextures(1, &mTexture);
-    glBindTexture(GL_TEXTURE_2D, mTexture);
-    glEGLImageTargetTexture2DOES(GL_TEXTURE_2D, mImage);
-
-    eglExportDRMImageMESA(mDisplay->eglDisplay(),
-                          mImage, &name, NULL, &stride);
 
     switch (format) {
     case QImage::Format_ARGB32:
@@ -97,14 +77,28 @@ QWaylandDrmBuffer::QWaylandDrmBuffer(QWaylandDisplay *display,
        break;
     }
 
-    mBuffer = display->createDrmBuffer(name, size.width(), size.height(),
-                                      stride, visual);
+    mPixmap = wl_egl_native_pixmap_create(display->nativeDisplay(),
+                                         size.width(), size.height(),
+                                         visual, 0);
+
+    mImage = eglCreateImageKHR(display->eglDisplay(),
+                              NULL, EGL_NATIVE_PIXMAP_KHR,
+                              (EGLClientBuffer) mPixmap, NULL);
+
+    glGenTextures(1, &mTexture);
+    qDebug() << "generating mTexture" << mTexture;
+    glBindTexture(GL_TEXTURE_2D, mTexture);
+    glEGLImageTargetTexture2DOES(GL_TEXTURE_2D, mImage);
+
+    mBuffer = wl_egl_native_pixmap_create_buffer(display->nativeDisplay(),
+                                                mPixmap);
 }
 
 QWaylandDrmBuffer::~QWaylandDrmBuffer(void)
 {
     glDeleteTextures(1, &mTexture);
     eglDestroyImageKHR(mDisplay->eglDisplay(), mImage);
+    wl_egl_native_pixmap_destroy(mPixmap);
     wl_buffer_destroy(mBuffer);
 }
 
index eafea13..f49263b 100644 (file)
@@ -76,6 +76,7 @@ public:
     QSize size() const { return mSize; }
 
 private:
+    struct wl_egl_pixmap *mPixmap;
     EGLImageKHR mImage;
     QWaylandDisplay *mDisplay;
     QSize mSize;
index 8ba1408..803a8e9 100644 (file)
@@ -27,7 +27,7 @@ HEADERS =   qwaylandintegration.h \
 contains(QT_CONFIG, opengl) {
     QT += opengl
 }
-LIBS += -lwayland-client -lxkbcommon -lEGL
+LIBS += -lwayland-client -lwayland-egl -lxkbcommon -lEGL
 unix {
        CONFIG += link_pkgconfig
        PKGCONFIG += libdrm