From b467b86bbf53340abf0cbfc41e92c0942db85b32 Mon Sep 17 00:00:00 2001 From: Rex Dieter Date: May 06 2016 18:29:21 +0000 Subject: more goodies, FTBFS fixes - pull in final/upstream fixes for QTBUG-51648,QTBUG-51649 - disable examples/tests in bootstrap mode --- diff --git a/0415-QtDBus-clean-up-signal-hooks-and-object-tree-in-clos.patch b/0415-QtDBus-clean-up-signal-hooks-and-object-tree-in-clos.patch new file mode 100644 index 0000000..3cac1ec --- /dev/null +++ b/0415-QtDBus-clean-up-signal-hooks-and-object-tree-in-clos.patch @@ -0,0 +1,87 @@ +From b77ef8a7e6e4104067d52824e29eadc8c66f5929 Mon Sep 17 00:00:00 2001 +From: Weng Xuetian +Date: Sat, 5 Mar 2016 12:23:21 -0800 +Subject: [PATCH 415/595] QtDBus: clean up signal hooks and object tree in + closeConnection + +If a QObject is added or passed as receiver to QDBusConnection::connect() +and it is managed by Q_GLOBAL_STATIC or similar mechanism, it is +possible that when that its destructor is called after the dbus daemon +thread ends. In that case, QObject::destroyed connected via +Qt::BlockingQueuedConnection to QDBusConnectionPrivate will cause dead +lock since the thread is no longer processing events. + +Task-number: QTBUG-51648 +Change-Id: I1a1810a6d6d0234af0269d5f3fc1f54101bf1547 +Reviewed-by: Thiago Macieira +--- + src/dbus/qdbusconnection_p.h | 1 + + src/dbus/qdbusintegrator.cpp | 26 +++++++++++++++++++++++++- + 2 files changed, 26 insertions(+), 1 deletion(-) + +diff --git a/src/dbus/qdbusconnection_p.h b/src/dbus/qdbusconnection_p.h +index c77daf7..565eb83 100644 +--- a/src/dbus/qdbusconnection_p.h ++++ b/src/dbus/qdbusconnection_p.h +@@ -254,6 +254,7 @@ private: + const QVector &metaTypes, int slotIdx); + + SignalHookHash::Iterator removeSignalHookNoLock(SignalHookHash::Iterator it); ++ void disconnectObjectTree(ObjectTreeNode &node); + + bool isServiceRegisteredByThread(const QString &serviceName); + +diff --git a/src/dbus/qdbusintegrator.cpp b/src/dbus/qdbusintegrator.cpp +index 478a2c4..3be775d 100644 +--- a/src/dbus/qdbusintegrator.cpp ++++ b/src/dbus/qdbusintegrator.cpp +@@ -1050,7 +1050,6 @@ QDBusConnectionPrivate::~QDBusConnectionPrivate() + qPrintable(name)); + + closeConnection(); +- rootNode.children.clear(); // free resources + qDeleteAll(cachedMetaObjects); + + if (mode == ClientMode || mode == PeerMode) { +@@ -1072,6 +1071,19 @@ QDBusConnectionPrivate::~QDBusConnectionPrivate() + } + } + ++void QDBusConnectionPrivate::disconnectObjectTree(QDBusConnectionPrivate::ObjectTreeNode &haystack) ++{ ++ QDBusConnectionPrivate::ObjectTreeNode::DataList::Iterator it = haystack.children.begin(); ++ ++ while (it != haystack.children.end()) { ++ disconnectObjectTree(*it); ++ it++; ++ } ++ ++ if (haystack.obj) ++ haystack.obj->disconnect(this); ++} ++ + void QDBusConnectionPrivate::closeConnection() + { + QDBusWriteLocker locker(CloseConnectionAction, this); +@@ -1095,6 +1107,18 @@ void QDBusConnectionPrivate::closeConnection() + } + + qDeleteAll(pendingCalls); ++ ++ // Disconnect all signals from signal hooks and from the object tree to ++ // avoid QObject::destroyed being sent to dbus daemon thread which has ++ // already quit. ++ SignalHookHash::iterator sit = signalHooks.begin(); ++ while (sit != signalHooks.end()) { ++ sit.value().obj->disconnect(this); ++ sit++; ++ } ++ ++ disconnectObjectTree(rootNode); ++ rootNode.children.clear(); // free resources + } + + void QDBusConnectionPrivate::checkThread() +-- +2.7.4 + diff --git a/0537-QtDBus-finish-all-pending-call-with-error-if-disconn.patch b/0537-QtDBus-finish-all-pending-call-with-error-if-disconn.patch new file mode 100644 index 0000000..18fdfad --- /dev/null +++ b/0537-QtDBus-finish-all-pending-call-with-error-if-disconn.patch @@ -0,0 +1,205 @@ +From 9be4ee52021bbb3227611979319ab5e3106063b2 Mon Sep 17 00:00:00 2001 +From: Weng Xuetian +Date: Thu, 3 Mar 2016 21:56:53 -0800 +Subject: [PATCH 537/595] QtDBus: finish all pending call with error if + disconnected + +libdbus will send a local signal if connection gets disconnected. When +this happens, end all pending calls with QDBusError::Disconnected. + +Task-number: QTBUG-51649 +Change-Id: I5c7d2a468bb5da746d0c0e53e458c1e376f186a9 +Reviewed-by: Thiago Macieira +--- + src/dbus/dbus_minimal_p.h | 2 ++ + src/dbus/qdbusconnection_p.h | 3 ++ + src/dbus/qdbusintegrator.cpp | 41 ++++++++++++++++++---- + src/dbus/qdbusutil_p.h | 2 ++ + .../dbus/qdbusconnection/tst_qdbusconnection.cpp | 21 +++++++++++ + .../dbus/qdbusconnection/tst_qdbusconnection.h | 1 + + 6 files changed, 64 insertions(+), 6 deletions(-) + +diff --git a/src/dbus/dbus_minimal_p.h b/src/dbus/dbus_minimal_p.h +index f0a2954..8f25b24 100644 +--- a/src/dbus/dbus_minimal_p.h ++++ b/src/dbus/dbus_minimal_p.h +@@ -99,9 +99,11 @@ typedef dbus_uint32_t dbus_bool_t; + /* dbus-shared.h */ + #define DBUS_SERVICE_DBUS "org.freedesktop.DBus" + #define DBUS_PATH_DBUS "/org/freedesktop/DBus" ++#define DBUS_PATH_LOCAL "/org/freedesktop/DBus/Local" + #define DBUS_INTERFACE_DBUS "org.freedesktop.DBus" + #define DBUS_INTERFACE_INTROSPECTABLE "org.freedesktop.DBus.Introspectable" + #define DBUS_INTERFACE_PROPERTIES "org.freedesktop.DBus.Properties" ++#define DBUS_INTERFACE_LOCAL "org.freedesktop.DBus.Local" + + #define DBUS_NAME_FLAG_ALLOW_REPLACEMENT 0x1 /**< Allow another service to become the primary owner if requested */ + #define DBUS_NAME_FLAG_REPLACE_EXISTING 0x2 /**< Request to replace the current primary owner */ +diff --git a/src/dbus/qdbusconnection_p.h b/src/dbus/qdbusconnection_p.h +index 565eb83..b733a68 100644 +--- a/src/dbus/qdbusconnection_p.h ++++ b/src/dbus/qdbusconnection_p.h +@@ -260,6 +260,8 @@ private: + + QString getNameOwnerNoCache(const QString &service); + ++ void watchForDBusDisconnection(); ++ + void _q_newConnection(QDBusConnectionPrivate *newConnection); + + protected: +@@ -279,6 +281,7 @@ private slots: + void serviceOwnerChangedNoLock(const QString &name, const QString &oldOwner, const QString &newOwner); + void registerServiceNoLock(const QString &serviceName); + void unregisterServiceNoLock(const QString &serviceName); ++ void handleDBusDisconnection(); + + signals: + void dispatchStatusChanged(); +diff --git a/src/dbus/qdbusintegrator.cpp b/src/dbus/qdbusintegrator.cpp +index 3be775d..d0468f4 100644 +--- a/src/dbus/qdbusintegrator.cpp ++++ b/src/dbus/qdbusintegrator.cpp +@@ -1121,6 +1121,12 @@ void QDBusConnectionPrivate::closeConnection() + rootNode.children.clear(); // free resources + } + ++void QDBusConnectionPrivate::handleDBusDisconnection() ++{ ++ while (!pendingCalls.isEmpty()) ++ processFinishedCall(pendingCalls.first()); ++} ++ + void QDBusConnectionPrivate::checkThread() + { + Q_ASSERT(thread() == QDBusConnectionManager::instance()); +@@ -1646,6 +1652,19 @@ void QDBusConnectionPrivate::handleSignal(const QDBusMessage& msg) + handleSignal(key, msg); // third try + } + ++void QDBusConnectionPrivate::watchForDBusDisconnection() ++{ ++ SignalHook hook; ++ // Initialize the hook for Disconnected signal ++ hook.service.clear(); // org.freedesktop.DBus.Local.Disconnected uses empty service name ++ hook.path = QDBusUtil::dbusPathLocal(); ++ hook.obj = this; ++ hook.params << QMetaType::Void; ++ hook.midx = staticMetaObject.indexOfSlot("handleDBusDisconnection()"); ++ Q_ASSERT(hook.midx != -1); ++ signalHooks.insert(QLatin1String("Disconnected:" DBUS_INTERFACE_LOCAL), hook); ++} ++ + void QDBusConnectionPrivate::setServer(QDBusServer *object, DBusServer *s, const QDBusErrorInternal &error) + { + mode = ServerMode; +@@ -1711,6 +1730,8 @@ void QDBusConnectionPrivate::setPeer(DBusConnection *c, const QDBusErrorInternal + qDBusSignalFilter, + this, 0); + ++ watchForDBusDisconnection(); ++ + QMetaObject::invokeMethod(this, "doDispatch", Qt::QueuedConnection); + } + +@@ -1787,6 +1808,8 @@ void QDBusConnectionPrivate::setConnection(DBusConnection *dbc, const QDBusError + Q_ASSERT(hook.midx != -1); + signalHooks.insert(QLatin1String("NameOwnerChanged:" DBUS_INTERFACE_DBUS), hook); + ++ watchForDBusDisconnection(); ++ + qDBusDebug() << this << ": connected successfully"; + + // schedule a dispatch: +@@ -1813,10 +1836,16 @@ void QDBusConnectionPrivate::processFinishedCall(QDBusPendingCallPrivate *call) + + QDBusMessage &msg = call->replyMessage; + if (call->pending) { +- // decode the message +- DBusMessage *reply = q_dbus_pending_call_steal_reply(call->pending); +- msg = QDBusMessagePrivate::fromDBusMessage(reply, connection->capabilities); +- q_dbus_message_unref(reply); ++ // when processFinishedCall is called and pending call is not completed, ++ // it means we received disconnected signal from libdbus ++ if (q_dbus_pending_call_get_completed(call->pending)) { ++ // decode the message ++ DBusMessage *reply = q_dbus_pending_call_steal_reply(call->pending); ++ msg = QDBusMessagePrivate::fromDBusMessage(reply, connection->capabilities); ++ q_dbus_message_unref(reply); ++ } else { ++ msg = QDBusMessage::createError(QDBusError::Disconnected, QDBusUtil::disconnectedErrorMessage()); ++ } + } + qDBusDebug() << connection << "got message reply:" << msg; + +@@ -2116,8 +2145,8 @@ void QDBusConnectionPrivate::sendInternal(QDBusPendingCallPrivate *pcall, void * + pcall->pending = pending; + q_dbus_pending_call_set_notify(pending, qDBusResultReceived, pcall, 0); + +- // DBus won't notify us when a peer disconnects so we need to track these ourselves +- if (mode == QDBusConnectionPrivate::PeerMode) ++ // DBus won't notify us when a peer disconnects or server terminates so we need to track these ourselves ++ if (mode == QDBusConnectionPrivate::PeerMode || mode == QDBusConnectionPrivate::ClientMode) + pendingCalls.append(pcall); + + return; +diff --git a/src/dbus/qdbusutil_p.h b/src/dbus/qdbusutil_p.h +index 8f5ae92..f4ab9b9 100644 +--- a/src/dbus/qdbusutil_p.h ++++ b/src/dbus/qdbusutil_p.h +@@ -155,6 +155,8 @@ namespace QDBusUtil + { return QStringLiteral(DBUS_SERVICE_DBUS); } + inline QString dbusPath() + { return QStringLiteral(DBUS_PATH_DBUS); } ++ inline QString dbusPathLocal() ++ { return QStringLiteral(DBUS_PATH_LOCAL); } + inline QString dbusInterface() + { + // it's the same string, but just be sure +diff --git a/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.cpp b/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.cpp +index e91f87d..f378091 100644 +--- a/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.cpp ++++ b/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.cpp +@@ -1218,6 +1218,27 @@ void tst_QDBusConnection::callVirtualObjectLocal() + QCOMPARE(obj.replyArguments, subPathReply.arguments()); + } + ++void tst_QDBusConnection::pendingCallWhenDisconnected() ++{ ++ if (!QCoreApplication::instance()) ++ QSKIP("Test requires a QCoreApplication"); ++ ++ QDBusServer *server = new QDBusServer; ++ QDBusConnection con = QDBusConnection::connectToPeer(server->address(), "disconnect"); ++ QTestEventLoop::instance().enterLoop(2); ++ QVERIFY(con.isConnected()); ++ QDBusMessage message = QDBusMessage::createMethodCall("", "/", QString(), "method"); ++ QDBusPendingCall reply = con.asyncCall(message); ++ ++ delete server; ++ ++ QTestEventLoop::instance().enterLoop(2); ++ QVERIFY(!con.isConnected()); ++ QVERIFY(reply.isFinished()); ++ QVERIFY(reply.isError()); ++ QVERIFY(reply.error().type() == QDBusError::Disconnected); ++} ++ + QString MyObject::path; + QString MyObjectWithoutInterface::path; + QString MyObjectWithoutInterface::interface; +diff --git a/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.h b/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.h +index a53ba32..720e484 100644 +--- a/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.h ++++ b/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.h +@@ -121,6 +121,7 @@ private slots: + void registerVirtualObject(); + void callVirtualObject(); + void callVirtualObjectLocal(); ++ void pendingCallWhenDisconnected(); + + public: + QString serviceName() const { return "org.qtproject.Qt.Autotests.QDBusConnection"; } +-- +2.7.4 + diff --git a/QTBUG-51648-QtDBus-clean-up-signal-hooks-and-object-tree-in-clos.patch b/QTBUG-51648-QtDBus-clean-up-signal-hooks-and-object-tree-in-clos.patch deleted file mode 100644 index 26c15d0..0000000 --- a/QTBUG-51648-QtDBus-clean-up-signal-hooks-and-object-tree-in-clos.patch +++ /dev/null @@ -1,88 +0,0 @@ -From b024fbe83863fc57364a52c717d5b43d654bdb5d Mon Sep 17 00:00:00 2001 -From: Weng Xuetian -Date: Sat, 5 Mar 2016 12:23:21 -0800 -Subject: [PATCH] QtDBus: clean up signal hooks and object tree in - closeConnection - -If a QObject is added or passed as receiver to QDBusConnection::connect() -and it is managed by Q_GLOBAL_STATIC or similar mechanism, it is -possible that when that its destructor is called after the dbus daemon -thread ends. In that case, QObject::destroyed connected via -Qt::BlockingQueuedConnection to QDBusConnectionPrivate will cause dead -lock since the thread is no longer processing events. - -Task-number: QTBUG-51648 -Change-Id: I1a1810a6d6d0234af0269d5f3fc1f54101bf1547 ---- - src/dbus/qdbusconnection_p.h | 1 + - src/dbus/qdbusintegrator.cpp | 28 +++++++++++++++++++++++++++- - 2 files changed, 28 insertions(+), 1 deletion(-) - -diff --git a/src/dbus/qdbusconnection_p.h b/src/dbus/qdbusconnection_p.h -index c77daf7..565eb83 100644 ---- a/src/dbus/qdbusconnection_p.h -+++ b/src/dbus/qdbusconnection_p.h -@@ -254,6 +254,7 @@ private: - const QVector &metaTypes, int slotIdx); - - SignalHookHash::Iterator removeSignalHookNoLock(SignalHookHash::Iterator it); -+ void disconnectObjectTree(ObjectTreeNode &node); - - bool isServiceRegisteredByThread(const QString &serviceName); - -diff --git a/src/dbus/qdbusintegrator.cpp b/src/dbus/qdbusintegrator.cpp -index cd44861..a3cd47b 100644 ---- a/src/dbus/qdbusintegrator.cpp -+++ b/src/dbus/qdbusintegrator.cpp -@@ -1030,7 +1030,6 @@ QDBusConnectionPrivate::~QDBusConnectionPrivate() - qPrintable(name)); - - closeConnection(); -- rootNode.children.clear(); // free resources - qDeleteAll(cachedMetaObjects); - - if (mode == ClientMode || mode == PeerMode) { -@@ -1052,6 +1051,20 @@ QDBusConnectionPrivate::~QDBusConnectionPrivate() - } - } - -+void QDBusConnectionPrivate::disconnectObjectTree(QDBusConnectionPrivate::ObjectTreeNode &haystack) -+{ -+ QDBusConnectionPrivate::ObjectTreeNode::DataList::Iterator it = haystack.children.begin(); -+ -+ while (it != haystack.children.end()) { -+ disconnectObjectTree(*it); -+ it++; -+ } -+ -+ if (haystack.obj) { -+ haystack.obj->disconnect(this); -+ } -+} -+ - void QDBusConnectionPrivate::closeConnection() - { - QDBusWriteLocker locker(CloseConnectionAction, this); -@@ -1075,6 +1088,19 @@ void QDBusConnectionPrivate::closeConnection() - } - - qDeleteAll(pendingCalls); -+ -+ // clean up all signal hook and object tree, to avoid QObject::destroyed -+ // being activated to dbus daemon thread which already quits. -+ // dbus connection is already closed, so there is nothing we could do be clean -+ // up everything here. -+ SignalHookHash::iterator sit = signalHooks.begin(); -+ while (sit != signalHooks.end()) { -+ sit.value().obj->disconnect(this); -+ sit++; -+ } -+ -+ disconnectObjectTree(rootNode); -+ rootNode.children.clear(); // free resources - } - - void QDBusConnectionPrivate::checkThread() --- -2.5.0 - diff --git a/QTBUG-51649-QtDBus-finish-all-pending-call-with-error-if-disconn.patch b/QTBUG-51649-QtDBus-finish-all-pending-call-with-error-if-disconn.patch deleted file mode 100644 index bf13f57..0000000 --- a/QTBUG-51649-QtDBus-finish-all-pending-call-with-error-if-disconn.patch +++ /dev/null @@ -1,156 +0,0 @@ -From 136eeec876ed5b995e7c27bcdcefe0199f5f183d Mon Sep 17 00:00:00 2001 -From: Weng Xuetian -Date: Thu, 3 Mar 2016 21:56:53 -0800 -Subject: [PATCH] QtDBus: finish all pending call with error if disconnected - -libdbus will send a local signal if connection gets disconnected. When -this happens, end all pending calls with QDBusError::Disconnected. - -Task-number: QTBUG-51649 -Change-Id: I5c7d2a468bb5da746d0c0e53e458c1e376f186a9 ---- - src/dbus/qdbusintegrator.cpp | 26 +++++++++++++++++----- - src/dbus/qdbusutil_p.h | 6 +++++ - .../dbus/qdbusconnection/tst_qdbusconnection.cpp | 22 ++++++++++++++++++ - .../dbus/qdbusconnection/tst_qdbusconnection.h | 1 + - 4 files changed, 49 insertions(+), 6 deletions(-) - -diff --git a/src/dbus/qdbusintegrator.cpp b/src/dbus/qdbusintegrator.cpp -index cd44861..320419f 100644 ---- a/src/dbus/qdbusintegrator.cpp -+++ b/src/dbus/qdbusintegrator.cpp -@@ -519,6 +519,14 @@ bool QDBusConnectionPrivate::handleMessage(const QDBusMessage &amsg) - switch (amsg.type()) { - case QDBusMessage::SignalMessage: - handleSignal(amsg); -+ // Check local disconnected signal from libdbus -+ if (amsg.interface() == QDBusUtil::dbusInterfaceLocal() -+ && amsg.path() == QDBusUtil::dbusPathLocal() -+ && amsg.member() == QDBusUtil::disconnected() -+ && !QDBusMessagePrivate::isLocal(amsg)) { -+ while (!pendingCalls.isEmpty()) -+ processFinishedCall(pendingCalls.first()); -+ } - // if there are any other filters in this DBusConnection, - // let them see the signal too - return false; -@@ -1767,10 +1775,16 @@ void QDBusConnectionPrivate::processFinishedCall(QDBusPendingCallPrivate *call) - - QDBusMessage &msg = call->replyMessage; - if (call->pending) { -- // decode the message -- DBusMessage *reply = q_dbus_pending_call_steal_reply(call->pending); -- msg = QDBusMessagePrivate::fromDBusMessage(reply, connection->capabilities); -- q_dbus_message_unref(reply); -+ // when processFinishedCall is called and pending call is not completed, -+ // it means we received disconnected signal from libdbus -+ if (q_dbus_pending_call_get_completed(call->pending)) { -+ // decode the message -+ DBusMessage *reply = q_dbus_pending_call_steal_reply(call->pending); -+ msg = QDBusMessagePrivate::fromDBusMessage(reply, connection->capabilities); -+ q_dbus_message_unref(reply); -+ } else { -+ msg = QDBusMessage::createError(QDBusError::Disconnected, QDBusUtil::disconnectedErrorMessage()); -+ } - } - qDBusDebug() << connection << "got message reply:" << msg; - -@@ -2070,8 +2084,8 @@ void QDBusConnectionPrivate::sendInternal(QDBusPendingCallPrivate *pcall, void * - pcall->pending = pending; - q_dbus_pending_call_set_notify(pending, qDBusResultReceived, pcall, 0); - -- // DBus won't notify us when a peer disconnects so we need to track these ourselves -- if (mode == QDBusConnectionPrivate::PeerMode) -+ // DBus won't notify us when a peer disconnects or server terminates so we need to track these ourselves -+ if (mode == QDBusConnectionPrivate::PeerMode || mode == QDBusConnectionPrivate::ClientMode) - pendingCalls.append(pcall); - - return; -diff --git a/src/dbus/qdbusutil_p.h b/src/dbus/qdbusutil_p.h -index 8f5ae92..ca70ff9 100644 ---- a/src/dbus/qdbusutil_p.h -+++ b/src/dbus/qdbusutil_p.h -@@ -155,6 +155,8 @@ namespace QDBusUtil - { return QStringLiteral(DBUS_SERVICE_DBUS); } - inline QString dbusPath() - { return QStringLiteral(DBUS_PATH_DBUS); } -+ inline QString dbusPathLocal() -+ { return QStringLiteral(DBUS_PATH_LOCAL); } - inline QString dbusInterface() - { - // it's the same string, but just be sure -@@ -165,8 +167,12 @@ namespace QDBusUtil - { return QStringLiteral(DBUS_INTERFACE_PROPERTIES); } - inline QString dbusInterfaceIntrospectable() - { return QStringLiteral(DBUS_INTERFACE_INTROSPECTABLE); } -+ inline QString dbusInterfaceLocal() -+ { return QStringLiteral(DBUS_INTERFACE_LOCAL); } - inline QString nameOwnerChanged() - { return QStringLiteral("NameOwnerChanged"); } -+ inline QString disconnected() -+ { return QStringLiteral("Disconnected"); } - inline QString disconnectedErrorMessage() - { return QStringLiteral("Not connected to D-Bus server"); } - } -diff --git a/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.cpp b/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.cpp -index e91f87d..6c7e6b1 100644 ---- a/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.cpp -+++ b/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.cpp -@@ -1218,6 +1218,28 @@ void tst_QDBusConnection::callVirtualObjectLocal() - QCOMPARE(obj.replyArguments, subPathReply.arguments()); - } - -+void tst_QDBusConnection::pendingCallWhenDisconnected() -+{ -+ QDBusServer *server = new QDBusServer; -+ QDBusConnection con = QDBusConnection::connectToPeer(server->address(), "disconnect"); -+ QTestEventLoop::instance().enterLoop(2); -+ QVERIFY(!QTestEventLoop::instance().timeout()); -+ QVERIFY(con.isConnected()); -+ -+ delete server; -+ -+ // Make sure we call the method before we know it is disconnected. -+ QVERIFY(con.isConnected()); -+ QDBusMessage message = QDBusMessage::createMethodCall("", "/", QString(), "method"); -+ QDBusPendingCall reply = con.asyncCall(message); -+ -+ QTestEventLoop::instance().enterLoop(2); -+ QVERIFY(!con.isConnected()); -+ QVERIFY(reply.isFinished()); -+ QVERIFY(reply.isError()); -+ QVERIFY(reply.error().type() == QDBusError::Disconnected); -+} -+ - QString MyObject::path; - QString MyObjectWithoutInterface::path; - QString MyObjectWithoutInterface::interface; -diff --git a/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.h b/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.h -index a53ba32..720e484 100644 ---- a/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.h -+++ b/tests/auto/dbus/qdbusconnection/tst_qdbusconnection.h -@@ -121,6 +121,7 @@ private slots: - void registerVirtualObject(); - void callVirtualObject(); - void callVirtualObjectLocal(); -+ void pendingCallWhenDisconnected(); - - public: - QString serviceName() const { return "org.qtproject.Qt.Autotests.QDBusConnection"; } --- -2.5.0 - -diff -up qtbase-opensource-src-5.6.0-rc/src/dbus/dbus_minimal_p.h.QTBUG-51649 qtbase-opensource-src-5.6.0-rc/src/dbus/dbus_minimal_p.h ---- qtbase-opensource-src-5.6.0-rc/src/dbus/dbus_minimal_p.h.QTBUG-51649 2016-02-18 01:24:38.000000000 -0600 -+++ qtbase-opensource-src-5.6.0-rc/src/dbus/dbus_minimal_p.h 2016-03-11 11:40:11.176244645 -0600 -@@ -99,8 +99,10 @@ typedef dbus_uint32_t dbus_bool_t; - /* dbus-shared.h */ - #define DBUS_SERVICE_DBUS "org.freedesktop.DBus" - #define DBUS_PATH_DBUS "/org/freedesktop/DBus" -+#define DBUS_PATH_LOCAL "/org/freedesktop/DBus/Local" - #define DBUS_INTERFACE_DBUS "org.freedesktop.DBus" - #define DBUS_INTERFACE_INTROSPECTABLE "org.freedesktop.DBus.Introspectable" -+#define DBUS_INTERFACE_LOCAL "org.freedesktop.DBus.Local" - #define DBUS_INTERFACE_PROPERTIES "org.freedesktop.DBus.Properties" - - #define DBUS_NAME_FLAG_ALLOW_REPLACEMENT 0x1 /**< Allow another service to become the primary owner if requested */ diff --git a/qt5-qtbase.spec b/qt5-qtbase.spec index 7eaf4d9..a5e7525 100644 --- a/qt5-qtbase.spec +++ b/qt5-qtbase.spec @@ -49,11 +49,10 @@ %if ! 0%{?bootstrap} %ifarch %{arm} %{ix86} x86_64 %{power64} s390 s390x aarch64 %global docs 1 -%global tests 1 -%endif %endif - %global examples 1 +%global tests 1 +%endif #define prerelease rc @@ -97,12 +96,6 @@ Patch52: qtbase-opensource-src-5.6.0-moc_WORDSIZE.patch # arm patch Patch54: qtbase-opensource-src-5.6.0-arm.patch -# https://codereview.qt-project.org/#/c/151496/ -Patch55: QTBUG-51648-QtDBus-clean-up-signal-hooks-and-object-tree-in-clos.patch - -# https://codereview.qt-project.org/#/c/151340/ -Patch56: QTBUG-51649-QtDBus-finish-all-pending-call-with-error-if-disconn.patch - # recently passed code review, not integrated yet # https://codereview.qt-project.org/126102/ Patch60: moc-get-the-system-defines-from-the-compiler-itself.patch @@ -118,6 +111,8 @@ Patch278: 0178-qt_common.prf-when-looking-for-GCC-4.6-match-GCC-6-t.patch Patch301: 0201-alsatest-Fix-the-check-to-treat-alsalib-1.1.x-as-cor.patch Patch321: 0221-QObject-fix-GCC-6-warning-about-qt_static_metacall-s.patch Patch393: 0293-Fix-QtDBus-deadlock-inside-kded-kiod.patch +Patch515: 0415-QtDBus-clean-up-signal-hooks-and-object-tree-in-clos.patch +Patch637: 0537-QtDBus-finish-all-pending-call-with-error-if-disconn.patch # macros, be mindful to keep sync'd with macros.qt5 Source10: macros.qt5 @@ -171,6 +166,7 @@ BuildRequires: pkgconfig(libproxy-1.0) BuildRequires: pkgconfig(ice) pkgconfig(sm) BuildRequires: pkgconfig(libpng) BuildRequires: pkgconfig(libudev) +%global openssl -openssl-linked BuildRequires: pkgconfig(openssl) BuildRequires: pkgconfig(libpulse) pkgconfig(libpulse-mainloop-glib) %if 0%{?fedora} @@ -367,9 +363,6 @@ RPM macros for building Qt5 packages. %patch52 -p1 -b .moc_WORDSIZE %patch54 -p1 -b .arm -%patch55 -p1 -b .QTBUG-51648 -## FTBFS, omit for now -%patch56 -p1 -b .QTBUG-51649 %patch60 -p1 -b .moc_system_defines %patch158 -p1 -b .0058 @@ -380,6 +373,8 @@ RPM macros for building Qt5 packages. %patch301 -p1 -b .0201 %patch321 -p1 -b .0221 %patch393 -p1 -b .0293 +%patch515 -p1 -b .0415 +%patch637 -p1 -b .0637 %define platform linux-g++ @@ -467,10 +462,10 @@ pushd %{_target_platform} -iconv \ -icu \ %{?journald} \ - -openssl-linked \ + %{?openssl} \ -optimized-qmake \ %{!?examples:-nomake examples} \ - -nomake tests \ + %{!?tests:-nomake tests} \ -no-pch \ -no-rpath \ -no-separate-debug-info \ @@ -615,11 +610,15 @@ install -p -m755 -D %{SOURCE6} %{buildroot}%{_sysconfdir}/X11/xinit/xinitrc.d/10 %check %if 0%{?tests} +## see tests/README for expected environment (running a plasma session essentially) +## we are not quite there yet export CTEST_OUTPUT_ON_FAILURE=1 export PATH=%{buildroot}%{_qt5_bindir}:$PATH export LD_LIBRARY_PATH=%{buildroot}%{_qt5_libdir} -make sub-tests %{?_smp_mflags} -C %{_target_platform} -xvfb-run -a \ +# dbus tests error out when building if session bus is not available +dbus-launch --exit-with-session \ +make sub-tests %{?_smp_mflags} -k -C %{_target_platform} ||: +xvfb-run -a --server-args="-screen 0 1280x1024x32" \ dbus-launch --exit-with-session \ time \ make check -k -C %{_target_platform}/tests ||: @@ -973,6 +972,8 @@ fi * Thu May 05 2016 Rex Dieter - 5.6.0-17 - support out-of-tree build - better %%check +- pull in final/upstream fixes for QTBUG-51648,QTBUG-51649 +- disable examples/tests in bootstrap mode * Sat Apr 30 2016 Rex Dieter - 5.6.0-16 - own %%{_qt5_plugindir}/egldeviceintegrations