From a3524950a04329b7f37f0d1107902a59f86b2c3b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Samuel=20R=C3=B8dal?= Date: Wed, 30 Mar 2011 15:39:09 +0200 Subject: Fixed dead-locks in XCB window surface. Move the mutex lock into the window surface instead of belonging to the QXcbShmImage, which will be destroyed and recreated in resize(). --- src/plugins/platforms/xcb/qxcbwindowsurface.cpp | 21 ++++++++------------- src/plugins/platforms/xcb/qxcbwindowsurface.h | 3 +++ 2 files changed, 11 insertions(+), 13 deletions(-) diff --git a/src/plugins/platforms/xcb/qxcbwindowsurface.cpp b/src/plugins/platforms/xcb/qxcbwindowsurface.cpp index 8ab0140..c90ebb5 100644 --- a/src/plugins/platforms/xcb/qxcbwindowsurface.cpp +++ b/src/plugins/platforms/xcb/qxcbwindowsurface.cpp @@ -44,7 +44,6 @@ #include "qxcbconnection.h" #include "qxcbscreen.h" #include "qxcbwindow.h" -#include "qmutex.h" #include #include @@ -65,9 +64,6 @@ public: void put(xcb_window_t window, const QPoint &dst, const QRect &source); void preparePaint(const QRegion ®ion); - void lock() { m_surfaceLock.lock(); } - void unlock() { m_surfaceLock.unlock(); } - private: void destroy(); @@ -81,7 +77,6 @@ private: xcb_window_t m_gc_window; QRegion m_dirty; - QMutex m_surfaceLock; }; QXcbShmImage::QXcbShmImage(QXcbScreen *screen, const QSize &size) @@ -114,7 +109,8 @@ void QXcbShmImage::destroy() xcb_image_destroy(m_xcb_image); shmdt(m_shm_info.shmaddr); shmctl(m_shm_info.shmid, IPC_RMID, 0); - Q_XCB_CALL(xcb_free_gc(xcb_connection(), m_gc)); + if (m_gc) + Q_XCB_CALL(xcb_free_gc(xcb_connection(), m_gc)); } void QXcbShmImage::put(xcb_window_t window, const QPoint &target, const QRect &source) @@ -175,13 +171,13 @@ QPaintDevice *QXcbWindowSurface::paintDevice() void QXcbWindowSurface::beginPaint(const QRegion ®ion) { - m_image->lock(); + m_surfaceLock.lock(); m_image->preparePaint(region); } void QXcbWindowSurface::endPaint(const QRegion &) { - m_image->unlock(); + m_surfaceLock.unlock(); } void QXcbWindowSurface::flush(QWidget *widget, const QRegion ®ion, const QPoint &offset) @@ -189,18 +185,18 @@ void QXcbWindowSurface::flush(QWidget *widget, const QRegion ®ion, const QPoi Q_UNUSED(region); Q_UNUSED(offset); + connection()->sync(); + QXcbWindow *window = static_cast(widget->window()->platformWindow()); extern QWidgetData* qt_widget_data(QWidget *); QPoint widgetOffset = qt_qwidget_data(widget)->wrect.topLeft(); - m_image->lock(); + QMutexLocker(&m_surfaceLock); QVector rects = region.rects(); for (int i = 0; i < rects.size(); ++i) m_image->put(window->window(), rects.at(i).topLeft() - widgetOffset, rects.at(i).translated(offset)); - - m_image->unlock(); } void QXcbWindowSurface::resize(const QSize &size) @@ -209,8 +205,7 @@ void QXcbWindowSurface::resize(const QSize &size) QXcbScreen *screen = static_cast(QPlatformScreen::platformScreenForWidget(window())); - if (m_image) - m_image->lock(); + QMutexLocker(&m_surfaceLock); delete m_image; m_image = new QXcbShmImage(screen, size); diff --git a/src/plugins/platforms/xcb/qxcbwindowsurface.h b/src/plugins/platforms/xcb/qxcbwindowsurface.h index f87e122..e508fe6 100644 --- a/src/plugins/platforms/xcb/qxcbwindowsurface.h +++ b/src/plugins/platforms/xcb/qxcbwindowsurface.h @@ -48,6 +48,8 @@ #include "qxcbobject.h" +#include + class QXcbShmImage; class QXcbWindowSurface : public QXcbObject, public QWindowSurface @@ -66,6 +68,7 @@ public: private: QXcbShmImage *m_image; + QMutex m_surfaceLock; }; #endif -- cgit v0.12