summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--cmake/QtFeature.cmake70
-rwxr-xr-xutil/cmake/configurejson2cmake.py84
-rwxr-xr-xutil/cmake/pro2cmake.py12
3 files changed, 148 insertions, 18 deletions
diff --git a/cmake/QtFeature.cmake b/cmake/QtFeature.cmake
index b957253fea..9e88ceac91 100644
--- a/cmake/QtFeature.cmake
+++ b/cmake/QtFeature.cmake
@@ -641,12 +641,74 @@ function(qt_config_compile_test name)
endif()
cmake_parse_arguments(arg "" "LABEL;PROJECT_PATH;C_STANDARD;CXX_STANDARD"
- "COMPILE_OPTIONS;LIBRARIES;CODE" ${ARGN})
+ "COMPILE_OPTIONS;LIBRARIES;CODE;PACKAGES" ${ARGN})
if(arg_PROJECT_PATH)
message(STATUS "Performing Test ${arg_LABEL}")
+
+ set(flags "")
+ qt_get_platform_try_compile_vars(platform_try_compile_vars)
+ list(APPEND flags ${platform_try_compile_vars})
+
+ # If the repo has its own cmake modules, include those in the module path, so that various
+ # find_package calls work.
+ if(EXISTS "${PROJECT_SOURCE_DIR}/cmake")
+ list(APPEND flags "-DCMAKE_MODULE_PATH:STRING=${PROJECT_SOURCE_DIR}/cmake")
+ endif()
+
+ # Pass which packages need to be found.
+ # Very scary / ugly escaping incoming.
+ if(arg_PACKAGES)
+ set(packages_list "")
+
+ # Parse the package names, version, etc. An example would be:
+ # PACKAGE Foo 6 REQUIRED
+ # PACKAGE Bar 2 COMPONENTS Baz
+ foreach(p ${arg_PACKAGES})
+ if(p STREQUAL PACKAGE)
+ if(package_entry)
+ # Use 6 backslashes + ; which will be collapsed when doing variable
+ # expansion at multiple stages.
+ list(JOIN package_entry "\\\\\\;" package_entry_string)
+ list(APPEND packages_list "${package_entry_string}")
+ endif()
+
+ set(package_entry "")
+ else()
+ list(APPEND package_entry "${p}")
+ endif()
+ endforeach()
+ # Parse final entry.
+ if(package_entry)
+ list(JOIN package_entry "\\\\\\;" package_entry_string)
+ list(APPEND packages_list "${package_entry_string}")
+ endif()
+
+ # Before the join, packages_list has 3 backslashes + ; for each package part
+ # (name, component) if you display them.
+ # After the join, packages_list has 2 backslashes + ; for each package part, and a
+ # '\;' to separate package entries.
+ list(JOIN packages_list "\;" packages_list)
+
+ # Finally when appending the joined string to the flags, the flags are separated by
+ # ';', the package entries by '\;', and the packages parts of an entry by '\\;'.
+ # Example:
+ # WrapFoo\\;6\\;COMPONENTS\\;bar\;WrapBaz\\;5
+ list(APPEND flags "-DQT_CONFIG_COMPILE_TEST_PACKAGES:STRING=${packages_list}")
+
+ # Inside the project, the value of QT_CONFIG_COMPILE_TEST_PACKAGES is used in a foreach
+ # loop that calls find_package() for each package entry, and thus the variable expansion
+ # ends up calling something like find_package(WrapFoo;6;COMPONENTS;bar) aka
+ # find_package(WrapFoo 6 COMPONENTS bar).
+ endif()
+
+ # Pass which libraries need to be linked against.
+ if(arg_LIBRARIES)
+ list(APPEND flags "-DQT_CONFIG_COMPILE_TEST_LIBRARIES:STRING=${arg_LIBRARIES}")
+ endif()
+
try_compile(HAVE_${name} "${CMAKE_BINARY_DIR}/config.tests/${name}" "${arg_PROJECT_PATH}"
- "${name}")
+ "${name}" CMAKE_FLAGS ${flags})
if(${HAVE_${name}})
set(status_label "Success")
@@ -721,6 +783,10 @@ function(qt_get_platform_try_compile_vars out_var)
list(APPEND flags "VCPKG_CHAINLOAD_TOOLCHAIN_FILE")
endif()
+ # Pass language standard flags.
+ list(APPEND flags "CMAKE_C_STANDARD")
+ list(APPEND flags "CMAKE_CXX_STANDARD")
+
# Assemble the list with regular options.
set(flags_cmd_line "")
foreach(flag ${flags})
diff --git a/util/cmake/configurejson2cmake.py b/util/cmake/configurejson2cmake.py
index 5f60e55ca4..11b216dc37 100755
--- a/util/cmake/configurejson2cmake.py
+++ b/util/cmake/configurejson2cmake.py
@@ -499,6 +499,70 @@ def parseInput(ctx, sinput, data, cm_fh):
return
+def get_library_usage_for_compile_test(library):
+ result = {}
+ mapped_library = find_3rd_party_library_mapping(library)
+ if not mapped_library:
+ result["fixme"] = f"# FIXME: use: unmapped library: {library}\n"
+ return result
+
+ if mapped_library.test_library_overwrite:
+ target_name = mapped_library.test_library_overwrite
+ else:
+ target_name = mapped_library.targetName
+ result["target_name"] = target_name
+ result["package_name"] = mapped_library.packageName
+ result["extra"] = mapped_library.extra
+ return result
+
+
+# Handles config.test/foo/foo.pro projects.
+def write_standalone_compile_test(cm_fh, ctx, data, config_test_name, is_library_test):
+ rel_test_project_path = f"{ctx['test_dir']}/{config_test_name}"
+ if posixpath.exists(f"{ctx['project_dir']}/{rel_test_project_path}/CMakeLists.txt"):
+ label = ""
+ libraries = []
+ packages = []
+
+ if "label" in data:
+ label = data["label"]
+
+ if is_library_test and config_test_name in data["libraries"]:
+ if "label" in data["libraries"][config_test_name]:
+ label = data["libraries"][config_test_name]["label"]
+
+ # If a library entry in configure.json has a test, and
+ # the test uses a config.tests standalone project, we
+ # need to get the package and target info for the
+ # library, and pass it to the test so compiling and
+ # linking succeeds.
+ library_usage = get_library_usage_for_compile_test(config_test_name)
+ if "target_name" in library_usage:
+ libraries.append(library_usage["target_name"])
+ if "package_name" in library_usage:
+ find_package_arguments = []
+ find_package_arguments.append(library_usage["package_name"])
+ if "extra" in library_usage:
+ find_package_arguments.extend(library_usage["extra"])
+ package_line = "PACKAGE " + " ".join(find_package_arguments)
+ packages.append(package_line)
+
+ cm_fh.write(
+ f"""
+qt_config_compile_test("{config_test_name}"
+ LABEL "{label}"
+ PROJECT_PATH "${{CMAKE_CURRENT_SOURCE_DIR}}/{rel_test_project_path}"
+"""
+ )
+ if libraries:
+ libraries_string = " ".join(libraries)
+ cm_fh.write(f" LIBRARIES {libraries_string}\n")
+ if packages:
+ packages_string = " ".join(packages)
+ cm_fh.write(f" PACKAGES {packages_string}")
+ cm_fh.write(f")\n")
+
+
def write_compile_test(
ctx, name, details, data, cm_fh, manual_library_list=None, is_library_test=False
):
@@ -514,15 +578,7 @@ def write_compile_test(
print(f" XXXX Failed to locate inherited library test {inherited_test_name}")
if isinstance(details, str):
- rel_test_project_path = f"{ctx['test_dir']}/{details}"
- if posixpath.exists(f"{ctx['project_dir']}/{rel_test_project_path}/CMakeLists.txt"):
- cm_fh.write(
- f"""
-qt_config_compile_test("{details}"
- LABEL "{data['label']}"
- PROJECT_PATH "${{CMAKE_CURRENT_SOURCE_DIR}}/{rel_test_project_path}")
-"""
- )
+ write_standalone_compile_test(cm_fh, ctx, data, details, is_library_test)
return
def resolve_head(detail):
@@ -644,14 +700,12 @@ qt_config_compile_test("{details}"
if len(library) == 0:
continue
- mapped_library = find_3rd_party_library_mapping(library)
- if not mapped_library:
- qmakeFixme += f"# FIXME: use: unmapped library: {library}\n"
+ library_usage = get_library_usage_for_compile_test(library)
+ if "fixme" in library_usage:
+ qmakeFixme += library_usage["fixme"]
continue
- if mapped_library.test_library_overwrite:
- library_list.append(mapped_library.test_library_overwrite)
else:
- library_list.append(mapped_library.targetName)
+ library_list.append(library_usage["target_name"])
cm_fh.write(f"qt_config_compile_test({featureName(name)}\n")
cm_fh.write(lineify("LABEL", data.get("label", "")))
diff --git a/util/cmake/pro2cmake.py b/util/cmake/pro2cmake.py
index e496a2448d..8d1a62ddc9 100755
--- a/util/cmake/pro2cmake.py
+++ b/util/cmake/pro2cmake.py
@@ -3912,7 +3912,17 @@ def handle_config_test_project(scope: Scope, cm_fh: IO[str]):
project_name = os.path.splitext(os.path.basename(scope.file_absolute_path))[0]
content = (
f"cmake_minimum_required(VERSION 3.14.0)\n"
- f"project(config_test_{project_name} LANGUAGES CXX)\n"
+ f"project(config_test_{project_name} LANGUAGES C CXX)\n"
+ """
+foreach(p ${QT_CONFIG_COMPILE_TEST_PACKAGES})
+ find_package(${p})
+endforeach()
+
+if(QT_CONFIG_COMPILE_TEST_LIBRARIES)
+ link_libraries(${QT_CONFIG_COMPILE_TEST_LIBRARIES})
+endif()
+
+"""
)
cm_fh.write(f"{content}\n")