Commit Graph

23 Commits

Author SHA1 Message Date
Alexandru Croitor
dd1030a450 CMake: Record used package version for each target dependency
When recording which package version to look for in
QtFooModuleDependencies.cmake and other files like it,
instead of using PROJECT_VERSION, use the version of the
package that contains the dependency.

For example if we're hypothetically building the qtdeclarative repo
from the 6.4 branch, against an installed 6.2 qtbase, then
the Qt6QmlModuleDependencies.cmake file will have a
find_package(Qt6Core 6.2) call because qtdeclarative's
find_package(Qt6Core) call found a 6.2 Core when it was configured.

This allows switching the versioning scheme of specific Qt modules
that might not want to follow the general Qt versioning scheme.

The first candidate would be QtWebEngine which might want to
follow the Chromium versioning scheme, something like
Qt 6.94.0 where 94 is the Chromium major version.

Implementation notes.
We now record the package version of a target in a property
called _qt_package_version. We do it for qt modules, plugins,
3rd party libraries, tools and the Platform target.

When we try to look up which version to write into the
QtFooModuleDependencies.cmake file (or the equivalent Plugins and
Tools file), we try to find the version
from a few sources: the property mentioned above, then the
Qt6{target}_VERSION variable, and finally PROJECT_VERSION.
In the latter case, we issue a warning because technically that should
never have to happen, and it's a bug or an unforeseen case if it does.

A few more places also need adjustments:
 - package versions to look for when configuring standalone
   tests and generating standalone tests Config files
 - handling of tools packages
 - The main Qt6 package lookup in each Dependencies.cmake files

Note that there are some requirements and consequences in case a
module wants to use a different versioning scheme like 6.94.0.

Requirements.
 - The root CMakeLists.txt file needs to call find_package with a
   version different from the usual PROJECT_VERSION. Ideally it
   should look for a few different Qt versions which are known to be
   compatible, for example the last stable and LTS versions, or just
   the lowest supported Qt version, e.g. 6.2.6 or whenever this change
   would land in the 6.2 branch.
 - If the repository has multiple modules, some of which need to
   follow the Qt versioning scheme and some not,
   project(VERSION x.y.z) calls need to be carefully placed in
   subdirectory scopes with appropriate version numbers, so that
   qt_internal_add_module / _tool / _plugin pick up the correct
   version.

Consequences.
 - The .so / .dylib names will contain the new version, e.g. .so.6.94
 - Linux ELF symbols will contain the new versions
 - syncqt private headers will now exist under a
   include/QtFoo/6.94.0/QtFoo/private folder
 - pri and prl files will also contain the new version numbers
 - pkg-config .pc files contain the new version numbers
 - It won't be possible to write
   find_package(Qt6 6.94 COMPONENTS WebEngineWidgets) in user code.
   One would have to write find_package(Qt6WebEngineWidgets 6.94)
   otherwise CMake will try to look for Qt6Config 6.94 which won't
   exist.
 - Similarly, a
   find_package(Qt6 6.4 COMPONENTS Widgets WebEngineWidgets) call
   would always find any kind of WebEngine package that is higher than
   6.4, which might be 6.94, 6.95, etc.
 - In the future, if we fix Qt6Config to pass EXACT to its
   subcomponent find_package calls,
   a find_package(Qt6 6.5.0 EXACT COMPONENTS Widgets WebEngineWidgets)
   would fail to find WebEngineWidgets, because its 6.94.0 version
   will not be equal to 6.5.0. Currently we don't pass through EXACT,
   so it's not an issue.

Augments 5ffc744b79

Task-number: QTBUG-103500
Change-Id: I8bdb56bfcbc7f7f6484d1e56651ffc993fd30bab
Reviewed-by: Michal Klocek <michal.klocek@qt.io>
Reviewed-by: Alexey Edelev <alexey.edelev@qt.io>
Reviewed-by: Jörg Bornemann <joerg.bornemann@qt.io>
2022-07-01 10:50:57 +02:00
Li Xinwei
9539c8a7f8 CMake: set correct COMPILE_PDB_NAME for static libraries
Output names of static libraries might be different from target names.
For example, the library name of Qt6::DeviceDiscoverySupportPrivate is
"Qt6DeviceDiscoverySupport.lib", and the library name of
Qt6::QTlsBackendCertOnlyPlugin is "qcertonlybackend.lib".
This commit make pdb files names consistent with the library names.

And make sure we have set correct OUTPUT_NAME property before calling
qt_set_common_target_properties()/qt_internal_set_compile_pdb_names().

Change-Id: Idb3cacd7a46a4f298fd584b927b5d726956faea8
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
2022-05-20 17:41:20 +08:00
Alexandru Croitor
56abd7e4e0 CMake: Fix exclusion of QtFoo in QtBarDepends for 3rd party libs
When configuring a static Qt with the -qt-zlib option and the build
system creates a 3rd party header module QtZlib, syncqt
does not generate a QtZlib header file that would include all its
public headers.

Then when the QtSvgDepends header is generated, it would add an
 #include <QtZlib> which would break compilation of the QtSvg PCH
file (which compiles QtSvgDepends).

We have logic to exclude addition of headers from regular 3rd party
static libraries, but not header only 3rd party libraries.

Adjust the code to handle header-only 3rd party libraries, as well as
make sure it works across repos by exporting the relevant properties.

As a drive-by, also rename and export some other informational
properties.

Amends af00402d64
Amends 6fdeaea24f
Amends be2745e478

Pick-to: 6.2 6.3
Change-Id: I087f50b193dd845e4a5ec906e8851d63122faf80
Reviewed-by: Alexey Edelev <alexey.edelev@qt.io>
2022-02-23 15:17:42 +01:00
Michal Klocek
be2745e478 Install 3rdparty headers for static builds
For static builds we need 3rdparty headers to be installed.
Leaf modules like qtwebengine needs 3rdparty libs and header for
zlib, freetype, harfbuzz, png, jpeg. Without those the Chromium bundled
versions are used, however it might end up badly if qt has already
bundled one.

Introduce new header only modules with additional arguments for
qt_internal_add_module:

 * EXTERNAL_HEADERS to pick exactly which headers are public
 * EXTERNAL_HEADERS_DIR to include whole directory preserving the
   files directory structure

Fix qtsync so it keep directory structure for all non-qt modules when
syncing headers and do not generate warnings for headers files.

Task-number: QTBUG-87154
Task-number: QTBUG-88614
Change-Id: If1c27bf8608791cd4e0a21839d6316a445a96e9f
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
Reviewed-by: Alexey Edelev <alexey.edelev@qt.io>
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
2022-02-19 01:52:32 +01:00
Alexandru Croitor
5ffc744b79 CMake: Allow disabling package version check
When building Qt repos, all find_package(Qt6) calls request a
PROJECT_VERSION version which is set in .cmake.conf via
QT_REPO_MODULE_VERSION.

This means trying to configure qtsvg from a 6.3 branch using a
6.2 qtbase won't work, because qtsvg will call find_package(Qt6 6.3)
and no such Qt6 package version exists.

There are certain scenarios where it might be useful to try to do
that though.
One of them is doing Qt development while locally mixing branches.
Another is building a 6.4 QtWebEngine against a 6.2 Qt.

Allow to opt out of the version check by configuring each Qt repo
with -DQT_NO_PACKAGE_VERSION_CHECK=TRUE. This setting is not
recorded and will have to be set again when configuring another
repo.

The version check will also be disabled by default when configuring
with the -developer-build feature. This will be recorded and embedded
into each ConfigVersion file.

If the version check is disabled, a warning will be shown mentioning
the incompatible version of a package that was found but that package
will still be accepted.
The warning will show both when building Qt or using Qt in a user
project.
The warnings can be disabled by passing
-DQT_NO_PACKAGE_VERSION_INCOMPATIBLE_WARNING=TRUE

Furthermore when building a Qt repo, another warning will show when an
incompatible package version is detected, to suggest to the Qt builder
whether they want to use the incompatible version by disabling the
version check.

Note that there are no compatibility promises when using mixed
non-matching versions. Things might not work. These options are only
provided for convenience and their users know what they are doing.

Pick-to: 6.2
Fixes: QTBUG-96458
Change-Id: I1a42e0b2a00b73513d776d89a76102ffd9136422
Reviewed-by: Craig Scott <craig.scott@qt.io>
2021-10-27 16:41:26 +02:00
Alexandru Croitor
3595613a0a CMake: Don't propagate -fapplication-extension to user projects
Both the compiler and linker -fapplication-extension flag should only
be applied when building Qt's libraries (not executables).

It's up to the user project whether their code will be restricted with
application-extension-only APIs.

In qmake that can be achieved by adding to the qmake project
  CONFIG += app_extension_api_only

In CMake it can be achieved by either adding the compiler and link flags
in the project directly (using target_X_options) or by setting the
appropriate setting in the Xcode project when using the Xcode
generator.

Amends e189126f1a

Pick-to: 6.2
Task-number: QTBUG-95199
Change-Id: Ie7a764d460a89c7650391abff0fcc5abfcabef64
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Joerg Bornemann <joerg.bornemann@qt.io>
2021-07-16 09:52:24 +02:00
Alexey Edelev
f33d11796f Hide QT_USE_BUNDLED_ CACHE variables from GUI
Make QT_USE_BUNDLED_ INTERNAL to hide them from GUI like QtCreator's
CMake configurator.

Pick-to: 6.1 6.2
Change-Id: Id9dcee31c69b579bbe38611cabb98e46550b0e89
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
2021-07-08 23:38:25 +02:00
Alexandru Croitor
c3c8b7083a CMake: Remove some dead installation code
It was copy-pasted (presumably from plugin handling code)
when initially introduced but was never used.

Change-Id: I571738b9f5269ca038f5931a773aa5c2c66aafbc
Reviewed-by: Joerg Bornemann <joerg.bornemann@qt.io>
2021-05-25 22:36:56 +02:00
Alexandru Croitor
1bd408d6f7 CMake: Introduce a public qt_add_library function
Internally it uses a new _qt_internal_add_library function (similar
how we have qt_add_executable and _qt_internal_add_executable) as well
as finalizer code line the executable case.

_qt_internal_add_library forwards arguments to add_library with some
Qt specific adjustments to the selected default target type (based on
whether Qt is configured as static or shared).

The new _qt_internal_add_library is now used in qt_add_plugin as well
as some internal library creating functions like
qt_internal_add_module.

This reduces some duplication of file name adjustments across
functions and creates a central point for creation of Qt-like
libraries (for some definition of Qt-like).

Change-Id: Id9a31fe6bf278c8c3bb1e61e00a9febf7f1a2664
Reviewed-by: Joerg Bornemann <joerg.bornemann@qt.io>
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
2021-05-25 22:36:53 +02:00
Alexey Edelev
ffe5f92546 Add _qt_module_interface_name for 3rdparty libraries
Since we add 3rdparty libraries to the set of the Qt modules, they are
treated as the Qt modules by the depenedcy helper as well. So give them
_qt_module_interface_name to fix dependency helper.

Amends 425ff34aa1

Change-Id: I5898c1c90156de1878aeeef5a0924349b44c50fa
Reviewed-by: Tor Arne Vestbø <tor.arne.vestbo@qt.io>
2021-05-23 16:16:09 +02:00
Alexandru Croitor
91c65dd80c CMake: Build plugin initializers as object libs
Instead of compiling the plugin initializers as part of a user
project, pre-compile them as object libraries while building Qt.

The installed object libraries can then be used with

    target_sources(qt_module INTERFACE $<TARGET_OBJECTS:plugin_init>)

so that they are linked into the final executable or shared library
via qt module usage requirement propagation.

This reduces the build times of user projects.

The link line placement of the object files should be correct for all
linux-y linkers because the only dependency for the object files is
Core and the Gui -> plugin -> Gui -> Core cycle does not hamper that
from empirical observations.

As a consequence of the recent change not to link plugin initialization
object files into static libraries, as well not having to compile the
files in user projects, we can get rid of the
_qt_internal_disable_static_default_plugins calls in various places.

A side note.

Consider a user static library (L) that links to a Qt static library
(Gui) which provides plugins (platform plugins).

If there is an executable (E) that links to (L), with no direct
dependency to any other Qt module and the intention is that the
executable will automatically get the platform plugin linked,
then (L) needs to link PUBLIC-ly to (Gui) so that the plugin usage
requirements are propagated successfully.

This is a limitation of using

  target_sources(qt_module INTERFACE $<TARGET_OBJECTS:plugin_init>)

which will propagate object files across static libraries only if
qt_module is linked publicly.

One could try to use

  target_link_libraries(qt_module
                        INTERFACE $<TARGET_OBJECTS:plugin_init>)

which preserves the linker arguments across static libs even if
qt_module is linked privately, but unfortunately CMake will lose
dependency information on Core, which means the object files might be
placed in the wrong place on the link line.
As far as I know this is a limitation of CMake that can't be worked
around at the moment.

Note this behavior was present before this change as well.

Task-number: QTBUG-80863
Task-number: QTBUG-92933
Change-Id: Ia99e8aa3d32d6197cacd6162515ac808f2c6c53f
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Joerg Bornemann <joerg.bornemann@qt.io>
2021-05-18 22:03:46 +02:00
Craig Scott
aa4a1006cb Refactor qt_internal_add_plugin() and qt6_add_plugin()
Remove code duplication by calling qt6_add_plugin() from
qt_internal_add_plugin().

Separate out the public and internal arguments for the
variables defined in QtBuild.cmake for these functions.
Provide them via commands instead for greater robustness.
This separation allows other Qt repos to access the appropriate
set of keywords where they define commands that forward
on to *_add_plugin() in their implementations. Retain
the old variables for now to simplify the integration
steps for updating other repos. The old variables can
be removed once there are no more references left to
them in any repo.

Task-number: QTBUG-88763
Pick-to: 6.1
Change-Id: I0105523afd95995923bd20fc963d245bbb15d34d
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
2021-03-29 18:10:22 +11:00
Craig Scott
5807e1ae81 Add plugins to Qt tools and executables for static builds
In static builds, we cannot allow any part of the main build to make a
call to find_package(Qt6...) where such a call may load a
Qt6*Plugins.cmake file. That would add additional dependencies to the
main module targets, setting up a circular dependency in the set of
*Config.cmake files which cannot be resolved. This scenario would be
triggered by per-repo builds or user projects.

But Qt's tools and other executables still need to load some plugins
in static builds. Sometimes a platform plugin may be enough, other
times we may want all supportable plugins (e.g. Qt Designer).
Therefore, add all plugins we can identify as relevant for an
executable that is part of the Qt build, but add them directly to the
executable without affecting the linking relationships between the
main module libraries.

Also remove the now unnecessary check for QT_BUILD_PROJECT_NAME in
top level builds because there should be no difference between per-repo
and top level builds any more (as far as linking static plugins is
concerned).

Examples that build as part of the main build will still build
successfully after this change, but they will not run if they require
a platform plugin. Examples need to be moved out to a separate build
where they can call find_package(Qt6) without QT_NO_CREATE_TARGETS
set to TRUE to be runnable (see QTBUG-90820).

Fixes: QTBUG-91915
Pick-to: 6.1
Change-Id: I8088baddb54e394ca111b103313596d6743570ba
Reviewed-by: Joerg Bornemann <joerg.bornemann@qt.io>
2021-03-23 11:15:33 +11:00
Alexey Edelev
dac4d5a492 Clear non-relevant CMake compiler flags
Add internal function to cleanup compiler flags out of the
CMAKE_xxx_FLAGS_xxx variables. Use introduced interface to clear
the '/EHsc' flag for the MSVC compiler family. This adjusts the
CMake behavior to the qmake one.

Change the 'EXCEPTIONS' option handling in helper functions. Add
ability to add enabling and disabling exception flags. Previously
it was only possible to add disabling exception flags.

Fixes: QTBUG-89952
Change-Id: I60d47660a97ae9b5a1d1f4107d352c9e97890144
Reviewed-by: Craig Scott <craig.scott@qt.io>
Reviewed-by: Joerg Bornemann <joerg.bornemann@qt.io>
2021-01-27 20:44:16 +01:00
Alexandru Croitor
b3576164f0 CMake: Disable static plugin imports for non-executable targets
There is no point in generating cpp files containing Q_IMPORT_PLUGIN()
macro calls for non-executable targets like modules, plugins and object
libraries in a static Qt build.
It causes unnecessary compiling of 10+ files for each of those targets.
In a static Qt build, plugin imports should only be done for executables,
tools and applications.

Pick-to: 6.0
Change-Id: Ied90ef2f6d77a61a093d393cfdf94c400284c4f0
Reviewed-by: Craig Scott <craig.scott@qt.io>
Reviewed-by: Joerg Bornemann <joerg.bornemann@qt.io>
2020-12-08 09:13:03 +01:00
Craig Scott
3859f15ec9 CMake: Enable NEW policies by CMake version with a global default
When a CMake release introduces a new policy that affects most Qt
modules, it may be appropriate to make each module aware of that newer
CMake version and use the NEW policy without raising the minimum CMake
version requirement. To reduce the churn associated with making that
change across all Qt modules individually, this change allows it to be
updated in a central place (qtbase), but in a way that allows a Qt
module to override it in its own .cmake.conf file if required (e.g. to
address the issues identified by policy warnings at a later time). The
policies are modified at the start of the call to
qt_build_repo_begin().

For commands defined by the qtbase module, qtbase needs to be in
control of the policy settings at the point where those commands are
defined. The above mechanism should not affect the policy settings for
these commands, so the various *Config.cmake.in files must not specify
policy ranges in a way that a Qt module's .cmake.conf file could
influence.

Starting with CMake 3.12, policies can be specified as a version range
with the cmake_minimum_required() and cmake_policy() commands. All
policies introduced in CMake versions up to the upper limit of that
range will be set to NEW. The actual version of CMake being used only
has to be at least the lower limit of the specified version range.
This change uses cmake_minimum_required() rather than cmake_policy()
due to the latter not halting further processing upon failure.
See the following:

    https://gitlab.kitware.com/cmake/cmake/-/issues/21557

Task-number: QTBUG-88700
Pick-to: 6.0
Change-Id: I0a1f2611dd629f847a18186394f500d7f52753bc
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
2020-12-07 13:22:57 +11:00
Li Xinwei
3ef32ce901 CMake: Don't install pri and debug info for bundled harfbuzz and pcre2
For shared build, Qt6BundledHarfbuzz.lib and Qt6BundledPcre2.lib are not
installed. But their pri files(qt_ext_harfbuzz.pri, qt_ext_pcre2.pri)
and debug info files(Qt6BundledHarfbuzz.pdb, Qt6BundledPcre2.pdb) are
still installed. These files should not be installed too.

Pick-to: 6.0.0 6.0
Change-Id: I3e54bec01d94ee3897b485a982d01b24edc602aa
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
2020-11-20 13:30:29 +00:00
Cristian Adam
68f3e37449 CMake Build: Enable separate debug info for all target types
Now all shared libraries and executables will get .debug files on
the platforms that support FEATURE_separate_debug_info

With the directory property _qt_skip_separate_debug_info certain
targets can retain the debug symbols in the binary e.g. lupdate with
MinGW 8.1.0 will cause objcopy / strip to fail.

Fixes: QTBUG-87015
Change-Id: I03b106e68ef0a42011d1ba641e6f686b2e7b7fb4
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
2020-11-04 01:41:06 +01:00
Tor Arne Vestbø
ba661f6bf1 cmake: Don't limit qt_internal_add_cmake_library to tests
Change-Id: I2dbe8075de6704a7a6557b877dc279a4b4cddd54
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
2020-10-28 00:22:22 +01:00
Alexandru Croitor
e6fd92816d CMake: Install PDB debug info for MSVC builds
Supports installing linker generated debug info for shared libraries
and executables, as well as compiler generated debug info for static
libraries.

Works with Ninja Multi-Config as well, with the caveat that the files
are installed optionally, aka the install rule will not error out if
a pdb file is not present. This is necessary, because it's not
possible to create per-config install rules properly.

Fixes: QTBUG-87006
Change-Id: I95e91a6557eb0ee0f882103be54cd38795c349f7
Reviewed-by: Joerg Bornemann <joerg.bornemann@qt.io>
2020-10-06 10:07:02 +02:00
Joerg Bornemann
893ee16352 CMake: Fix build of Release user projects against RelWithDebInfo Qt
Building a user project in Release configuration against a Qt built with
CMAKE_CONFIGURATION_TYPES=RelWithDebInfo;Debug led to the user project
being linked against the Debug Qt libraries. This is especially painful
with MSVC where debug and release runtimes are incompatible.

We now create *AdditionalTargetInfo.cmake files along the
exported *Targets.cmake files that set the IMPORT_*_<CONFIG> properties
to the values of the release config Qt was built with.

User projects built with an unknown
configuration (CMAKE_BUILD_TYPE=ArbitraryName) will link against a
release Qt. This can be controlled by setting the variable
QT_DEFAULT_IMPORT_CONFIGURATION to, for example, DEBUG in the user
project.

Fixes: QTBUG-86743
Change-Id: I12c4b065a9845c7317f6acddab46b649f2732c9e
Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
2020-09-25 17:02:52 +02:00
Alexandru Croitor
e0c62a48b8 CMake: Rename internal functions to contain qt_internal
Offer compatibility wrapper functions until we update all of the Qt
repos to use the new names.

Task-number: QTBUG-86815
Change-Id: I5826a4116f52a8509db32601ef7c200f9bd331de
Reviewed-by: Joerg Bornemann <joerg.bornemann@qt.io>
Reviewed-by: Kai Koehne <kai.koehne@qt.io>
2020-09-23 16:59:05 +02:00
Alexandru Croitor
44cce1a2ea CMake: Split QtBuild.cmake into smaller files
QtBuild.cmake is huge. Split it.

Move module, plugin, tools, executables and test related functions out
of QtBuild.cmake into separate files.
Do the same for many other things too.

An additional requirement is that all the new Helpers files only
define functions and macros.
No global variable definitions are allowed, nor execution of commands
with side effects.

Some notes:
qt_install_qml_files is removed because it's dead code.

Some functions still need to be figured out, because they are
interspersed and depend on various global state assignments.

Task-number: QTBUG-86035
Change-Id: I21d79ff02eef923c202eb1000422888727cb0e2c
Reviewed-by: Joerg Bornemann <joerg.bornemann@qt.io>
2020-08-14 13:17:11 +02:00