From 61aee8c7bdf32dc0851da7ad207a4e54fca3aba7 Mon Sep 17 00:00:00 2001 From: Marc Chevrier Date: Mon, 28 Oct 2024 18:18:43 +0100 Subject: [PATCH] Add support of "LINKER:" prefix for Windows executable creation The following variables now support the LINKER: prefix: * CMAKE__CREATE_WIN32_EXE * CMAKE__CREATE_CONSOLE_EXE --- Source/cmLocalGenerator.cxx | 20 ++++---- .../cmMakefileExecutableTargetGenerator.cxx | 20 ++++---- Tests/RunCMake/CMakeLists.txt | 3 +- .../targets/cxx_exe_cross_emulator.json | 8 +--- .../targets/cxx_exe_cross_emulator_args.json | 8 +--- .../targets/cxx_exe_test_launcher.json | 8 +--- ..._exe_test_launcher_and_cross_emulator.json | 8 +--- ...P0181-NEW-C_CREATE_CONSOLE_EXE-check.cmake | 3 ++ ...MP0181-NEW-C_CREATE_CONSOLE_EXE-result.txt | 1 + ...CMP0181-NEW-C_CREATE_WIN32_EXE-check.cmake | 3 ++ ...-CMP0181-NEW-C_CREATE_WIN32_EXE-result.txt | 1 + ...P0181-OLD-C_CREATE_CONSOLE_EXE-check.cmake | 2 + ...MP0181-OLD-C_CREATE_CONSOLE_EXE-result.txt | 1 + ...CMP0181-OLD-C_CREATE_WIN32_EXE-check.cmake | 2 + ...-CMP0181-OLD-C_CREATE_WIN32_EXE-result.txt | 1 + .../LINKER_expansion4.cmake | 47 +++++++++++++++++++ .../RunCMakeTest.cmake | 8 ++++ 17 files changed, 96 insertions(+), 48 deletions(-) create mode 100644 Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_CONSOLE_EXE-check.cmake create mode 100644 Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_CONSOLE_EXE-result.txt create mode 100644 Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_WIN32_EXE-check.cmake create mode 100644 Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_WIN32_EXE-result.txt create mode 100644 Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_CONSOLE_EXE-check.cmake create mode 100644 Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_CONSOLE_EXE-result.txt create mode 100644 Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_WIN32_EXE-check.cmake create mode 100644 Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_WIN32_EXE-result.txt create mode 100644 Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4.cmake diff --git a/Source/cmLocalGenerator.cxx b/Source/cmLocalGenerator.cxx index 863154cdd9..baede4177c 100644 --- a/Source/cmLocalGenerator.cxx +++ b/Source/cmLocalGenerator.cxx @@ -1604,17 +1604,19 @@ void cmLocalGenerator::GetTargetFlags( } } - std::string exeFlags; - if (target->IsWin32Executable(config)) { - exeFlags += this->Makefile->GetSafeDefinition( - cmStrCat("CMAKE_", linkLanguage, "_CREATE_WIN32_EXE")); - exeFlags += " "; - } else { - exeFlags += this->Makefile->GetSafeDefinition( - cmStrCat("CMAKE_", linkLanguage, "_CREATE_CONSOLE_EXE")); - exeFlags += " "; + { + auto exeType = cmStrCat( + "CMAKE_", linkLanguage, "_CREATE_", + (target->IsWin32Executable(config) ? "WIN32" : "CONSOLE"), "_EXE"); + std::string exeFlags; + this->AppendFlags(exeFlags, this->Makefile->GetDefinition(exeType), + exeType, target, cmBuildStep::Link, linkLanguage); + if (!exeFlags.empty()) { + linkFlags.emplace_back(std::move(exeFlags)); + } } + std::string exeFlags; if (target->IsExecutableWithExports()) { exeFlags += this->Makefile->GetSafeDefinition( cmStrCat("CMAKE_EXE_EXPORTS_", linkLanguage, "_FLAG")); diff --git a/Source/cmMakefileExecutableTargetGenerator.cxx b/Source/cmMakefileExecutableTargetGenerator.cxx index 22e5890fa1..e24f2b75be 100644 --- a/Source/cmMakefileExecutableTargetGenerator.cxx +++ b/Source/cmMakefileExecutableTargetGenerator.cxx @@ -375,17 +375,17 @@ void cmMakefileExecutableTargetGenerator::WriteExecutableRule(bool relink) linkFlags, "CMAKE_EXE_LINKER_FLAGS", this->GeneratorTarget, cmBuildStep::Link, linkLanguage, this->GetConfigName()); - if (this->GeneratorTarget->IsWin32Executable( - this->Makefile->GetSafeDefinition("CMAKE_BUILD_TYPE"))) { + { + auto exeType = + cmStrCat("CMAKE_", linkLanguage, "_CREATE_", + (this->GeneratorTarget->IsWin32Executable( + this->Makefile->GetDefinition("CMAKE_BUILD_TYPE")) + ? "WIN32" + : "CONSOLE"), + "_EXE"); this->LocalGenerator->AppendFlags( - linkFlags, - this->Makefile->GetSafeDefinition( - cmStrCat("CMAKE_", linkLanguage, "_CREATE_WIN32_EXE"))); - } else { - this->LocalGenerator->AppendFlags( - linkFlags, - this->Makefile->GetSafeDefinition( - cmStrCat("CMAKE_", linkLanguage, "_CREATE_CONSOLE_EXE"))); + linkFlags, this->Makefile->GetDefinition(exeType), exeType, + this->GeneratorTarget, cmBuildStep::Link, linkLanguage); } // Add symbol export flags if necessary. diff --git a/Tests/RunCMake/CMakeLists.txt b/Tests/RunCMake/CMakeLists.txt index 5a602553fd..c118be101f 100644 --- a/Tests/RunCMake/CMakeLists.txt +++ b/Tests/RunCMake/CMakeLists.txt @@ -875,7 +875,8 @@ add_RunCMake_test(target_link_libraries-LINK_GROUP -DCMAKE_SYSTEM_NAME=${CMAKE_S -DCMAKE_IMPORT_LIBRARY_PREFIX=${CMAKE_IMPORT_LIBRARY_PREFIX} -DCMAKE_IMPORT_LIBRARY_SUFFIX=${CMAKE_IMPORT_LIBRARY_SUFFIX} -DCMAKE_LINK_LIBRARY_FLAG=${CMAKE_LINK_LIBRARY_FLAG}) -add_RunCMake_test(target_link_libraries-LINKER-prefix -DCMAKE_C_COMPILER_ID=${CMAKE_C_COMPILER_ID} +add_RunCMake_test(target_link_libraries-LINKER-prefix -DCMAKE_SYSTEM_NAME=${CMAKE_SYSTEM_NAME} + -DCMAKE_C_COMPILER_ID=${CMAKE_C_COMPILER_ID} -DCMAKE_C_COMPILER_FRONTEND_VARIANT=${CMAKE_C_COMPILER_FRONTEND_VARIANT}) add_RunCMake_test(add_link_options -DCMAKE_C_COMPILER_ID=${CMAKE_C_COMPILER_ID}) add_RunCMake_test(target_link_options -DCMAKE_C_COMPILER_ID=${CMAKE_C_COMPILER_ID} diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_cross_emulator.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_cross_emulator.json index bbd973b074..a1b15caab1 100644 --- a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_cross_emulator.json +++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_cross_emulator.json @@ -87,13 +87,7 @@ "link": { "language": "CXX", "lto": null, - "commandFragments": [ - { - "fragment" : ".*", - "role" : "flags", - "backtrace": null - } - ] + "commandFragments": null }, "archive": null, "dependencies": [ diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_cross_emulator_args.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_cross_emulator_args.json index c1a8b0c8b1..24a7550ad0 100644 --- a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_cross_emulator_args.json +++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_cross_emulator_args.json @@ -91,13 +91,7 @@ "link": { "language": "CXX", "lto": null, - "commandFragments": [ - { - "fragment" : ".*", - "role" : "flags", - "backtrace": null - } - ] + "commandFragments": null }, "archive": null, "dependencies": [ diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_test_launcher.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_test_launcher.json index 900236883f..f5e365c336 100644 --- a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_test_launcher.json +++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_test_launcher.json @@ -87,13 +87,7 @@ "link": { "language": "CXX", "lto": null, - "commandFragments": [ - { - "fragment" : ".*", - "role" : "flags", - "backtrace": null - } - ] + "commandFragments": null }, "archive": null, "dependencies": [ diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_test_launcher_and_cross_emulator.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_test_launcher_and_cross_emulator.json index 06e7a7bc2f..8facf86aa9 100644 --- a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_test_launcher_and_cross_emulator.json +++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe_test_launcher_and_cross_emulator.json @@ -91,13 +91,7 @@ "link": { "language": "CXX", "lto": null, - "commandFragments": [ - { - "fragment" : ".*", - "role" : "flags", - "backtrace": null - } - ] + "commandFragments": null }, "archive": null, "dependencies": [ diff --git a/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_CONSOLE_EXE-check.cmake b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_CONSOLE_EXE-check.cmake new file mode 100644 index 0000000000..99f5aa3fc2 --- /dev/null +++ b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_CONSOLE_EXE-check.cmake @@ -0,0 +1,3 @@ + +set(reference_file "LINKER.txt") +include ("${CMAKE_CURRENT_LIST_DIR}/LINKER_expansion-validation.cmake") diff --git a/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_CONSOLE_EXE-result.txt b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_CONSOLE_EXE-result.txt new file mode 100644 index 0000000000..8d98f9debd --- /dev/null +++ b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_CONSOLE_EXE-result.txt @@ -0,0 +1 @@ +.* diff --git a/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_WIN32_EXE-check.cmake b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_WIN32_EXE-check.cmake new file mode 100644 index 0000000000..99f5aa3fc2 --- /dev/null +++ b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_WIN32_EXE-check.cmake @@ -0,0 +1,3 @@ + +set(reference_file "LINKER.txt") +include ("${CMAKE_CURRENT_LIST_DIR}/LINKER_expansion-validation.cmake") diff --git a/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_WIN32_EXE-result.txt b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_WIN32_EXE-result.txt new file mode 100644 index 0000000000..8d98f9debd --- /dev/null +++ b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-NEW-C_CREATE_WIN32_EXE-result.txt @@ -0,0 +1 @@ +.* diff --git a/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_CONSOLE_EXE-check.cmake b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_CONSOLE_EXE-check.cmake new file mode 100644 index 0000000000..e0d406f27c --- /dev/null +++ b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_CONSOLE_EXE-check.cmake @@ -0,0 +1,2 @@ + +include ("${CMAKE_CURRENT_LIST_DIR}/LINKER_expansion-CMP0181-OLD-validation.cmake") diff --git a/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_CONSOLE_EXE-result.txt b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_CONSOLE_EXE-result.txt new file mode 100644 index 0000000000..8d98f9debd --- /dev/null +++ b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_CONSOLE_EXE-result.txt @@ -0,0 +1 @@ +.* diff --git a/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_WIN32_EXE-check.cmake b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_WIN32_EXE-check.cmake new file mode 100644 index 0000000000..e0d406f27c --- /dev/null +++ b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_WIN32_EXE-check.cmake @@ -0,0 +1,2 @@ + +include ("${CMAKE_CURRENT_LIST_DIR}/LINKER_expansion-CMP0181-OLD-validation.cmake") diff --git a/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_WIN32_EXE-result.txt b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_WIN32_EXE-result.txt new file mode 100644 index 0000000000..8d98f9debd --- /dev/null +++ b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4-CMP0181-OLD-C_CREATE_WIN32_EXE-result.txt @@ -0,0 +1 @@ +.* diff --git a/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4.cmake b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4.cmake new file mode 100644 index 0000000000..4e88e91ae2 --- /dev/null +++ b/Tests/RunCMake/target_link_libraries-LINKER-prefix/LINKER_expansion4.cmake @@ -0,0 +1,47 @@ + +enable_language(C) + +cmake_policy(SET CMP0181 ${CMP0181}) + +# ensure command line is always displayed and do not use any response file +set(CMAKE_VERBOSE_MAKEFILE TRUE) + +if (CMAKE_GENERATOR MATCHES "Borland|NMake") + string(REPLACE "${CMAKE_START_TEMP_FILE}" "" CMAKE_C_LINK_EXECUTABLE "${CMAKE_C_LINK_EXECUTABLE}") + string(REPLACE "${CMAKE_END_TEMP_FILE}" "" CMAKE_C_LINK_EXECUTABLE "${CMAKE_C_LINK_EXECUTABLE}") +endif() + + +set(CMAKE_C_CREATE_WIN32_EXE "${CMAKE_C_CREATE_WIN32_EXE} LINKER:-foo,bar") +add_executable (c_create_win32_exe WIN32 main.c) + +set(CMAKE_C_CREATE_CONSOLE_EXE "${CMAKE_C_CREATE_CONSOLE_EXE} LINKER:-foo,bar") +add_executable(c_create_console_exe main.c) + + +# generate reference for LINKER flag +if (CMP0181 STREQUAL "NEW") + if (CMAKE_C_LINKER_WRAPPER_FLAG) + set(linker_flag ${CMAKE_C_LINKER_WRAPPER_FLAG}) + list(GET linker_flag -1 linker_space) + if (linker_space STREQUAL " ") + list(REMOVE_AT linker_flag -1) + else() + set(linker_space) + endif() + list (JOIN linker_flag " " linker_flag) + if (CMAKE_C_LINKER_WRAPPER_FLAG_SEP) + set(linker_sep "${CMAKE_C_LINKER_WRAPPER_FLAG_SEP}") + + string (APPEND linker_flag "${linker_space}" "-foo${linker_sep}bar") + else() + set(linker_prefix "${linker_flag}${linker_space}") + + set (linker_flag "${linker_prefix}-foo ${linker_prefix}bar") + endif() + else() + set(linker_flag "-foo bar") + endif() + + file(WRITE "${CMAKE_CURRENT_BINARY_DIR}/LINKER.txt" "${linker_flag}") +endif() diff --git a/Tests/RunCMake/target_link_libraries-LINKER-prefix/RunCMakeTest.cmake b/Tests/RunCMake/target_link_libraries-LINKER-prefix/RunCMakeTest.cmake index fcdf915cb7..5cfd5193db 100644 --- a/Tests/RunCMake/target_link_libraries-LINKER-prefix/RunCMakeTest.cmake +++ b/Tests/RunCMake/target_link_libraries-LINKER-prefix/RunCMakeTest.cmake @@ -46,6 +46,14 @@ if (RunCMake_GENERATOR MATCHES "Makefiles|Ninja|Xcode|Visual Studio" run_cmake_target(LINKER_expansion3-CMP0181-${policy} C_SHARED_CREATE_LINK_FLAGS c_shared_create_link_flags --verbose) run_cmake_target(LINKER_expansion3-CMP0181-${policy} C_MODULE_CREATE_LINK_FLAGS c_module_create_link_flags --verbose) endif() + + if (CMAKE_SYSTEM_NAME MATCHES "Windows") + set(RunCMake_TEST_BINARY_DIR ${RunCMake_BINARY_DIR}/LINKER_expansion4-CMP0181-${policy}-build) + run_cmake_with_options(LINKER_expansion4 -DCMP0181=${policy}) + + run_cmake_target(LINKER_expansion4-CMP0181-${policy} C_CREATE_WIN32_EXE c_create_win32_exe --verbose) + run_cmake_target(LINKER_expansion4-CMP0181-${policy} C_CREATE_CONSOLE_EXE c_create_console_exe --verbose) + endif() endif() endforeach() endif()