aboutsummaryrefslogtreecommitdiffstats
path: root/tests
diff options
context:
space:
mode:
authorAndrei Golubev <andrei.golubev@qt.io>2022-07-01 13:51:12 +0200
committerAndrei Golubev <andrei.golubev@qt.io>2022-07-29 15:22:45 +0200
commit91ce865050b9e017e63ae5b0c54e2d385705d155 (patch)
tree466ac2b33f5d4f5cb78c94d31713eccaf8881dbb /tests
parentddda42d90e09a5e984f3f78acf4be637ef45fde1 (diff)
qqmltypecompiler: align runtime function table order to qmlcachegen
When we write runtime functions to compilation unit at run time, the order of the functions in the unit (often) differs from the order of functions in the unit produced ahead of time by qmlcachegen and friends. Additionally, the order also differs from what qmltc expects (and qmlcompiler library in general) Fix the order by simplifying the procedure of JS code generation when we create the compilation unit at run time: new logic just goes over the objects in the document linearly, instead of relying on bindings (which are known to be out of order w.r.t. AST) Change-Id: I4070b9d061f03c4c76d03120654ad3f30725493a Reviewed-by: Ulf Hermann <ulf.hermann@qt.io> (cherry picked from commit 8d0adee3b3317f1fab03742bdf0f7cdbe57df914) Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Diffstat (limited to 'tests')
-rw-r--r--tests/auto/qml/qmltc/tst_qmltc.cpp10
-rw-r--r--tests/auto/qml/qqmljsscope/data/compilationUnitsCompatibility.qml6
-rw-r--r--tests/auto/qml/qqmljsscope/tst_qqmljsscope.cpp53
3 files changed, 59 insertions, 10 deletions
diff --git a/tests/auto/qml/qmltc/tst_qmltc.cpp b/tests/auto/qml/qmltc/tst_qmltc.cpp
index af0ba4878e..dfad4c15eb 100644
--- a/tests/auto/qml/qmltc/tst_qmltc.cpp
+++ b/tests/auto/qml/qmltc/tst_qmltc.cpp
@@ -1950,19 +1950,9 @@ void tst_qmltc::listView()
QCOMPARE(model->count(), 0);
created.appendDigit("5");
- if (isCacheDisabled()) {
- // TODO: doesn't work in no_disk_cache mode because
- // QV4::Lookup::nextIndex values are different. These come from
- // CompiledData::Lookup table of the compilation unit -- why would that
- // change during QQmlTypeCompiler's CU generation?
- QEXPECT_FAIL("", "Doesn't work without qmlcachegen - needs investigation", Continue);
- }
QCOMPARE(model->count(), 1);
created.appendOperator("+");
- if (isCacheDisabled()) { // same as above
- QEXPECT_FAIL("", "Doesn't work without qmlcachegen - needs investigation", Continue);
- }
QCOMPARE(model->count(), 2);
// TODO: add more testing (e.g. check that values are actually recorded)
diff --git a/tests/auto/qml/qqmljsscope/data/compilationUnitsCompatibility.qml b/tests/auto/qml/qqmljsscope/data/compilationUnitsCompatibility.qml
new file mode 100644
index 0000000000..bcc49537bb
--- /dev/null
+++ b/tests/auto/qml/qqmljsscope/data/compilationUnitsCompatibility.qml
@@ -0,0 +1,6 @@
+import QtQuick
+
+Text {
+ anchors.bottomMargin: Math.max(32, 31) + 10 // == 42
+ font.letterSpacing: Math.max(2, 3)
+}
diff --git a/tests/auto/qml/qqmljsscope/tst_qqmljsscope.cpp b/tests/auto/qml/qqmljsscope/tst_qqmljsscope.cpp
index 6bbb221396..a5efd3147e 100644
--- a/tests/auto/qml/qqmljsscope/tst_qqmljsscope.cpp
+++ b/tests/auto/qml/qqmljsscope/tst_qqmljsscope.cpp
@@ -23,6 +23,7 @@
#include <private/qqmljstyperesolver_p.h>
#include <QtQml/private/qqmljslexer_p.h>
#include <QtQml/private/qqmljsparser_p.h>
+#include <private/qqmlcomponent_p.h>
using namespace Qt::StringLiterals;
@@ -107,6 +108,7 @@ private Q_SLOTS:
void emptyBlockBinding();
void qualifiedName();
void resolvedNonUniqueScopes();
+ void compilationUnitsAreCompatible();
public:
tst_qqmljsscope()
@@ -764,5 +766,56 @@ void tst_qqmljsscope::resolvedNonUniqueScopes()
}
}
+static void
+getRuntimeInfoFromCompilationUnit(const QV4::CompiledData::Unit *unit,
+ QList<const QV4::CompiledData::Function *> &runtimeFunctions)
+{
+ QVERIFY(unit);
+ for (uint i = 0; i < unit->functionTableSize; ++i) {
+ const QV4::CompiledData::Function *function = unit->functionAt(i);
+ QVERIFY(function);
+ runtimeFunctions << function;
+ }
+}
+
+// Note: this test is here because we never explicitly test qCompileQmlFile()
+void tst_qqmljsscope::compilationUnitsAreCompatible()
+{
+ const QString url = u"compilationUnitsCompatibility.qml"_s;
+ QList<const QV4::CompiledData::Function *> componentFunctions;
+ QList<const QV4::CompiledData::Function *> cachegenFunctions;
+
+ QQmlEngine engine;
+ QQmlComponent component(&engine);
+ component.loadUrl(testFileUrl(url));
+ QVERIFY2(component.isReady(), qPrintable(component.errorString()));
+ QScopedPointer<QObject> root(component.create());
+ QVERIFY2(root, qPrintable(component.errorString()));
+ QQmlComponentPrivate *cPriv = QQmlComponentPrivate::get(&component);
+ QVERIFY(cPriv);
+ auto unit = cPriv->compilationUnit;
+ QVERIFY(unit);
+ QVERIFY(unit->unitData());
+ getRuntimeInfoFromCompilationUnit(unit->unitData(), componentFunctions);
+
+ if (QTest::currentTestFailed())
+ return;
+
+ QmlIR::Document document(false); // we need QmlIR information here
+ QVERIFY(run(url, &document));
+ QVERIFY(document.javaScriptCompilationUnit.unitData());
+ getRuntimeInfoFromCompilationUnit(document.javaScriptCompilationUnit.unitData(),
+ cachegenFunctions);
+ if (QTest::currentTestFailed())
+ return;
+
+ QCOMPARE(cachegenFunctions.size(), componentFunctions.size());
+ // name index should be fairly unique to distinguish different functions
+ // within a document. their order must be the same for both qmlcachegen and
+ // qqmltypecompiler (runtime)
+ for (qsizetype i = 0; i < cachegenFunctions.size(); ++i)
+ QCOMPARE(uint(cachegenFunctions[i]->nameIndex), uint(componentFunctions[i]->nameIndex));
+}
+
QTEST_MAIN(tst_qqmljsscope)
#include "tst_qqmljsscope.moc"