Process all properties of custom parsed types and generate errors if the
custom parsed properties are actually used. Then print an extra error
stating that qmltc does not support custom parsers.
Pick-to: 6.9 6.8
Fixes: QTBUG-134206
Change-Id: I37e4f3f8d0ee4e0926c0d64c99a4a521b093a1ab
Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
This is done in prepartion for the following patch in the chain.
Pick-to: 6.8
Change-Id: If8ce75be8ba00e7e4cdd5a0f5e66319ab0d36755
Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Allow qqmljsscopes of QML components to have "own" module names, and
add a helper method moduleName() that helps retrieve the module name
of some (possibly non QML component) qqmljsscope by iterating over its
parents.
That is required for the renaming of qmlcomponents and allows to check
if the qml element to be renamed is defined in the same module as the
current module. (It is not allowed to rename a QML component from
another module).
Task-number: QTBUG-114993
Change-Id: I09d57ec87cfc64de31859b2af6334264c4fa6912
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
Use the private API to convert QQmlSA objects into QQmlJS elements
wherever it was not possible to use the QQmlSA objects:
The static method canConvertForLiteralBinding has a comment that seems
to say 'we need this so dont touch this' so do not change its code.
Furthermore, it requires a QQmlJSTypeResolver, so obtain it from the
PassManager's private struct.
It seems that QQmlJSLiteralBindingCheck was the only user of
QQmlJSMetaPropertyBinding::literalTypeName, so move it to
QQmlJSLiteralBindingCheck instead of adding literalTypeName to the
QQmlSA interface.
Make QQmlJSLinter always create the passManager, even when there are no
plugins available, such that the QQmlJSLiteralBindingCheck can be run
using the QQmlSA interface. Also fix Qmltc to use the new
QQmlJSLiteralBindingCheck api.
Change-Id: I27dfc63d411e38740e2993ccf9af352271ae6d47
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
Change qqmljsimporter to accept a custom importvisitor instead of a
custom importvisitorcreator. This gives more flexibility, for example to
allow to use populateQmlFile() in combination with qqmljsimporter.
Extend DomEnvironment::ensureImporter() to set up a custom
visitor in the importer that calls populateQmlFile() to construct the
Dom lazily.
Adapt the qmltc custom visitor creator to be a custom visitor.
Add a basic test to see if the qqmljsscope created on two files with the
populateQmlFile() custom visitor share the same address. This is a
requirement for the find usages functionality.
Also run the importvisitor even when parsing fails:
The importvisitor for the Dom will parse the code again with parser
recovery, and therefore the importvisitor has to always be run to get
the parser recovery working in the tests.
Do not try to load dependencies in LoadInfo::doAddDependencies, because
it will trigger QmlFile lazyloading. This happens because dependencies
in the form of import statements can only be processed if
qqmldomastcreator already collected all the import statements.
Instead, load the dependencies in qqmldomastcreator (that is, during the
lazy loading) when encountering import statements. Like this, a lazy QML
file will only load its imported modules when its getting populated.
Also make sure to not load anything if NoDependencies is enabled in the
DomEnvironment options.
Add a state enableLoadFileLazily in qqmldomastcreator to know if
loadPendingDependencies() needs to be called or not. When the file is
being lazily loaded, then loadPendingDependencies() needs to be called
to get the imports correctly loaded. When the file is not (because
WithSemanticAnalysis is disabled in the DomEnvironment), then
the imports are already being processed in loadPendingDependencies() and
calling it again recursively breaks loadPendingDependencies().
Allow the qqmldomastcreator to commit lazily loaded dependencies to the
validEnv by saving a pointer in domEnvironment of the latest used
domEnvironment. And do a commitToBase after loading dependencies from
imported modules.
Task-number: QTBUG-122645
Change-Id: I3ca8bc011dcb5920fffab786cdb9e748667be48e
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Add a warning for QML defined types imported from other modules in
qmltcvisitor to avoid qmltc generating invalid C++ code.
This requires populating the moduleName member of qqmljsscope where it
was ignored:
* for qmldir files imported via command line options
* for inline components
* for the file to be compiled
The module name of the QML file to be compiled is passed
from CMake to qmltc via a newly introduced command line argument, and is
simulated in the tst_qmltc_qprocess tests.
Pick-to: 6.5 6.6 6.7
Fixes: QTBUG-121592
Change-Id: I965d759a028546c648ccf6c9aa469b84538be446
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
It is not needed by the QQmlSA API. Additionally, remove the comparison
operator for LoggerCategory and LoggerId, and replace its users by
getting the id from the category before comparing.
Pick-to: 6.6
Change-Id: I7747b09b941cfd5326b95d2ee2f78b0ee10991d3
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
Reviewed-by: Semih Yavuz <semih.yavuz@qt.io>
Reviewed-by: Olivier De Cannière <olivier.decanniere@qt.io>
This patch adds abstractions for QML Elements, Bindings, Methods and
Properties. This abstraction layer avoids exposing internal details and
should be more suited for static analysis tasks. It is now possible to
write qmllint plugins without including private headers.
As a drive-by, change tst_qmllint:verifyJsRoot to open files in text
mode instead of binary. This fixes an issue where line endings cause
issues on Windows.
Fixes: QTBUG-102276
Change-Id: I6b6e53f1e0078734a18f3aa51807fbe875b375f0
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Add QMLTC_EXPORT_MACRO_NAME and QMLTC_EXPORT_FILE_NAME arguments to
qt_add_qml_module() that allows the user to export qmltc-generated code
from its library. The qmltc-generated code will include the header-file
specified in QMLTC_EXPORT_FILE_NAME and will be exported with the macro
specified by QMLTC_EXPORT_MACRO_NAME.
Leave both options unspecified to not export the code generated by
qmltc.
Describe the options in the documentation and write a test to see if the
class really has an export macro in the generated code:
1) tst_qmltc_qprocess will test if the macro and the header are correctly
inserted in the generated code.
2) tst_qmltc_{no,}diskcache will test if the generated code can still be
used from a static library.
Fixes: QTBUG-106840
Task-number: QTBUG-96040
Change-Id: I554f03bcdf043e8114e42f51a7289a5c00de4f89
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
There are many ways to "hide" the qmldir from the engine at run time,
which turns singletons into regular types. While all of this is invalid,
we should not assert on it, but rather produce a legible warning.
Furthermore, sharpen the importing of extra modules from qrc as implicit
imports. We should really only import modules the file in question can
ever be part of. Otherwise we needlessly produce the above situation and
hide legitimate warning messages.
Amends commit 7517c1b3ae.
Now we need to teach our tools about the default import paths in the
resorurce file system. They cannot guess any type they may find in any
resource file anymore.
Pick-to: 6.5
Task-number: QTBUG-106929
Change-Id: Ic8c02396d10830a7f461e8a81649bb8c9a1add1f
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
QmlImportVisitor has some log messages that is only used for controls
sanity tests. Move these loggers into a QuickControlsSanity plugin.
Move the relevant tests from tst_qmllint to tst_sanity as we link the
plugin to tst_sanity. Also remove qmlControlsSanity category from the
default categories of QQmlJsLogger as it should be only utilised by this
plugin.
Task-number: QTBUG-103276
Change-Id: Iacc624711a2cd00aeb9d89fbde7c0131896d30ce
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
Dashes and other special characters in qml filenames makes
life quite complicated, the generated cpp file will contain
everywhere and be uncompilable.
Instead, directly print an error message explaoining which names
are allowed for type compilation and return.
Reasoning:
The name of the qml file is also the name of the qml object.
For example, using a dash in the filename makes the corresponding
qml type have a dash in its name and renders the type mostly
unsuable in qml.
Therefore, only allow characters, digits and underscores.
Pick-to: 6.4
Fixes: QTBUG-107079
Change-Id: I4bff12e4a644b479213e7cc578207c8a443fc517
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
We need those to prevent usage of the host Qt's import path when
building QML files for the target.
Task-number: QTBUG-106365
Pick-to: 6.4 6.4.0
Change-Id: I34499af850fb759603206cb429ff97633c76054d
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
Instead of doing build file path to source file path mapping for each
QML file, we could store qml module prefix to qml module output
directory mapping instead. This reduces the produced qrc size and makes
it more convenient to work with
Do a clean separation at the QQmlJSImporter level to prevent using
resource file mapper for build directory path resolution
Amends 7f567e6a42
Change-Id: If984abada1d39c386af5712af778eb29956e0537
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
This change makes qmljslogger use an ID based system for categorizing
logging entries instead of using an enum. This allows plugins to
register their own logging categories after the fact.
It's also necessary for us to later show the warning ID when
printing warnings and for creating documentation for each ID entry.
Currently not every ID maps cleanly to only one type of warning,
this has to be cleaned up in a follow-up change.
Task-number: QTBUG-103453
Change-Id: I4cac6be7ca165b938e0ea032d077823bf17baf75
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Due to custom basenames in CMake qmltc can create non-default file names
that contain the generated C++. This would cause troubles when locally
importing such a custom-marked QML file from the same module. Resolve
this by introducing a qrc-based mapping from source file name to C++
header file that the generated code would be put into
Use the mapping information inside QmltcVisitor so that imported types
are properly set
Doing so, with some additional fixes around file paths collection,
allows to get rid of the prototype code completely
Fixes: QTBUG-104094
Pick-to: 6.4
Change-Id: I6a54774addf303449f35915df501ab3f47470c44
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Alexey Edelev <alexey.edelev@qt.io>
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Replace the current license disclaimer in files by
a SPDX-License-Identifier.
Files that have to be modified by hand are modified.
License files are organized under LICENSES directory.
Pick-to: 6.4
Task-number: QTBUG-67283
Change-Id: I63563bbeb6f60f89d2c99660400dca7fab78a294
Reviewed-by: Shawn Rutledge <shawn.rutledge@qt.io>
Relocate the prototype code that tests for reserved C++ words used in
QML document over to QmltcVisitor
As a drive by, remove internal name update code as well since this is
already covered by the visitor for a long time
Pick-to: 6.4
Change-Id: I88b2ea6b2f0ac313357b36b6cf8957e99ab56edc
Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Remove the prototype code bits in favor of QmltcVisitor logic
To make this work correctly, we have to use QmltcVisitor when
visiting imported scopes
Pick-to: 6.4
Change-Id: I6225fb672a020f7720fe29806c4ad6370c737568
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
We no longer need it so remove it from the prototype code. Some code
that updates QQmlJSScopes is still necessary on the other hand
Pick-to: 6.4
Change-Id: I22c9bbcf30ff080a69f360f2f3a0515b18e8e2f3
Reviewed-by: Maximilian Goldstein <max.goldstein@qt.io>
qmltc now shows a helpful error message if no C++ file or no C++ header
file argument was passed instead of hitting internal assertions.
Change-Id: I859426f95001b22aff41f391cddf1327e31425b8
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
Reviewed-by: Andrei Golubev <andrei.golubev@qt.io>
Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
We generally avoid passing arguments as non-const reference.
Change-Id: I3d2d7ba372f487af71d2478b6238be0756ed4ae0
Reviewed-by: Andrei Golubev <andrei.golubev@qt.io>
While deeper integration requires more changes, we can already
establish the general relationship now. The idea: slowly migrate
to the proper qmltc compiler code. To achieve this, we can step
by step distill prototype's code generator in the qmltc code
generation. Right now, do it at the highest level by compiling
everything with the prototype's codegen (as before) but within
the "proper" qmltc compiler
Change-Id: I8a1e62f0559ff437ec2a4b0727147a441367c8e2
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
- Wrap prototype code into Qt namespace
- Move inline component logic from prototype/visitor to qmltcvisitor
and erase (for now) property method setting (in favor of the
prototype logic which is more advanced)
- Move prototype/typeresolver.cpp into qmltctyperesolver.cpp
- Delete (now useless) prototype/{visitor, typeresolver}
- Start cleaning up prototype/qmlcompiler.h
- Adjust prototype/codegenerator accordingly
Change-Id: If49d6aa8bb97093b273915caa356278ca9bbdfe1
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
qmltc should really interpret most of qmlcompiler warnings as errors.
There could be exceptions but for now let's just reject any malicious
code (except for ControlsSanity since it is itself malicious)
Fixes: QTBUG-100052
Change-Id: Ib18741d0a46c4d0ddb40b53e34658804c0245018
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
This should just work now since the offending file is commented out as
unsupported
As a drive by, change the location of global warnings processing: we
should do it before code generation starts
Change-Id: Id0fc02dd5c8cd19090cf0382d8d4f390717f0ecd
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Reviewed-by: Maximilian Goldstein <max.goldstein@qt.io>
High-level goal: be able to reuse existing infrastructure
"as is" to configure semantic analysis categories in tools
(qmllint, qmltc, qmlsc, etc.)
To achieve that, simplify the logging to always "log"
something, without explicitly specifying the severity. The
severity is now baked into the category (and we can extend
those to cover different cases)
One slight deviation is the cache generation which likes
to do its own thing at present. Provide a "forced logging"
option where we can specify which severify we want. The
hope is that this gets removed at some point
Particular list of (noteworthy) changes:
* No more "thresholding" by the level (this is rarely needed
and is actually questionable). Instead, we can ignore a
particular category explicitly
* Category levels are repurposed as category severities
(at least from the high-level picture that always should've
been this way)
* log{Warning,Info,Critical} removed. We use category severity
instead
* "category error" makes zero sense so removed: if our severity
is:
- QtWarningMsg (qmllint), it is already an "error"
- QtCriticalMsg (compilers), it is already an "error"
* Align m_output and m_{infos,warnings,errors} stored information
* Accept the fact that we don't support QtDebugMsg and QtFatalMsg
* Additional categories added to cover for places where the same
category would be both an error and not an error
Task-number: QTBUG-100052
Change-Id: I3cd5d17d58be204f48428877bed053f756ac40a8
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
This change adds a warning if we encounter a component marked as a
singleton in a qmldir file which does not contain a pragma
Singleton entry and vice versa.
Note that the warning only gets triggered if the singleton is
actually used.
Fixes: QTBUG-98558
Change-Id: Id7c63f48ba49759c15dffcaee0270c7caab2eb7d
Reviewed-by: Andrei Golubev <andrei.golubev@qt.io>
It does not seem to be necessary at all at the moment. Using the TP
status of the tool, we can eliminate it now. This could always be
reverted if users needed it, but so far --resource is enough
Change-Id: I39cd2cd854d99a6eee8f6dcf49ab904aad53c241
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
Similarly to qmllint, we should use QQmlJSResourceFileMapper
in qmltc. This should in theory allow us to avoid
implicit import dir vs qmldir path issues (where the former
comes from source dir while the latter comes from build dir)
At present, it does not seem to be the case, however. But
this is to be addressed separately
Task-number: QTBUG-100103
Pick-to: 6.3
Change-Id: Ie85799cb0a4b8b1620964000bc5939e9d046678e
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
qmllint's utility is rather limited when we can pass it neither the
qmldir nor qmltypes files. Instead of trying to somehow handle the case
with ifdefs, move the feature check into the build system and
completely disable the tool if we lack the parser.
The same holds for qmltc, which is already completely unusable without
the parser (and just prints an error message if build without the
feature enabled).
Change-Id: I31828bb7d551caeaffd1974d1dff14a25446ce95
Reviewed-by: Andrei Golubev <andrei.golubev@qt.io>
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
The tools will still grudgingly accept qmltypes files being passed via
the -i option. We generally expect qmldir files, though. Ignoring the
qmldir file and importing the qmltypes directly, ignores qmldir imports,
dependencies and other component entries. This leads to unresolvable
types.
[ChangeLog][QML Tooling] qmllint expects qmldir files, not qmltypes
files to be passed via the -i option now. This enables it to see the
imports and dependencies of the module being imported. For backwards
compatibility it still accepts qmltypes files, with a warning.
Pick-to: 6.3
Fixes: QTBUG-99043
Change-Id: I5ed32d7e78df1e604aaf1bfa2ebda09d5d57b628
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
The default AOT compiler compiles QML code in indirect, dynamic mode. It
uses the logger's Log_Compiler category to determine the verbosity of
its output. In addition you can use the qt.qml.compiler.aot category for
even more verbosity. In preparation for using QQmlJSAotCompiler with
qmlcachegen, the default level of that category is increased to
QtFatalMsg. The highest level we actually output is QtDebugMsg, so it
doesn't make a difference yet.
If the logger's Log_Compiler category is set to produce errors, it will
qFatal() on "pragma Strict" violations.
Change-Id: Ieb74bfa7cd51cfa8616792ab467c32f6ba0e0702
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
The compile passes shouldn't need to change the document, AST, or IR. At
least not accidentally. We might add interfaces to explicitly modify
things later. As a side effect, you can now use one instance of
QQmlJSTypeResolver for multiple documents by re-init()'ing it.
Change-Id: Ic3544b3ddedd30d7f8d00b1df9cee3e6292ca7de
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
We want to be able to skip it.
Task-number: QTBUG-98305
Change-Id: Ibb0293d348f2828a28be4c458cf955b4cc706caa
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
... and give a hint on what to do about it. In order to not duplicate
all the warnings from the importer, make sure it runs only once.
Change-Id: Ie2b314ff659664f7c84c20cc7971c094e15c59cf
Reviewed-by: Maximilian Goldstein <max.goldstein@qt.io>
Ignore type conversions for now. Expect C++ to handle them
magically for us. The simple binding type dependent conversions
that are performed already should suffice
Task-number: QTBUG-84368
Change-Id: I62bd36ccf6c60fd62c2a50b6e011c637c5bcfbce
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
We only support dynamic semantics here.
Task-number: QTBUG-98305
Change-Id: I520da912062917e40e5628d003558fe80b612948
Reviewed-by: Maximilian Goldstein <max.goldstein@qt.io>
Update the QQmlJSScope::insertPropertyIdentifier along the way
since it doesn't mark a signal method as a signal
Task-number: QTBUG-84368
Change-Id: I4594520e46e2d85cc7fa82357d9cc1c62c66b732
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
Already during the prototyping phase, conflicts in class names were
encountered within Qt code base. Those could be avoided by namespaces.
Initial qmltc logic was using meaningless "q_qmltc" namespace, so let's
improve that by allowing user-specified namespaces + making Qt's own
QML files (compiled to C++) being available under QT_NAMESPACE. The
latter is achieved by providing (and using) the internal version of a
qmltc-invoking function
Task-number: QTBUG-84368
Task-number: QTBUG-96040
Change-Id: I99cdf1baba8838c093b6b469f6744869f72af093
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
- Finish output ir and the writer for it
- Add simple compiler logic to generate dull class declarations
Task-number: QTBUG-84368
Change-Id: I75be0f44b84ad3cfb1d862072d58b3bf87063d31
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
This is a stub commit that introduces qmltc as a binary
We don't even attempt to generate any code here yet
Task-number: QTBUG-84368
Change-Id: I98da17d839970a2561f501f3b9d6b1e1310e0e01
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>