diff options
-rw-r--r-- | src/corelib/kernel/qcoreapplication.cpp | 6 | ||||
-rw-r--r-- | tests/auto/corelib/kernel/qcoreapplication/tst_qcoreapplication.cpp | 28 |
2 files changed, 32 insertions, 2 deletions
diff --git a/src/corelib/kernel/qcoreapplication.cpp b/src/corelib/kernel/qcoreapplication.cpp index 0301a40876..c3a05551b8 100644 --- a/src/corelib/kernel/qcoreapplication.cpp +++ b/src/corelib/kernel/qcoreapplication.cpp @@ -1451,7 +1451,7 @@ void QCoreApplicationPrivate::sendPostedEvents(QObject *receiver, int event_type // first, we diddle the event so that we can deliver // it, and that no one will try to touch it later. pe.event->posted = false; - QScopedPointer<QEvent> e(pe.event); + QEvent *e = pe.event; QObject * r = pe.receiver; --r->d_func()->postedEvents; @@ -1469,8 +1469,10 @@ void QCoreApplicationPrivate::sendPostedEvents(QObject *receiver, int event_type }; MutexUnlocker unlocker(locker); + QScopedPointer<QEvent> event_deleter(e); // will delete the event (with the mutex unlocked) + // after all that work, it's time to deliver the event. - QCoreApplication::sendEvent(r, e.data()); + QCoreApplication::sendEvent(r, e); // careful when adding anything below this point - the // sendEvent() call might invalidate any invariants this diff --git a/tests/auto/corelib/kernel/qcoreapplication/tst_qcoreapplication.cpp b/tests/auto/corelib/kernel/qcoreapplication/tst_qcoreapplication.cpp index ff1d8b2a36..ccaa2bec4f 100644 --- a/tests/auto/corelib/kernel/qcoreapplication/tst_qcoreapplication.cpp +++ b/tests/auto/corelib/kernel/qcoreapplication/tst_qcoreapplication.cpp @@ -69,6 +69,7 @@ private slots: void eventLoopExecAfterExit(); void customEventDispatcher(); void testQuitLock(); + void QTBUG31606_QEventDestructorDeadLock(); }; class EventSpy : public QObject @@ -769,6 +770,33 @@ void tst_QCoreApplication::testQuitLock() app.exec(); } + +void tst_QCoreApplication::QTBUG31606_QEventDestructorDeadLock() +{ + class MyEvent : public QEvent + { public: + MyEvent() : QEvent(QEvent::Type(QEvent::User + 1)) {} + ~MyEvent() { + QCoreApplication::postEvent(qApp, new QEvent(QEvent::Type(QEvent::User+2))); + } + }; + + int argc = 1; + char *argv[] = { const_cast<char*>("tst_qcoreapplication") }; + QCoreApplication app(argc, argv); + + EventSpy spy; + app.installEventFilter(&spy); + + QCoreApplication::postEvent(&app, new MyEvent); + QCoreApplication::processEvents(); + QVERIFY(spy.recordedEvents.contains(QEvent::User + 1)); + QVERIFY(!spy.recordedEvents.contains(QEvent::User + 2)); + QCoreApplication::processEvents(); + QVERIFY(spy.recordedEvents.contains(QEvent::User + 2)); +} + + static void createQObjectOnDestruction() { // Make sure that we can create a QObject after the last QObject has been |