mirror of
https://github.com/Kitware/CMake.git
synced 2026-11-06 13:27:09 +00:00
1 parent
d03678cc5a
commit
c35312e1e7
13 files changed
+131
-1
No files matched your search
@@ -3634,8 +3634,31 @@ Multi-level Expression Evaluation
|
||||
echo $<TARGET_GENEX_EVAL:foo,$<TARGET_PROPERTY:foo,CUSTOM_KEYS>>
|
||||
)
|
||||
|
||||
Support Expressions
|
||||
-------------------
|
||||
|
||||
Conversions
|
||||
^^^^^^^^^^^
|
||||
|
||||
.. genex:: $<ARGS:cmake-list>
|
||||
|
||||
.. versionadded:: 4.5
|
||||
|
||||
Transform a :ref:`semicolon-separated list <CMake Language Lists>` into a
|
||||
comma-separated list as expected by many generator expressions.
|
||||
|
||||
.. code-block:: cmake
|
||||
|
||||
# check if the current config is a debug one
|
||||
|
||||
## Converting a cmake list by hand does not give the expected result
|
||||
$<CONFIG:$<LIST:JOIN,$<GLOBAL_PROPERTY:DEBUG_CONFIGURATIONS>,$<COMMA>>>
|
||||
|
||||
## correct way to proceed
|
||||
$<CONFIG:$<ARGS:$<GLOBAL_PROPERTY:DEBUG_CONFIGURATIONS>>>
|
||||
|
||||
Escaped Characters
|
||||
------------------
|
||||
^^^^^^^^^^^^^^^^^^
|
||||
|
||||
These expressions evaluate to specific string literals. Use them in place of
|
||||
the actual string literal where you need to prevent them from having their
|
||||
|
||||
@@ -0,0 +1,6 @@
|
||||
GenEx-ARGS
|
||||
----------
|
||||
|
||||
* CMake gains the :genex:`$<ARGS>` generator expression to convert a
|
||||
:ref:`semicolon-separated list <CMake Language Lists>` into a comma-separated
|
||||
list.
|
||||
@@ -2,6 +2,11 @@
|
||||
file LICENSE.rst or https://cmake.org/licensing for details. */
|
||||
#include "cmGeneratorExpressionEvaluator.h"
|
||||
|
||||
#include <iterator>
|
||||
|
||||
#include <cm/string_view>
|
||||
#include <cmext/string_view>
|
||||
|
||||
#ifndef CMAKE_BOOTSTRAP
|
||||
# include <cm3p/json/value.h>
|
||||
#endif
|
||||
@@ -111,6 +116,33 @@ std::string GeneratorExpressionContent::Evaluate(
|
||||
return std::string();
|
||||
}
|
||||
|
||||
if (!parameters.empty()) {
|
||||
cm::string_view ARGS_BEGIN = "<ARGS>"_s;
|
||||
cm::string_view ARGS_END = "</ARGS>"_s;
|
||||
|
||||
std::vector<std::string> args;
|
||||
// split any parameter with the prefix <ARGS>:
|
||||
for (auto const& param : parameters) {
|
||||
if (cmHasPrefix(param, ARGS_BEGIN) && cmHasSuffix(param, ARGS_END)) {
|
||||
auto values = param.substr(ARGS_BEGIN.length(),
|
||||
param.length() - ARGS_BEGIN.length() -
|
||||
ARGS_END.length());
|
||||
if (values.empty()) {
|
||||
args.push_back(std::move(values));
|
||||
continue;
|
||||
}
|
||||
|
||||
std::vector<std::string> tokens =
|
||||
cmTokenize(values, ',', cmTokenizerMode::New);
|
||||
args.insert(args.end(), std::make_move_iterator(tokens.begin()),
|
||||
std::make_move_iterator(tokens.end()));
|
||||
} else {
|
||||
args.push_back(param);
|
||||
}
|
||||
}
|
||||
parameters = std::move(args);
|
||||
}
|
||||
|
||||
{
|
||||
#ifndef CMAKE_BOOTSTRAP
|
||||
auto execProfilingRAII =
|
||||
|
||||
@@ -360,6 +360,30 @@ static const struct BoolNode : public cmGeneratorExpressionNode
|
||||
}
|
||||
} boolNode;
|
||||
|
||||
static const struct ArgsNode : public cmGeneratorExpressionNode
|
||||
{
|
||||
ArgsNode() {} // NOLINT(modernize-use-equals-default)
|
||||
|
||||
int NumExpectedParameters() const override { return ZeroOrMoreParameters; }
|
||||
|
||||
std::string Evaluate(std::vector<std::string> const& parameters,
|
||||
cm::GenEx::Evaluation*,
|
||||
GeneratorExpressionContent const*,
|
||||
cmGeneratorExpressionDAGChecker*) const override
|
||||
{
|
||||
if (parameters.empty()) {
|
||||
return std::string{};
|
||||
}
|
||||
if (parameters.size() == 1 && parameters[0].empty()) {
|
||||
return parameters.front();
|
||||
}
|
||||
|
||||
cmList args{ parameters.begin(), parameters.end(),
|
||||
cmList::ExpandElements::Yes, cmList::EmptyElements::Yes };
|
||||
return cmStrCat("<ARGS>", args.join(","_s), "</ARGS>");
|
||||
}
|
||||
} argsNode;
|
||||
|
||||
static const struct IfNode : public cmGeneratorExpressionNode
|
||||
{
|
||||
IfNode() {} // NOLINT(modernize-use-equals-default)
|
||||
@@ -6460,6 +6484,7 @@ cmGeneratorExpressionNode const* cmGeneratorExpressionNode::GetNode(
|
||||
{ "AND", &andNode },
|
||||
{ "OR", &orNode },
|
||||
{ "NOT", ¬Node },
|
||||
{ "ARGS", &argsNode },
|
||||
{ "C_COMPILER_ID", &cCompilerIdNode },
|
||||
{ "CXX_COMPILER_ID", &cxxCompilerIdNode },
|
||||
{ "OBJC_COMPILER_ID", &objcCompilerIdNode },
|
||||
|
||||
@@ -573,6 +573,7 @@ add_RunCMake_test(GenEx-LINK_GROUP)
|
||||
add_RunCMake_test(GenEx-TARGET_FILE -DLINKER_SUPPORTS_PDB=${LINKER_SUPPORTS_PDB})
|
||||
add_RunCMake_test(GenEx-TARGET_IMPORT_FILE)
|
||||
add_RunCMake_test(GenEx-GENEX_EVAL)
|
||||
add_RunCMake_test(GenEx-ARGS)
|
||||
add_RunCMake_test(GenEx-GLOBAL_PROPERTY)
|
||||
add_RunCMake_test(GenEx-RULE_PROPERTY)
|
||||
add_RunCMake_test(GenEx-SOURCE_EXISTS)
|
||||
|
||||
@@ -0,0 +1,5 @@
|
||||
cmake_minimum_required(VERSION 4.0...4.4)
|
||||
|
||||
project(${RunCMake_TEST} NONE)
|
||||
|
||||
include(${RunCMake_TEST}.cmake)
|
||||
@@ -0,0 +1,11 @@
|
||||
|
||||
include(RunCMake)
|
||||
|
||||
run_cmake(no-arguments)
|
||||
run_cmake(list-conversion)
|
||||
|
||||
if(RunCMake_GENERATOR_IS_MULTI_CONFIG)
|
||||
run_cmake_with_options(simple -DCMAKE_CONFIGURATION_TYPES=Debug)
|
||||
else()
|
||||
run_cmake_with_options(simple -DCMAKE_BUILD_TYPE=Debug)
|
||||
endif()
|
||||
@@ -0,0 +1,6 @@
|
||||
file(READ "${RunCMake_TEST_BINARY_DIR}/list-conversion-generated.txt" content)
|
||||
|
||||
set(reference "<ARGS>AA,BB</ARGS>|<ARGS>CC,DD</ARGS>|<ARGS>EE,FF,GG</ARGS>")
|
||||
if(NOT content MATCHES "${reference}")
|
||||
set(RunCMake_TEST_FAILED "actual content:\n [[${content}]]\nbut expected:\n [[${reference}]]")
|
||||
endif()
|
||||
@@ -0,0 +1,6 @@
|
||||
|
||||
set_property(GLOBAL PROPERTY COMMA_LIST "AA,BB")
|
||||
set_property(GLOBAL PROPERTY CMAKE_LIST "CC;DD")
|
||||
set_property(GLOBAL PROPERTY MIX_LIST "EE,FF;GG")
|
||||
|
||||
file(GENERATE OUTPUT list-conversion-generated.txt CONTENT "$<ARGS:$<GLOBAL_PROPERTY:COMMA_LIST>>|$<ARGS:$<GLOBAL_PROPERTY:CMAKE_LIST>>|$<ARGS:$<GLOBAL_PROPERTY:MIX_LIST>>")
|
||||
@@ -0,0 +1,5 @@
|
||||
file(READ "${RunCMake_TEST_BINARY_DIR}/no-arguments-generated.txt" content)
|
||||
|
||||
if(NOT content MATCHES "><|><")
|
||||
set(RunCMake_TEST_FAILED "actual content:\n [[${content}]]\nbut expected:\n [[><|><]]")
|
||||
endif()
|
||||
@@ -0,0 +1,2 @@
|
||||
|
||||
file(GENERATE OUTPUT no-arguments-generated.txt CONTENT ">$<ARGS><|>$<ARGS:><")
|
||||
@@ -0,0 +1,5 @@
|
||||
file(READ "${RunCMake_TEST_BINARY_DIR}/simple-generated.txt" content)
|
||||
|
||||
if(NOT content MATCHES "1")
|
||||
set(RunCMake_TEST_FAILED "actual content:\n [[${content}]]\nbut expected:\n [[1]]")
|
||||
endif()
|
||||
@@ -0,0 +1,3 @@
|
||||
|
||||
set_property(GLOBAL PROPERTY DEBUG_CONGIFURATIONS Debug Other)
|
||||
file(GENERATE OUTPUT simple-generated.txt CONTENT "$<CONFIG:$<ARGS:$<GLOBAL_PROPERTY:DEBUG_CONGIFURATIONS>>>")
|
||||
Reference in new issue
Block a user