Xcb: fix crash on screen power save
Handle various cases where we have null QScreen or QPlatformScreen pointers. With this change, I can run Qt Creator for several days. Before, it would crash multiple times per day with a two-monitor setup. Change-Id: I0923d886ae2a4199ac37edd711ddd4f6f99df93d Reviewed-by: Friedemann Kleint <Friedemann.Kleint@theqtcompany.com> Reviewed-by: Lars Knoll <lars.knoll@theqtcompany.com> Reviewed-by: Shawn Rutledge <shawn.rutledge@theqtcompany.com>
This commit is contained in:
parent
a38df3f3ba
commit
7532fb4e61
@ -311,9 +311,12 @@ QPaintDevice *QXcbBackingStore::paintDevice()
|
|||||||
|
|
||||||
void QXcbBackingStore::beginPaint(const QRegion ®ion)
|
void QXcbBackingStore::beginPaint(const QRegion ®ion)
|
||||||
{
|
{
|
||||||
|
if (!m_image && !m_size.isEmpty())
|
||||||
|
resize(m_size, QRegion());
|
||||||
|
|
||||||
if (!m_image)
|
if (!m_image)
|
||||||
return;
|
return;
|
||||||
|
m_size = QSize();
|
||||||
m_paintRegion = region;
|
m_paintRegion = region;
|
||||||
m_image->preparePaint(m_paintRegion);
|
m_image->preparePaint(m_paintRegion);
|
||||||
|
|
||||||
@ -420,7 +423,8 @@ void QXcbBackingStore::resize(const QSize &size, const QRegion &)
|
|||||||
return;
|
return;
|
||||||
Q_XCB_NOOP(connection());
|
Q_XCB_NOOP(connection());
|
||||||
|
|
||||||
QXcbScreen *screen = static_cast<QXcbScreen *>(window()->screen()->handle());
|
|
||||||
|
QXcbScreen *screen = window()->screen() ? static_cast<QXcbScreen *>(window()->screen()->handle()) : 0;
|
||||||
QPlatformWindow *pw = window()->handle();
|
QPlatformWindow *pw = window()->handle();
|
||||||
if (!pw) {
|
if (!pw) {
|
||||||
window()->create();
|
window()->create();
|
||||||
@ -429,6 +433,11 @@ void QXcbBackingStore::resize(const QSize &size, const QRegion &)
|
|||||||
QXcbWindow* win = static_cast<QXcbWindow *>(pw);
|
QXcbWindow* win = static_cast<QXcbWindow *>(pw);
|
||||||
|
|
||||||
delete m_image;
|
delete m_image;
|
||||||
|
if (!screen) {
|
||||||
|
m_image = 0;
|
||||||
|
m_size = size;
|
||||||
|
return;
|
||||||
|
}
|
||||||
m_image = new QXcbShmImage(screen, size, win->depth(), win->imageFormat());
|
m_image = new QXcbShmImage(screen, size, win->depth(), win->imageFormat());
|
||||||
// Slow path for bgr888 VNC: Create an additional image, paint into that and
|
// Slow path for bgr888 VNC: Create an additional image, paint into that and
|
||||||
// swap R and B while copying to m_image after each paint.
|
// swap R and B while copying to m_image after each paint.
|
||||||
|
@ -71,6 +71,7 @@ private:
|
|||||||
QXcbShmImage *m_image;
|
QXcbShmImage *m_image;
|
||||||
QRegion m_paintRegion;
|
QRegion m_paintRegion;
|
||||||
QImage m_rgbImage;
|
QImage m_rgbImage;
|
||||||
|
QSize m_size;
|
||||||
};
|
};
|
||||||
|
|
||||||
QT_END_NAMESPACE
|
QT_END_NAMESPACE
|
||||||
|
@ -652,7 +652,7 @@ void QXcbWindow::setGeometry(const QRect &rect)
|
|||||||
m_xcbScreen = newScreen;
|
m_xcbScreen = newScreen;
|
||||||
const QRect wmGeometry = windowToWmGeometry(rect);
|
const QRect wmGeometry = windowToWmGeometry(rect);
|
||||||
|
|
||||||
if (newScreen != currentScreen)
|
if (newScreen && newScreen != currentScreen)
|
||||||
QWindowSystemInterface::handleWindowScreenChanged(window(), newScreen->QPlatformScreen::screen());
|
QWindowSystemInterface::handleWindowScreenChanged(window(), newScreen->QPlatformScreen::screen());
|
||||||
|
|
||||||
if (qt_window_private(window())->positionAutomatic) {
|
if (qt_window_private(window())->positionAutomatic) {
|
||||||
@ -1606,7 +1606,7 @@ void QXcbWindow::requestActivateWindow()
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!m_mapped) {
|
if (!m_mapped || !xcbScreen()) {
|
||||||
m_deferredActivation = true;
|
m_deferredActivation = true;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user