aboutsummaryrefslogtreecommitdiffstats
path: root/tests/auto/qml/qmlcppcodegen
Commit message (Collapse)AuthorAgeFilesLines
* QmlCompiler: Don't read out of bounds when analyzing splice()Ulf Hermann24 hours3-0/+19
| | | | | | | | | | You can call splice with only one argument, after all. Pick-to: 6.10 6.8 6.5 Fixes: QTBUG-142253 Change-Id: I3dec244325fd4d57a045ec024968e26e4f6372db Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io> Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
* Compiler: Stop std::move-ing the changed register in certain casesOlivier De Cannière4 days3-0/+31
| | | | | | | | | | | | | | | | | | | | | | | | | | This patch removes an optimization where we std::move the changed register into its target. A copy is performed instead. This resolves the more urgent issue of miscompilations. QTBUG-141920 has popped up and was either exposed or introduced by b303e0624d2ea2ab1c124961e7510a64d0ca1412. That change performs optimizations that avoid intermediary copies of values between registers. It was found that, in the process, the mapping from RegisterContent to variable name stored in m_resiterVariables was changed. One RegisterContent no longer uniquely maps to a variable name because of the direct moving of values to their destination. The registers alias the same value. This could cause issues and might need to be addressed. The original std::move was only added after 6.5 by 3193911b02424dd0365e03526a4c12ed7888b7ca. Cherry-pick to the later versions. Fixes: QTBUG-141920 Pick-to: 6.10 6.8 Change-Id: Ie6dad1a809ac5ee08de70971ec92d3c97fc50080 Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* CMake: Allow qmlls.build.ini generation to be skippedUlf Hermann5 days1-0/+1
| | | | | | | | | We don't want a qmlls.build.ini to be generated on a module that's intentionally hidden from the outside world. That won't work anyway. Change-Id: I4231361ab4d786d661db19f80b5cf0de84cc0b35 Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io> Reviewed-by: Edward Welbourne <edward.welbourne@qt.io>
* QtQml: Don't mark QJSValues on the AOT stackUlf Hermann7 days3-0/+38
| | | | | | | | | | | | QJSValue and QJSManagedValue hold persistent values which are marked elsewhere. QJSPrimitiveValue doesn't need to be marked at all. Amends commit 2d016a2653c59f10a57dc1903b817f71d16d0622. Pick-to: 6.10 6.8 Fixes: QTBUG-142097 Change-Id: I50d6405a684726a81ceee506b2d4f8b90330fcaf Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QmlCompiler: Fix rejection of dynamic properties in object literalsUlf Hermann2025-11-114-4/+38
| | | | | | | | | | | | | | | | Since we early-return in a number of places, the condition needs to be checked first. Also, remove the dead code that tries to implement dynamic properties in object literals. Amends commits f839171eefbba670536262fa3b847d24bfdc627b and f47df45b4981d2d3eedfdbcf7574a7d2e2625627 which were mistaken in trying to support this case. Pick-to: 6.10 6.8 Fixes: QTBUG-141849 Change-Id: I34a6c47375b9e8fa1320259e3f335d304ce8e589 Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io> Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* QtQml: Fix marking of values on AOT stackUlf Hermann2025-11-054-0/+55
| | | | | | | | | | | | | We need to pop the value that's being processed before we push further values. Amends commit 2d016a2653c59f10a57dc1903b817f71d16d0622. Fixes: QTBUG-141646 Pick-to: 6.10 6.8 Change-Id: I92c69d612891d4360d83348c4df707389dda582a Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io> Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QmlCompiler: Fix side effect detection for callsUlf Hermann2025-10-315-29/+67
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | We cannot pass registers that are potentially affected by side effect as arguments to calls. For this to work, we need to sharpen the side effect detection some more. 1. A conversion is always "var" which can be affected by side effects. However, the actual question is whether one of the conversion origins can be affected by side effects. A conversion of "int" and "undefined", for example, can certainly not be affected. 2. When determining side effects we need to look at the original types, not the adjusted ones. Adjusted types are often "var" because we need to pass a value as "var" to some function. That doesn't mean the value can be affected by side effects, though. 3. When generating the write-back, we should first check if it's necessary at all before looking for side effects. Furthermore, we need to slightly adjust the deltablue benchmark since two values were potentially affected by side effects. The walkStrength may be shadowed by a type with internal structure. Only at the call site of the weaker() and stronger() functions it would then be collapsed into int. However, those function calls might change the original walkStrength, thereby producing a side effect for further calls. We can exclude this effect by collapsing to Number right away using the '+' operator. Finally, we need to make the initialization of the Categorizer benchmark non-Strict. The loop that writes into an array of type unknown until the return statement while calling a function on every iteration is obviously affected by side effects. However, the meat of the benchmark is actually not the initialization. So that should be fine. Pick-to: 6.10 6.8 Fixes: QTBUG-141420 Change-Id: Iad47eddcf0afaa4e502f1d151cf383a6fd23f5ba Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io> Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* Fix configure warningsUlf Hermann2025-10-291-1/+3
| | | | | | | | | | | | * Make nonstandard RESOURCE_PREFIXes explicit * Add TEST_PLUGIN to MockExtensionPlugin * Remove lint target from intentionally hidden module Also remove some useless VERSION statements and an ineffective QTP0001. Change-Id: Iadbacce55810bdbb2cbc6a1c7175303b96e06120 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io> Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
* QtQml: Fix resolution of aliases to local aliasesUlf Hermann2025-10-133-0/+34
| | | | | | | | | | | | | When we find an alias to a local alias, we need to first check if the target alias is already resolved. Otherwise we can't insert the source alias, yet. Amends commit 9e1378260a3f3a6eb4cad8d6ae47bc218e6a2b5f. Pick-to: 6.10 Fixes: QTBUG-141059 Change-Id: If272a746595b39cb2dbc2b8cc0c2f688277cfe59 Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
* QtQml: Reset scope object call lookup if it failsUlf Hermann2025-10-093-0/+65
| | | | | | | | | | | | | In exceptional circumstances the function can turn out to be null. This may happen if the context has already been torn down. We must not try to call it then. Also, fix the error message to include the actual object. Pick-to: 6.10 Fixes: QTBUG-140465 Change-Id: I6fc446fbc8df70c9652c1efef03daed9fa9ea839 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QmlCompiler: Expect singleton members to be shadowableUlf Hermann2025-10-085-0/+91
| | | | | | | | | | | | | | | | | | | | | | You can return an instance of a derived class from a singleton's create() method and that derived class can shadow members of the singleton. We have no choice but to run many singleton accesses through the shadow check. There are some exceptions: 1. Extended singletons can't be shadowed since their concrete type can't be known in advance and the respective QQmlType can't stitch the metaobjects together to make that happen. 2. Composite singletons can't have factory functions. They also cannot be shadowed. 3. If the whole class is final. We can't detect that, yet, though. Pick-to: 6.10 Fixes: QTBUG-140738 Change-Id: Ia6c235636aec723e834db0089a9471f3b0a1e2fa Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io> Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* QmlCompiler: Fix write access to QVariantMapUlf Hermann2025-10-073-4/+41
| | | | | | | | | | | | Without this, it tries to resolve the metaObject of QVariantMap, which crashes. Amends commit cca07aa78841f2d743f0b4d933abb0dd66f0b948. Fixes: QTBUG-139626 Pick-to: 6.10 6.8 Change-Id: Id747429ed0d558932b9a6cb8f59e3740982efb56 Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* QtQml: Add test for writing to delayed propertiesUlf Hermann2025-10-064-1/+196
| | | | | | | | | | This proves that commit a7349e6433d092398d76cafa5408753f06892cd7 fixes QTBUG-139687. Pick-to: 6.10 6.8 Fixes: QTBUG-139687 Change-Id: I2730b545738bf75e381b0b396b74c5060fa9b0e1 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QtQml: Fix assigning to QML-defined list propertiesUlf Hermann2025-10-023-0/+71
| | | | | | | | | | | | | | | | | Returning an invalid QVariant from toVariant() is not helpful. We can't produce a QQmlListReference in that case because there is no object, but a QObjectList works just fine. Writing to list properties via the metaobject is very much supported. We can easily implement it using the same technique we use for reading. Finally, to get the signal counts right, we also need to compare the lists before assignment when taking the QQmlProperty code path. Pick-to: 6.10 6.8 Fixes: QTBUG-140690 Change-Id: I09d6412f3f2ec86144810f47d0d620b63dfcd280 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QmlCompiler: Don't adjust the same conversion multiple timesUlf Hermann2025-09-233-0/+75
| | | | | | | | | | | | The same conversion can re-surface in multiple places in the byte code by virtue of being stored and loaded unchanged. If we've already adjusted it, we don't need to do it again. Pick-to: 6.10 Fixes: QTBUG-140415 Change-Id: Ic1e7e90af49f0ee9440a9c37abd4ab8ee0fdbe3e Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io> Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QmlCompiler: Properly handle uncertain component statusUlf Hermann2025-09-184-0/+42
| | | | | | | | | | | | | | | | | | | | | | | | | | | In order to determine whether an ID is visible from a referrer we need not only determine the component boundaries of the referrer, but also those of the candidate elements with the respective ID. Rewrite the logic to have QQmlJSScopesById handle this. It has to iterate the respective elements anyway and can therefore easily check if one of them is assigned to an unknown property. It now provides low-level methods that output all possible candidates for an ID, while also stating the confidence associated with them. The plain id() and scope() methods only return results we are actually certain about. In places where we generate warnings or can allow for some fuzzy results, we use the low-level methods, since those generally produce more informative results. The QML DOM was passing the JavaScript global object as referrer to the scope() method before. This happened to work but was, of course, wrong. Make sure that ID elements in the DOM receive a proper QML scope to avoid that. Pick-to: 6.10 6.9 6.8 Task-number: QTBUG-140041 Change-Id: I41cf8603ae6a5d5461d3c12d74521e68b5e28ea4 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io> Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* tst_qmlcppcodegen: Adjust to fixed binding behavior in qtbaseUlf Hermann2025-09-181-1/+2
| | | | | | | | | | | | If the binding throws an exception, the binding wrapper internally returns false. This should result in the value being discarded. We had a long standing bug in qtbase that caused the value to still be accepted in certain cases. Commit 440a63a33e7176167d91244467fa380bae684173 fixed that. Fixes: QTBUG-140161 Change-Id: Ib36a32909dc3d487bea887cb7f89d7fcfeca2031 Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
* QmlCompiler: Guard against disappearing arrow functionsUlf Hermann2025-09-153-0/+80
| | | | | | | | | | | You can override a QObject method with a JavaScript function and take away the JavaScript function later by swapping out objects. This should not crash. Pick-to: 6.10 6.9 Fixes: QTBUG-140074 Change-Id: I85b17f4f619235024d0f1a27b4ff4128c7a57083 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QtQml: Avoid double-wrapping when converting to QVariantListUlf Hermann2025-09-114-1/+29
| | | | | | | | | Amends commit 1b89c1edcae68351632c2755e5408410c2ff98e3 Fixes: QTBUG-139764 Pick-to: 6.10 6.9 6.8 Change-Id: I1488527a235d74fc0352c72b9bfb69589c2f3d93 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QmlCompiler: Ensure QObjects returned to AOT-compiled code are wrappedUlf Hermann2025-09-024-0/+72
| | | | | | | | | | | | If a QObject is returned from a method call, the QML engine takes ownership of it and it needs to be deleted by the garbage collector. Our generated C++ code so far did not actually take ownership of the object and thereby caused it to leak. Pick-to: 6.10 6.9 6.8 Fixes: QTBUG-138919 Change-Id: I7bd57b3612bf4b98937756e8a7a7c03aff1c9b32 Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* QtQml: Mark values on the AOT-compiled stack during gcUlf Hermann2025-09-024-0/+88
| | | | | | | | | | Keep them in a special generated struct with virtual method that gets called from the GC for each frame. Pick-to: 6.10 6.9 6.8 Fixes: QTBUG-139059 Change-Id: I81bcbeab6531e174a5207d03f57d241461ae9ba3 Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* QtQml: Store detached Sequence objects on the JS heapUlf Hermann2025-09-023-4/+46
| | | | | | | | | | | | | | | | | | | | | While the Sequence is detached it is subject to the GC or unrelated C++ code deleting objects from its internals. Since it's then not the owning object's responsibility to track this anymore, we need to track it ourselves. The way to do it is to use the existing V4 objects. We don't have to store the sequence on the JS heap if it cannot store a QObject. Only lists of variants or pointers are affected. This independently fixes QTBUG-129972 for 6.8 where VariantAssociationObject does not exist, yet. This is because the detached sequence shown in that bug won't need to be written back to anymore in order to stay up to date. Pick-to: 6.10 6.9 6.8 Fixes: QTBUG-129972 Task-number: QTBUG-139025 Change-Id: Ib469c6c65f2f96041e2ad2fd106f8cd60a182e13 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QmlCompiler: Fix access to optional QVariantMapUlf Hermann2025-09-013-0/+10
| | | | | | | | | | Without this, it tries to resolve the metaObject of QVariantMap, which crashes. Fixes: QTBUG-139626 Pick-to: 6.10 6.9 6.8 Change-Id: I9248f57c428810024f9983df959f475e6557576c Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QtQml: Store detached VariantAssociation objects on the JS heapUlf Hermann2025-08-214-0/+129
| | | | | | | | | | | | While the VariantAssociation is detached it is subject to the GC or unrelated C++ code deleting objects from its internals. Since it's then not the owning object's responsibility to track this anymore, we need to track it ourselves. The way to do it is to use the existing V4 objects. Pick-to: 6.10 6.9 Task-number: QTBUG-139025 Change-Id: Ic1d5aa85171b5d91c2b9d546963268b6f09c2802 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* Compiler: Detect calls on partially deleted objects and throwOlivier De Cannière2025-08-183-0/+43
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | Component.onDestruction can be used to execute some code as an object is being destructed. The code may, however, reference objects that are no longer in a valid state because they themselves have already been destructed. We then throw an exeception. Commit a741271dd58b21728928684f1ef1efaa91e79ebf introduced the init step for calls in which the types of arguments are resolved. For object methods, we need to check that the object is still valid or throw an exception otherwise. This is made more complicated by the fact that, in some cases, the destruction of the object happens in a somewhat chaotic manner where, for instance, the object is still alive but its method and property storage has already been deleted. This inconsistent state is the cause of QTBUG-138516 and existing checks for invalid objects were not sufficient and we crashed when trying to use the function that we were unable to resolve. We can detect this particular problem by checking whether the ddata of the object still has its jsWrapper. Amends a741271dd58b21728928684f1ef1efaa91e79ebf Fixes: QTBUG-138516 Pick-to: 6.10 6.9 Change-Id: Ifdd7708d73ea6012d1e07aebed257b3f538183c1 Reviewed-by: Ulf Hermann <ulf.hermann@qt.io> Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
* qmltyperegistrar: Manually register names for Q_ENUMSUlf Hermann2025-07-074-0/+47
| | | | | | | | | | | | Flags declared with Q_FLAGS lack the methods for properly extracting the typedef'd name. We need to manually register the typedef. Amends commit 8bf5aae19b77b618f3f7a55a59e87c8a319475a8. Pick-to: 6.10 6.9 6.8 Fixes: QTBUG-138174 Change-Id: I7c373f4d810a0c9a5590f39cc629015662a69ed4 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QtQml: Correctly track alias resolutions skipsOlivier De Cannière2025-07-023-0/+26
| | | | | | | | | | | | | | | | | | | | | | | | | | | When trying to resolve all aliases on an object, we iterate over them one by one. If all are resolved successfully, we return AllAliasesResolved and consider this object done, if an alias fails, we return NoAliasResolved or SomeAliasesResolved and we will try again later. This can be the case for aliases to aliases. We defer resolving the first one until the target alias is resolved first. There was a bug in the logic that counts how many of the aliases were successfully resolved and how many were skipped. When skipping an alias to an alias, we cannot count it among the completed ones. This leads to an alias not being resolved and added to the property cache. Thankfully, a runtime assert then catches the discrepancy between the number of aliases in the property cache and in the compilation unit. Early exit when detecting that the alias points to a non-local unresolved alias to try again later. Also update the aliasIndex as part of the for loop update. Amends 9e1378260a3f3a6eb4cad8d6ae47bc218e6a2b5f Pick-to: 6.10 Change-Id: I6ee7a796a0b4890393d5b17ebea2686c55955394 Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
* QmlCompiler: Preserve external side effects across jumpsUlf Hermann2025-06-273-0/+32
| | | | | | | | | | | | | | | Now that we discern internal and external side effects, we cannot implicitly rely on every jump to generate a side effect anymore. We need to actually update the virtual registers and also merge the side effects (along with other flags). Amends commit 6b14ba5c2fbc2810bb62a87008e338cca571acf6 Pick-to: 6.10 6.9 6.8 6.5 Task-number: QTBUG-137540 Change-Id: I6b46c7a4773759c8f6f30308ba72082555ce3e61 Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io> Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* compiler: Avoid invalid C++ code generationFabian Kosmale2025-06-262-2/+19
| | | | | | | | | | | | | | | | inlineConsoleMethod's stringConversion needs to create a string, so that we can later append to it. Because we were missing parentheses, this did not happen, and we would end up with code looking like u']'.append(...) which obviously isn't valid C++. Fix this by always adding parentheses around the expression. Found while trying to prove that QTBUG-109279 was fixed. Task-number: QTBUG-109279 Pick-to: 6.10 6.9 Change-Id: I67fce5b2c1f1460a5d6b617824f3c36f9804ea76 Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* QmlCompiler: Discern between different kinds of side effectsUlf Hermann2025-06-232-1/+46
| | | | | | | | | | A mere jump does not cause all value types and lists to be invalidated. Only calls to other functions or writes to other properties do that. Pick-to: 6.10 6.9 6.8 6.5 Fixes: QTBUG-137540 Change-Id: I069c6873455c51bbea59cf876d2bc7ecd188f81b Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* QmlCompiler: Sharpen side effect detectionUlf Hermann2025-06-233-1/+50
| | | | | | | | | | | Stack-created lists of primitives or pointers cannot be affected by side effects. We cannot write a value affected by side effects to a list that isn't, though. Pick-to: 6.10 6.9 6.8 6.5 Task-number: QTBUG-137540 Change-Id: I99ab4337cabc6111a81b8164fd94962edc0db25e Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* QmlCompiler: Restore support for writing to temporary arraysUlf Hermann2025-06-233-0/+26
| | | | | | | | | | | We use the JavaScript extension as "read" type to signify that the code generator will accept any type with such an extension. This requires some adjustments in the type resolver. Pick-to: 6.10 6.9 6.8 6.5 Task-number: QTBUG-137540 Change-Id: Ia34ca0a24c417c5372852268ba2f55825484639d Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* Qml: Allow accessing unscoped enums values as <Component>.<Enum>.<Key>Olivier De Cannière2025-05-312-10/+4
| | | | | | | | | | [ChangeLog][QML] It is now possible to access unscoped enum values in a scoped way as <component name>.<enum name>.<key>. Previously, it was only possible to access them in an unscoped way. Task-number: QTBUG-116513 Change-Id: Iff56cd3365516215e1e195a147fae66ee17d39e3 Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
* Compiler: Deduplicate conversion origins based on register's contentOlivier De Cannière2025-05-013-0/+20
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | In the type propagator, when encountering back jumps, we need to run the pass again in order to ensure that the state of the registers at the target of the jump is fully known. For this, we need to compare the latest state in the current pass with states we have encountered earlier. If a match is found, no more passes are needed. The propagation is run multiple times and state is accumulated between passes. For certain conversions, this will try to append types as origins again every iteration. These would previously have been deduplicated by QQmlJSTypeResolver::merge but, since the change at 1e095058e165b1c2f244799ca1928ae4cc046a2c, we consider 2 registers to be equal only if their d pointers are equal. And since instructions such as MoveRegexp create a new register for the literal type RegExpr every time, the pointer doesn't match with the one from the register created by the instruction during the ealier pass. This would lead to set of origin types growing forever and to the state never matching a previous one. This, in turn, caused an infinite loop because an additional pass was always deemed necessary. Therefore, restore the old logic that deduplicates based on contained type, variant, and (recursively) scope. Amends 1e095058e165b1c2f244799ca1928ae4cc046a2c Fixes: QTBUG-135457 Pick-to: 6.9 Change-Id: I23167e95b958304698d12537598c1d72b03a5364 Reviewed-by: Ulf Hermann <ulf.hermann@qt.io> Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* Compiler: Skip bindings to properties of type QQmlScriptStringOlivier De Cannière2025-04-173-0/+44
| | | | | | | | | | | | | | There is nothing to do in the compiler. Setting the value of the property is already handled in by the object creator or the qobjectwrapper. Reading the value doesn't really makes sense and defeats its purpose . Fixes: QTBUG-134790 Pick-to: 6.9 6.8 Change-Id: I4576eb528e0dec273830b0244149a92ceb325bc9 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* Tests: include QTest, not QtTestGiuseppe D'Angelo2025-04-151-1/+1
| | | | | | | | | | | | | Never use module-wide inclusions. They blow up build times. For QtTest this is usually just a typo (QTest was meant instead). Add missing includes as needed. In the diffs I've spotted other huge inclusions (QtQuick, QtQml), but those need more attention. Task-number: QTQAINFRA-7110 Pick-to: 6.9 6.8 Change-Id: I74bf3fe212f50a7a3a6af2b1c80bbcaabc2516d7 Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
* QmlCompiler: Error out on unstorable typesUlf Hermann2025-04-144-0/+33
| | | | | | | | | We already do this for return types, but it's fatal on any type. Pick-to: 6.9 Fixes: QTBUG-135342 Change-Id: I7aee2a19ffcd39d2707eceb34b5073057d8b5ebb Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* Compiler: Use regular lookup for redundant optional lookupsOlivier De Cannière2025-04-103-0/+18
| | | | | | | | | | | | | If we can determine that the base of an optional lookup cannot hold null or undefined, we can simply omit the optional part and generate a regular get lookup. This is also true whenever we lookup an enum. Amends fc4ee77116624c784d8c42f2b8e5dbf2f78b6d89 Fixes: QTBUG-135649 Pick-to: 6.9 6.8 Change-Id: I64984fdecc75cd4dbc2274a08aa73b5274fb09b7 Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
* QmlCompiler: Do not re-resolve iterator value typesUlf Hermann2025-03-314-0/+52
| | | | | | | | | | | | | | | We've resolved the value type in the type propagator. Trying to do it again in the code generator, after the iterator may have been adjusted, is quite wrong. If we resolve the list value type on a type that's not a list (anymore), then we get an invalid type, which subsequently crashes. Amends commit a173d50a9e54d2a21a5207f6c66bb54bb8f3a612. Pick-to: 6.9 6.8 Fixes: QTBUG-135288 Change-Id: I1227803ed100c83f8fc11898be0a4d0199d639dd Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
* QML: Add final property attributeOlivier De Cannière2025-03-064-0/+27
| | | | | | | | | This works the same as the FINAL attribute to Q_PROPERTY. Task-number: QTBUG-98320 Change-Id: Icc2cf1afb5354fd711770f7147ded853b74cd1da Reviewed-by: Ulf Hermann <ulf.hermann@qt.io> Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* tst_qmlcppcodegen: Avoid cmake warningFabian Kosmale2025-03-041-0/+1
| | | | | Change-Id: Ic737b2750114d022dbc292ebc19da36b82db1c2a Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* QtQml: Support url and date in 'instanceof' and 'as'Ulf Hermann2025-02-282-0/+15
| | | | | | | | | | | | | | | | | | | Those have several possible representations. Besides QQmlValueTypeWrapper, they can also be their own special heap objects with extra methods, or VariantObject. Also, remove some pointless restrictions in QmlCompiler that prevented such as-casts from being compiled to C++. The code generator will currently reject non-trivial type assertions for value types. Therefore we don't have to take care of ValueTypeBehavior: Assertable, yet. Also fix tst_qqmllanguage::instanceOf() to actually test something. So far the return value of the expression was ignored for most data tags. Pick-to: 6.9 Fixes: QTBUG-130291 Change-Id: I2facf48455a04a02a078615e5ebd4b1c26d1bd93 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QtQml: Clean up qmldir redirectionUlf Hermann2025-02-267-0/+57
| | | | | | | | | | | We need to perform the redirection before inserting imports into namespaces. Through the redirection we might discover a module that we have already imported before. In that case we must not import it again. Pick-to: 6.9 6.8 Fixes: QTBUG-133587 Change-Id: I47a279461763b5397137002a9e7c7d3bfc7ad15d Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
* QtQml: Fix AOT compiled context for destroy() and toString() methodsUlf Hermann2025-02-263-0/+133
| | | | | | | | | | | | | | | | | | | | Those are not mapped to regular QMetaMethods but rather come with special method indices and need to be resolved separately. Amends commit a741271dd58b21728928684f1ef1efaa91e79ebf This exposes that the override order between JavaScript extensions and their base types was wrong. JavaScript extensions do certainly not override their base types. Fix this, too. We also need to always specialize the lookups for these calls. It doesn't actually matter if there is propertyData or not since we branch off into the special cases anyway when calling them. Pick-to: 6.9 Fixes: QTBUG-132602 Change-Id: Iea83ce94459b0d0a3bf54731898fd62b9ad46c46 Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
* QmlCompiler: Tighten detection of assignment to unknown propertiesUlf Hermann2025-02-213-0/+30
| | | | | | | | | | | | | | While those properties may be of type Component, they don't have to. We can in fact not resolve anything resembling an ID while inside one of those objects because we cannot determine the component boundaries. Amends commit dea8e38d95508acd67da997d0c2a9c91ef1bc887 Pick-to: 6.9 6.8 Fixes: QTBUG-133460 Change-Id: Iac7294166d38ce591c45c0d31b139a52eda70fc1 Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io> Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* QmlCompiler: Extend the listConversion testUlf Hermann2025-02-192-0/+44
| | | | | | | | | | | | | The actual conversion code suggests that we may be creating a shared list property. However, the assignment code internally won't let that happen. Test as much. Amends commit 3108c58b97074b68ba48f452955727c67c4f77bc Task-number: QTBUG-133047 Change-Id: I66f0f043e0dabd2693aa50a30478461a5db5c5ad Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io> Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
* QmlCompiler: Only import hardcoded builtins by defaultUlf Hermann2025-02-183-0/+18
| | | | | | | | | | | | | | | | | | | | | | | | | At run time, not all the builtins are always available, but only those hardcoded into the parser. If we always import all the builtins at compile time, we introduce subtle errors when they shadow parts of the JavaScript global object. Now the builtins need to be actually imported. We cannot rely on the magic that adds them to the root scope of each document anymore. To this end, they need to become a regular module. The builtins are now loaded using a qmldir, just like any other module. The only thing special about is its "system" attribute which we now take to mean "read jsroot.qmltypes". Furthermore, the builtins get a "static" attribute so that we don't warn about them being unused. Even though they can now technically be unused, we really want people to still import them. Pick-to: 6.9 6.8 Fixes: QTBUG-133461 Change-Id: I322e14ba85c939773d36143ca24e88a7c9db23f5 Reviewed-by: Sami Shalayel <sami.shalayel@qt.io> Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io> Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
* Compiler: Add missing conversion for variant equality comparisonsOlivier De Cannière2025-02-184-0/+50
| | | | | | | | | | | | The comparison code was generated properly but the conversion to safely assign the result of the comparison to the out accumulator was missing. Amends 78b58582baccb2c214dfb07083e91eb47e45358a Fixes: QTBUG-133636 Pick-to: 6.9 6.8 Change-Id: I9f790b449b48c382064954ad4235d25d221f1168 Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
* tst_qmlcppcodegen: Explicitly link against private APIFabian Kosmale2025-02-181-0/+4
| | | | | | | | | | | The QML module uses private headers; currently, this works because qmlcachegen implicitly links the generated code against the QmlPrivate, but we want to move away from that. Task-number: QTBUG-87776 Pick-to: 6.9 6.8 Change-Id: If15d7b0549510ee97729e450523776691747f151 Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
* QtQml: Add conversion code for QQmlListProperty to other listsUlf Hermann2025-01-243-7/+74
| | | | | | | | | | | We have the same conversion code already for lists of value types and JavaScript arrays. Specialize the common cases of QObjectList and QQmlListProperty<QObject>. Pick-to: 6.9 6.8 Fixes: QTBUG-133047 Change-Id: I10826d4a965e18471a486e19befef961ec9a4a6e Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>