From e163c4943593aec7f69c2bbaf49a0020d806d23d Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Tue, 9 Aug 2022 11:13:05 -0700 Subject: [PATCH] qdbusxml2cpp: remove the old "In"-for-signal compatibility code This led to an infinite recursion in case the annotation was completely missing. Instead of trying to fix that, I'm simply implementing the "### Qt6" request from c62f71722639c39f210ddbec0c4d832521b3f187 . [ChangeLog][qdbusxml2cpp] Removed the old compatibility code that accepted "In" annotations for signal argument names, introduced in Qt 5.8. Pick-to: 6.4 Fixes: QTBUG-104722 Change-Id: Ie4bb662dcb274440ab8bfffd1709bfc3daf0846d Reviewed-by: David Faure --- src/tools/qdbusxml2cpp/qdbusxml2cpp.cpp | 24 ++-- .../org.qtproject.QtDBus.Pinger.xml | 2 +- .../tools/qdbusxml2cpp/tst_qdbusxml2cpp.cpp | 134 ++++++++++++++---- 3 files changed, 113 insertions(+), 47 deletions(-) diff --git a/src/tools/qdbusxml2cpp/qdbusxml2cpp.cpp b/src/tools/qdbusxml2cpp/qdbusxml2cpp.cpp index ccfd3f3990..c79baf66d6 100644 --- a/src/tools/qdbusxml2cpp/qdbusxml2cpp.cpp +++ b/src/tools/qdbusxml2cpp/qdbusxml2cpp.cpp @@ -175,12 +175,9 @@ static QString classNameForInterface(const QString &interface, ClassType classTy return retval; } -// ### Qt6 Remove the two isSignal ifs -// They are only here because before signal arguments where previously searched as "In" so to maintain compatibility -// we first search for "Out" and if not found we search for "In" static QByteArray qtTypeName(const QString &where, const QString &signature, const QDBusIntrospection::Annotations &annotations, qsizetype paramId = -1, - const char *direction = "Out", bool isSignal = false) + const char *direction = "Out") { int type = QDBusMetaType::signatureToMetaType(signature.toLatin1()).id(); if (type == QMetaType::UnknownType) { @@ -197,17 +194,12 @@ static QByteArray qtTypeName(const QString &where, const QString &signature, qttype = annotations.value(oldAnnotationName); if (qttype.isEmpty()) { - if (!isSignal || qstrcmp(direction, "Out") == 0) { - fprintf(stderr, "%s: Got unknown type `%s' processing '%s'\n", - PROGRAMNAME, qPrintable(signature), qPrintable(inputFile)); - fprintf(stderr, - "You should add \"/> to the XML " - "description for '%s'\n", - qPrintable(annotationName), qPrintable(where)); - } - - if (isSignal) - return qtTypeName(where, signature, annotations, paramId, "In", isSignal); + fprintf(stderr, "%s: Got unknown type `%s' processing '%s'\n", + PROGRAMNAME, qPrintable(signature), qPrintable(inputFile)); + fprintf(stderr, + "You should add \"/> to the XML " + "description for '%s'\n", + qPrintable(annotationName), qPrintable(where)); exit(1); } @@ -318,7 +310,7 @@ static void writeSignalArgList(QTextStream &ts, const QStringList &argNames, for (qsizetype i = 0; i < outputArgs.size(); ++i) { const QDBusIntrospection::Argument &arg = outputArgs.at(i); QString type = constRefArg( - qtTypeName(arg.name, arg.type, annotations, i, "Out", true /* isSignal */)); + qtTypeName(arg.name, arg.type, annotations, i, "Out")); if (!first) ts << ", "; diff --git a/tests/auto/dbus/qdbusabstractinterface/org.qtproject.QtDBus.Pinger.xml b/tests/auto/dbus/qdbusabstractinterface/org.qtproject.QtDBus.Pinger.xml index ad61351cb2..70d5a4e9c3 100644 --- a/tests/auto/dbus/qdbusabstractinterface/org.qtproject.QtDBus.Pinger.xml +++ b/tests/auto/dbus/qdbusabstractinterface/org.qtproject.QtDBus.Pinger.xml @@ -12,7 +12,7 @@ - + diff --git a/tests/auto/tools/qdbusxml2cpp/tst_qdbusxml2cpp.cpp b/tests/auto/tools/qdbusxml2cpp/tst_qdbusxml2cpp.cpp index db0c8af0fd..918fa1d711 100644 --- a/tests/auto/tools/qdbusxml2cpp/tst_qdbusxml2cpp.cpp +++ b/tests/auto/tools/qdbusxml2cpp/tst_qdbusxml2cpp.cpp @@ -21,6 +21,8 @@ private slots: void process(); void includeStyle_data(); void includeStyle(); + void missingAnnotation_data(); + void missingAnnotation(); }; struct BasicTypeList { @@ -57,6 +59,44 @@ static QString stripHeader(QString output) return output.remove(header); } +static void runTool(QProcess &process, const QByteArray &data) +{ + // test both interface and adaptor generation + QFETCH_GLOBAL(QString, commandLineArg); + + // Run the tool + const QString binpath = QLibraryInfo::path(QLibraryInfo::BinariesPath); + QStringList arguments = { commandLineArg, "-", "-N" }; + process.setArguments(arguments); + process.setProgram(binpath + QLatin1String("/qdbusxml2cpp")); + process.start(QIODevice::Text | QIODevice::ReadWrite); + QVERIFY2(process.waitForStarted(), qPrintable(process.errorString())); + + // feed it our XML data + static const char xmlHeader[] = + "\n" + DBUS_INTROSPECT_1_0_XML_DOCTYPE_DECL_NODE // \n is included + "\n" + " \n" + " \n"; + static const char xmlFooter[] = "\n" + " \n" + " \n" + "\n"; + + process.write(xmlHeader, sizeof(xmlHeader) - 1); + process.write(data); + process.write(xmlFooter, sizeof(xmlFooter) - 1); + + while (process.bytesToWrite()) + QVERIFY2(process.waitForBytesWritten(), qPrintable(process.errorString())); + // fprintf(stderr, "%s%s%s", xmlHeader, xmlSnippet.toLatin1().constData(), xmlFooter); + + process.closeWriteChannel(); + QVERIFY2(process.waitForFinished(), qPrintable(process.errorString())); + QCOMPARE(process.exitStatus(), QProcess::NormalExit); +} + void tst_qdbusxml2cpp::initTestCase_data() { QTest::addColumn("outputMode"); @@ -181,6 +221,15 @@ void tst_qdbusxml2cpp::process_data() .arg(basicTypeList[i].dbusType) << rx << rx; } + + QRegularExpression rx(R"(Q_SIGNALS:.*\b\Qvoid Signal(const QVariantMap &map);\E)", + QRegularExpression::DotMatchesEverythingOption); + QTest::newRow("signal-complex") + << R"( + + " + )" + << rx << rx; } void tst_qdbusxml2cpp::process() @@ -191,38 +240,10 @@ void tst_qdbusxml2cpp::process() QVERIFY2(interfaceSearch.isValid(), qPrintable(interfaceSearch.errorString())); QVERIFY2(adaptorSearch.isValid(), qPrintable(adaptorSearch.errorString())); - // test both interface and adaptor generation QFETCH_GLOBAL(int, outputMode); - QFETCH_GLOBAL(QString, commandLineArg); - - // Run the tool - const QString binpath = QLibraryInfo::path(QLibraryInfo::BinariesPath); - const QString command = binpath + QLatin1String("/qdbusxml2cpp"); QProcess process; - process.start(command, QStringList() << commandLineArg << "-" << "-N"); - QVERIFY2(process.waitForStarted(), qPrintable(process.errorString())); - - // feed it our XML data - static const char xmlHeader[] = - "\n" - DBUS_INTROSPECT_1_0_XML_DOCTYPE_DECL_NODE // \n is included - "\n" - " \n" - " \n"; - static const char xmlFooter[] = "\n" - " \n" - " \n" - "\n"; - - process.write(xmlHeader, int(sizeof xmlHeader) - 1); - process.write(xmlSnippet.toLatin1()); - process.write(xmlFooter, int(sizeof xmlFooter) - 1); - while (process.bytesToWrite()) - QVERIFY2(process.waitForBytesWritten(), qPrintable(process.errorString())); - // fprintf(stderr, "%s%s%s", xmlHeader, xmlSnippet.toLatin1().constData(), xmlFooter); - - process.closeWriteChannel(); - QVERIFY2(process.waitForFinished(), qPrintable(process.errorString())); + runTool(process, xmlSnippet.toLatin1()); + if (QTest::currentTestFailed()) return; QByteArray errOutput = process.readAllStandardError(); QVERIFY2(errOutput.isEmpty(), errOutput); @@ -284,6 +305,59 @@ void tst_qdbusxml2cpp::includeStyle() QVERIFY(fullOutput.contains(expected)); } +void tst_qdbusxml2cpp::missingAnnotation_data() +{ + QTest::addColumn("xmlSnippet"); + QTest::addColumn("annotationName"); + + QTest::newRow("property") + << R"()" + << "org.qtproject.QtDBus.QtTypeName"; + QTest::newRow("method-in") + << R"( + + )" + << "org.qtproject.QtDBus.QtTypeName.In0"; + QTest::newRow("method-out") + << R"( + + )" + << "org.qtproject.QtDBus.QtTypeName.Out0"; + QTest::newRow("signal") + << R"( + + )" + << "org.qtproject.QtDBus.QtTypeName.Out0"; + QTest::newRow("signal-out") + << R"( + + )" + << "org.qtproject.QtDBus.QtTypeName.Out0"; +} + +void tst_qdbusxml2cpp::missingAnnotation() +{ + QFETCH(QString, xmlSnippet); + QFETCH(QString, annotationName); + + QString type = "(ii)"; + QProcess process; + runTool(process, xmlSnippet.arg(type).toLatin1()); + if (QTest::currentTestFailed()) return; + + // it must have failed + QString errOutput = QString::fromLatin1(process.readAllStandardError().trimmed()); + QCOMPARE(process.exitCode(), 1); + QCOMPARE(process.readAllStandardOutput(), QByteArray()); + QVERIFY(!errOutput.isEmpty()); + + // check it did suggest the right annotation + QString expected = R"(qdbusxml2cpp: Got unknown type `%1' processing '' +You should add to the XML description for 'name')"; + expected = expected.arg(type, annotationName); + QCOMPARE(errOutput, expected); +} + QTEST_MAIN(tst_qdbusxml2cpp) #include "tst_qdbusxml2cpp.moc"