-
Bug
-
Resolution: Unresolved
-
P3: Somewhat important
-
None
-
5.12.5
-
None
Consider the following example:
#include <QtCore/QAbstractEventDispatcher>
#include <QtCore/QCoreApplication>
#include <QtCore/QDebug>
QAtomicInt done = 0;
void E1();
void E2();
void E3();
void E1() {
qDebug() << "E1";
QMetaObject::invokeMethod(qApp, &E2, Qt::QueuedConnection);
QMetaObject::invokeMethod(qApp, &E3, Qt::QueuedConnection);
}
void E2() {
qDebug() << "E2";
while (done == 0) {
QCoreApplication::processEvents();
}
QCoreApplication::exit(0);
}
void E3() {
// We never reach this
qDebug() << "E3";
done = 1;
}
int main(int argc, char *argv[])
{
QCoreApplication app(argc, argv);
QMetaObject::invokeMethod(qApp, &E1, Qt::QueuedConnection);
app.exec();
}
As soon as some other thread posts an event E4 to the current event loop, E3 will be executed, followed by E4 as expected.
This is what happens:
- Posted events will increase a counter (serial number) in the glib event dispatcher
- Before a call into QCoreApplication::sendPostedEvents, the dispatcher stores the current counter value (lastSerialNumber). If multiple events are sitting in the event queue, the counter value will reflect the last posted event.
- Explicit periodic calls to QCoreApplication::processEvents() go into QEventDispatcherGlib::processEvents() which invokes an iteration in the glib event loop. So far so good.
- The glib event loop now calls postEventSourcePrepare() which compares the stored lastSerialNumber to the current serial number. This function acts as a filter to decide whether the glib event loop should invoke QCoreApplicationPrivate::sendPostedEvents(). Since it finds lastSerialNumber to be equal to the current serial number, it doesn't do anything.
- relates to
-
QTBUG-21049 processEvents processes only a single Event
-
- Closed
-