mirror of
https://github.com/Kitware/CMake.git
synced 2026-08-09 01:01:12 +00:00
@@ -301,6 +301,7 @@ Properties on Targets
|
|||||||
/prop_tgt/SOVERSION
|
/prop_tgt/SOVERSION
|
||||||
/prop_tgt/STATIC_LIBRARY_FLAGS_CONFIG
|
/prop_tgt/STATIC_LIBRARY_FLAGS_CONFIG
|
||||||
/prop_tgt/STATIC_LIBRARY_FLAGS
|
/prop_tgt/STATIC_LIBRARY_FLAGS
|
||||||
|
/prop_tgt/STATIC_LIBRARY_OPTIONS
|
||||||
/prop_tgt/SUFFIX
|
/prop_tgt/SUFFIX
|
||||||
/prop_tgt/TYPE
|
/prop_tgt/TYPE
|
||||||
/prop_tgt/VERSION
|
/prop_tgt/VERSION
|
||||||
|
|||||||
@@ -3,11 +3,12 @@ LINK_FLAGS
|
|||||||
|
|
||||||
Additional flags to use when linking this target if it is a shared library,
|
Additional flags to use when linking this target if it is a shared library,
|
||||||
module library, or an executable. Static libraries need to use
|
module library, or an executable. Static libraries need to use
|
||||||
:prop_tgt:`STATIC_LIBRARY_FLAGS`.
|
:prop_tgt:`STATIC_LIBRARY_OPTIONS` or :prop_tgt:`STATIC_LIBRARY_FLAGS`
|
||||||
|
properties.
|
||||||
|
|
||||||
The LINK_FLAGS property, managed as a string, can be used to add extra flags
|
The ``LINK_FLAGS`` property, managed as a string, can be used to add extra
|
||||||
to the link step of a target. :prop_tgt:`LINK_FLAGS_<CONFIG>` will add to the
|
flags to the link step of a target. :prop_tgt:`LINK_FLAGS_<CONFIG>` will add
|
||||||
configuration ``<CONFIG>``, for example, ``DEBUG``, ``RELEASE``,
|
to the configuration ``<CONFIG>``, for example, ``DEBUG``, ``RELEASE``,
|
||||||
``MINSIZEREL``, ``RELWITHDEBINFO``, ...
|
``MINSIZEREL``, ``RELWITHDEBINFO``, ...
|
||||||
|
|
||||||
.. note::
|
.. note::
|
||||||
|
|||||||
@@ -1,7 +1,8 @@
|
|||||||
LINK_FLAGS_<CONFIG>
|
LINK_FLAGS_<CONFIG>
|
||||||
-------------------
|
-------------------
|
||||||
|
|
||||||
Per-configuration linker flags for a shared library, module or executable target.
|
Per-configuration linker flags for a shared library, module or executable
|
||||||
|
target.
|
||||||
|
|
||||||
This is the configuration-specific version of :prop_tgt:`LINK_FLAGS`.
|
This is the configuration-specific version of :prop_tgt:`LINK_FLAGS`.
|
||||||
|
|
||||||
|
|||||||
@@ -1,7 +1,10 @@
|
|||||||
LINK_OPTIONS
|
LINK_OPTIONS
|
||||||
------------
|
------------
|
||||||
|
|
||||||
List of options to use when linking this target.
|
List of options to use for the link step of shared library, module
|
||||||
|
and executable targets. Targets that are static libraries need to use
|
||||||
|
the :prop_tgt:`STATIC_LIBRARY_OPTIONS` target property.
|
||||||
|
|
||||||
|
|
||||||
This property holds a :ref:`;-list <CMake Language Lists>` of options
|
This property holds a :ref:`;-list <CMake Language Lists>` of options
|
||||||
specified so far for its target. Use the :command:`target_link_options`
|
specified so far for its target. Use the :command:`target_link_options`
|
||||||
|
|||||||
@@ -2,11 +2,16 @@ STATIC_LIBRARY_FLAGS
|
|||||||
--------------------
|
--------------------
|
||||||
|
|
||||||
Archiver (or MSVC librarian) flags for a static library target.
|
Archiver (or MSVC librarian) flags for a static library target.
|
||||||
Targets that are shared libraries, modules, or executables can use
|
Targets that are shared libraries, modules, or executables need to use
|
||||||
the :prop_tgt:`LINK_OPTIONS` or :prop_tgt:`LINK_FLAGS` target property.
|
the :prop_tgt:`LINK_OPTIONS` or :prop_tgt:`LINK_FLAGS` target properties.
|
||||||
|
|
||||||
The STATIC_LIBRARY_FLAGS property, managed as a string, can be used to add
|
The ``STATIC_LIBRARY_FLAGS`` property, managed as a string, can be used to add
|
||||||
extra flags to the link step of a static library target.
|
extra flags to the link step of a static library target.
|
||||||
:prop_tgt:`STATIC_LIBRARY_FLAGS_<CONFIG>` will add to the configuration
|
:prop_tgt:`STATIC_LIBRARY_FLAGS_<CONFIG>` will add to the configuration
|
||||||
``<CONFIG>``, for example, ``DEBUG``, ``RELEASE``, ``MINSIZEREL``,
|
``<CONFIG>``, for example, ``DEBUG``, ``RELEASE``, ``MINSIZEREL``,
|
||||||
``RELWITHDEBINFO``, ...
|
``RELWITHDEBINFO``, ...
|
||||||
|
|
||||||
|
.. note::
|
||||||
|
|
||||||
|
This property has been superseded by :prop_tgt:`STATIC_LIBRARY_OPTIONS`
|
||||||
|
property.
|
||||||
|
|||||||
@@ -1,6 +1,12 @@
|
|||||||
STATIC_LIBRARY_FLAGS_<CONFIG>
|
STATIC_LIBRARY_FLAGS_<CONFIG>
|
||||||
-----------------------------
|
-----------------------------
|
||||||
|
|
||||||
Per-configuration archiver (or MSVC librarian) flags for a static library target.
|
Per-configuration archiver (or MSVC librarian) flags for a static library
|
||||||
|
target.
|
||||||
|
|
||||||
This is the configuration-specific version of :prop_tgt:`STATIC_LIBRARY_FLAGS`.
|
This is the configuration-specific version of :prop_tgt:`STATIC_LIBRARY_FLAGS`.
|
||||||
|
|
||||||
|
.. note::
|
||||||
|
|
||||||
|
This property has been superseded by :prop_tgt:`STATIC_LIBRARY_OPTIONS`
|
||||||
|
property.
|
||||||
|
|||||||
20
Help/prop_tgt/STATIC_LIBRARY_OPTIONS.rst
Normal file
20
Help/prop_tgt/STATIC_LIBRARY_OPTIONS.rst
Normal file
@@ -0,0 +1,20 @@
|
|||||||
|
STATIC_LIBRARY_OPTIONS
|
||||||
|
----------------------
|
||||||
|
|
||||||
|
Archiver (or MSVC librarian) flags for a static library target.
|
||||||
|
Targets that are shared libraries, modules, or executables need to use
|
||||||
|
the :prop_tgt:`LINK_OPTIONS` target property.
|
||||||
|
|
||||||
|
This property holds a :ref:`;-list <CMake Language Lists>` of options
|
||||||
|
specified so far for its target. Use :command:`set_target_properties` or
|
||||||
|
:command:`set_property` commands to set its content.
|
||||||
|
|
||||||
|
Contents of ``STATIC_LIBRARY_OPTIONS`` may use "generator expressions" with the
|
||||||
|
syntax ``$<...>``. See the :manual:`cmake-generator-expressions(7)` manual
|
||||||
|
for available expressions. See the :manual:`cmake-buildsystem(7)` manual
|
||||||
|
for more on defining buildsystem properties.
|
||||||
|
|
||||||
|
.. note::
|
||||||
|
|
||||||
|
This property must be used in preference to :prop_tgt:`STATIC_LIBRARY_FLAGS`
|
||||||
|
property.
|
||||||
4
Help/release/dev/STATIC_LIBRARY_OPTIONS.rst
Normal file
4
Help/release/dev/STATIC_LIBRARY_OPTIONS.rst
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
STATIC_LIBRARY_OPTIONS
|
||||||
|
----------------------
|
||||||
|
|
||||||
|
* static library targets gained new :prop_tgt:`STATIC_LIBRARY_OPTIONS` property.
|
||||||
@@ -3017,6 +3017,47 @@ void cmGeneratorTarget::GetLinkOptions(std::vector<std::string>& result,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
void processStaticLibraryLinkOptions(
|
||||||
|
cmGeneratorTarget const* tgt,
|
||||||
|
const std::vector<cmGeneratorTarget::TargetPropertyEntry*>& entries,
|
||||||
|
std::vector<std::string>& options,
|
||||||
|
std::unordered_set<std::string>& uniqueOptions,
|
||||||
|
cmGeneratorExpressionDAGChecker* dagChecker, const std::string& config,
|
||||||
|
std::string const& language)
|
||||||
|
{
|
||||||
|
processOptionsInternal(tgt, entries, options, uniqueOptions, dagChecker,
|
||||||
|
config, false, "static library link options",
|
||||||
|
language, OptionsParse::Shell);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void cmGeneratorTarget::GetStaticLibraryLinkOptions(
|
||||||
|
std::vector<std::string>& result, const std::string& config,
|
||||||
|
const std::string& language) const
|
||||||
|
{
|
||||||
|
std::vector<cmGeneratorTarget::TargetPropertyEntry*> entries;
|
||||||
|
std::unordered_set<std::string> uniqueOptions;
|
||||||
|
|
||||||
|
cmGeneratorExpressionDAGChecker dagChecker(
|
||||||
|
this->GetName(), "STATIC_LIBRARY_OPTIONS", nullptr, nullptr);
|
||||||
|
|
||||||
|
if (const char* linkOptions = this->GetProperty("STATIC_LIBRARY_OPTIONS")) {
|
||||||
|
std::vector<std::string> options;
|
||||||
|
cmGeneratorExpression ge;
|
||||||
|
cmSystemTools::ExpandListArgument(linkOptions, options);
|
||||||
|
for (const auto& option : options) {
|
||||||
|
std::unique_ptr<cmCompiledGeneratorExpression> cge = ge.Parse(option);
|
||||||
|
entries.push_back(
|
||||||
|
new cmGeneratorTarget::TargetPropertyEntry(std::move(cge)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
processStaticLibraryLinkOptions(this, entries, result, uniqueOptions,
|
||||||
|
&dagChecker, config, language);
|
||||||
|
|
||||||
|
cmDeleteAll(entries);
|
||||||
|
}
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
void processLinkDepends(
|
void processLinkDepends(
|
||||||
cmGeneratorTarget const* tgt,
|
cmGeneratorTarget const* tgt,
|
||||||
|
|||||||
@@ -424,6 +424,9 @@ public:
|
|||||||
void GetLinkOptions(std::vector<std::string>& result,
|
void GetLinkOptions(std::vector<std::string>& result,
|
||||||
const std::string& config,
|
const std::string& config,
|
||||||
const std::string& language) const;
|
const std::string& language) const;
|
||||||
|
void GetStaticLibraryLinkOptions(std::vector<std::string>& result,
|
||||||
|
const std::string& config,
|
||||||
|
const std::string& language) const;
|
||||||
|
|
||||||
void GetLinkDepends(std::vector<std::string>& result,
|
void GetLinkDepends(std::vector<std::string>& result,
|
||||||
const std::string& config,
|
const std::string& config,
|
||||||
|
|||||||
@@ -1844,7 +1844,7 @@ void cmGlobalXCodeGenerator::CreateBuildSettings(cmGeneratorTarget* gtgt,
|
|||||||
if (gtgt->GetType() == cmStateEnums::OBJECT_LIBRARY ||
|
if (gtgt->GetType() == cmStateEnums::OBJECT_LIBRARY ||
|
||||||
gtgt->GetType() == cmStateEnums::STATIC_LIBRARY) {
|
gtgt->GetType() == cmStateEnums::STATIC_LIBRARY) {
|
||||||
this->CurrentLocalGenerator->GetStaticLibraryFlags(
|
this->CurrentLocalGenerator->GetStaticLibraryFlags(
|
||||||
extraLinkOptions, cmSystemTools::UpperCase(configName), gtgt);
|
extraLinkOptions, cmSystemTools::UpperCase(configName), llang, gtgt);
|
||||||
} else {
|
} else {
|
||||||
const char* targetLinkFlags = gtgt->GetProperty("LINK_FLAGS");
|
const char* targetLinkFlags = gtgt->GetProperty("LINK_FLAGS");
|
||||||
if (targetLinkFlags) {
|
if (targetLinkFlags) {
|
||||||
|
|||||||
@@ -979,6 +979,7 @@ void cmLocalGenerator::GetIncludeDirectories(std::vector<std::string>& dirs,
|
|||||||
|
|
||||||
void cmLocalGenerator::GetStaticLibraryFlags(std::string& flags,
|
void cmLocalGenerator::GetStaticLibraryFlags(std::string& flags,
|
||||||
std::string const& config,
|
std::string const& config,
|
||||||
|
std::string const& linkLanguage,
|
||||||
cmGeneratorTarget* target)
|
cmGeneratorTarget* target)
|
||||||
{
|
{
|
||||||
this->AppendFlags(
|
this->AppendFlags(
|
||||||
@@ -992,6 +993,11 @@ void cmLocalGenerator::GetStaticLibraryFlags(std::string& flags,
|
|||||||
std::string name = "STATIC_LIBRARY_FLAGS_" + config;
|
std::string name = "STATIC_LIBRARY_FLAGS_" + config;
|
||||||
this->AppendFlags(flags, target->GetProperty(name));
|
this->AppendFlags(flags, target->GetProperty(name));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::vector<std::string> options;
|
||||||
|
target->GetStaticLibraryLinkOptions(options, config, linkLanguage);
|
||||||
|
// STATIC_LIBRARY_OPTIONS are escaped.
|
||||||
|
this->AppendCompileOptions(flags, options);
|
||||||
}
|
}
|
||||||
|
|
||||||
void cmLocalGenerator::GetTargetFlags(
|
void cmLocalGenerator::GetTargetFlags(
|
||||||
@@ -1009,7 +1015,7 @@ void cmLocalGenerator::GetTargetFlags(
|
|||||||
|
|
||||||
switch (target->GetType()) {
|
switch (target->GetType()) {
|
||||||
case cmStateEnums::STATIC_LIBRARY:
|
case cmStateEnums::STATIC_LIBRARY:
|
||||||
this->GetStaticLibraryFlags(linkFlags, buildType, target);
|
this->GetStaticLibraryFlags(linkFlags, buildType, linkLanguage, target);
|
||||||
break;
|
break;
|
||||||
case cmStateEnums::MODULE_LIBRARY:
|
case cmStateEnums::MODULE_LIBRARY:
|
||||||
libraryLinkVariable = "CMAKE_MODULE_LINKER_FLAGS";
|
libraryLinkVariable = "CMAKE_MODULE_LINKER_FLAGS";
|
||||||
|
|||||||
@@ -323,6 +323,7 @@ public:
|
|||||||
|
|
||||||
/** Fill out the static linker flags for the given target. */
|
/** Fill out the static linker flags for the given target. */
|
||||||
void GetStaticLibraryFlags(std::string& flags, std::string const& config,
|
void GetStaticLibraryFlags(std::string& flags, std::string const& config,
|
||||||
|
std::string const& linkLanguage,
|
||||||
cmGeneratorTarget* target);
|
cmGeneratorTarget* target);
|
||||||
|
|
||||||
/** Fill out these strings for the given target. Libraries to link,
|
/** Fill out these strings for the given target. Libraries to link,
|
||||||
|
|||||||
@@ -1038,7 +1038,9 @@ void cmLocalVisualStudio7Generator::OutputBuildTool(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
std::string libflags;
|
std::string libflags;
|
||||||
this->GetStaticLibraryFlags(libflags, configTypeUpper, target);
|
this->GetStaticLibraryFlags(libflags, configTypeUpper,
|
||||||
|
target->GetLinkerLanguage(configName),
|
||||||
|
target);
|
||||||
if (!libflags.empty()) {
|
if (!libflags.empty()) {
|
||||||
fout << "\t\t\t\tAdditionalOptions=\"" << libflags << "\"\n";
|
fout << "\t\t\t\tAdditionalOptions=\"" << libflags << "\"\n";
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -148,7 +148,7 @@ void cmMakefileLibraryTargetGenerator::WriteStaticLibraryRules()
|
|||||||
|
|
||||||
std::string extraFlags;
|
std::string extraFlags;
|
||||||
this->LocalGenerator->GetStaticLibraryFlags(
|
this->LocalGenerator->GetStaticLibraryFlags(
|
||||||
extraFlags, cmSystemTools::UpperCase(this->ConfigName),
|
extraFlags, cmSystemTools::UpperCase(this->ConfigName), linkLanguage,
|
||||||
this->GeneratorTarget);
|
this->GeneratorTarget);
|
||||||
this->WriteLibraryRules(linkRuleVar, extraFlags, false);
|
this->WriteLibraryRules(linkRuleVar, extraFlags, false);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3055,9 +3055,14 @@ void cmVisualStudio10TargetGenerator::WriteLibOptions(
|
|||||||
this->GeneratorTarget->GetType() != cmStateEnums::OBJECT_LIBRARY) {
|
this->GeneratorTarget->GetType() != cmStateEnums::OBJECT_LIBRARY) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const std::string& linkLanguage =
|
||||||
|
this->GeneratorTarget->GetLinkClosure(config)->LinkerLanguage;
|
||||||
|
|
||||||
std::string libflags;
|
std::string libflags;
|
||||||
this->LocalGenerator->GetStaticLibraryFlags(
|
this->LocalGenerator->GetStaticLibraryFlags(
|
||||||
libflags, cmSystemTools::UpperCase(config), this->GeneratorTarget);
|
libflags, cmSystemTools::UpperCase(config), linkLanguage,
|
||||||
|
this->GeneratorTarget);
|
||||||
if (!libflags.empty()) {
|
if (!libflags.empty()) {
|
||||||
Elem e2(e1, "Lib");
|
Elem e2(e1, "Lib");
|
||||||
cmGlobalVisualStudio10Generator* gg = this->GlobalGenerator;
|
cmGlobalVisualStudio10Generator* gg = this->GlobalGenerator;
|
||||||
|
|||||||
7
Tests/RunCMake/LinkStatic/LinkOptionsLib.c
Normal file
7
Tests/RunCMake/LinkStatic/LinkOptionsLib.c
Normal file
@@ -0,0 +1,7 @@
|
|||||||
|
#if defined(_WIN32)
|
||||||
|
__declspec(dllexport)
|
||||||
|
#endif
|
||||||
|
int flags_lib(void)
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
@@ -1,3 +1,30 @@
|
|||||||
include(RunCMake)
|
include(RunCMake)
|
||||||
|
|
||||||
run_cmake(LINK_SEARCH_STATIC)
|
run_cmake(LINK_SEARCH_STATIC)
|
||||||
|
|
||||||
|
|
||||||
|
macro(run_cmake_target test subtest target)
|
||||||
|
set(RunCMake_TEST_BINARY_DIR ${RunCMake_BINARY_DIR}/${test}-build)
|
||||||
|
set(RunCMake_TEST_NO_CLEAN 1)
|
||||||
|
run_cmake_command(${test}-${subtest} ${CMAKE_COMMAND} --build . --target ${target} ${ARGN})
|
||||||
|
|
||||||
|
unset(RunCMake_TEST_BINARY_DIR)
|
||||||
|
unset(RunCMake_TEST_NO_CLEAN)
|
||||||
|
endmacro()
|
||||||
|
|
||||||
|
if (NOT CMAKE_C_COMPILER_ID STREQUAL "Intel")
|
||||||
|
# Intel compiler does not reject bad flags or objects!
|
||||||
|
set(RunCMake_TEST_OUTPUT_MERGE TRUE)
|
||||||
|
if (NOT RunCMake_GENERATOR_IS_MULTI_CONFIG)
|
||||||
|
set(RunCMake_TEST_OPTIONS -DCMAKE_BUILD_TYPE=Release)
|
||||||
|
endif()
|
||||||
|
|
||||||
|
run_cmake(STATIC_LIBRARY_OPTIONS)
|
||||||
|
|
||||||
|
run_cmake_target(STATIC_LIBRARY_OPTIONS basic StaticLinkOptions)
|
||||||
|
run_cmake_target(STATIC_LIBRARY_OPTIONS genex StaticLinkOptions_genex --config Release)
|
||||||
|
run_cmake_target(STATIC_LIBRARY_OPTIONS shared SharedLinkOptions)
|
||||||
|
|
||||||
|
unset(RunCMake_TEST_OPTIONS)
|
||||||
|
unset(RunCMake_TEST_OUTPUT_MERGE)
|
||||||
|
endif()
|
||||||
|
|||||||
@@ -0,0 +1,4 @@
|
|||||||
|
|
||||||
|
if (NOT actual_stdout MATCHES "BADFLAG")
|
||||||
|
set (RunCMake_TEST_FAILED "Not found expected 'BADFLAG'.")
|
||||||
|
endif()
|
||||||
@@ -0,0 +1 @@
|
|||||||
|
.*
|
||||||
@@ -0,0 +1,7 @@
|
|||||||
|
|
||||||
|
if (NOT actual_stdout MATCHES "BADFLAG_RELEASE")
|
||||||
|
set (RunCMake_TEST_FAILED "Not found expected 'BADFLAG_RELEASE'.")
|
||||||
|
endif()
|
||||||
|
if (actual_stdout MATCHES "SHELL:")
|
||||||
|
string (APPEND RunCMake_TEST_FAILED "\nFound unexpected prefix 'SHELL:'.")
|
||||||
|
endif()
|
||||||
@@ -0,0 +1 @@
|
|||||||
|
.*
|
||||||
@@ -0,0 +1,4 @@
|
|||||||
|
|
||||||
|
if (actual_stdout MATCHES "BADFLAG")
|
||||||
|
string (APPEND RunCMake_TEST_FAILED "\nFound unexpected flag 'BADFLAG'.")
|
||||||
|
endif()
|
||||||
@@ -0,0 +1 @@
|
|||||||
|
.*
|
||||||
21
Tests/RunCMake/LinkStatic/STATIC_LIBRARY_OPTIONS.cmake
Normal file
21
Tests/RunCMake/LinkStatic/STATIC_LIBRARY_OPTIONS.cmake
Normal file
@@ -0,0 +1,21 @@
|
|||||||
|
|
||||||
|
enable_language(C)
|
||||||
|
|
||||||
|
set(obj "${CMAKE_C_OUTPUT_EXTENSION}")
|
||||||
|
if(BORLAND)
|
||||||
|
set(pre -)
|
||||||
|
endif()
|
||||||
|
|
||||||
|
add_library(StaticLinkOptions STATIC LinkOptionsLib.c)
|
||||||
|
set_property(TARGET StaticLinkOptions PROPERTY STATIC_LIBRARY_OPTIONS ${pre}BADFLAG${obj})
|
||||||
|
|
||||||
|
# static library with generator expression
|
||||||
|
add_library(StaticLinkOptions_genex STATIC LinkOptionsLib.c)
|
||||||
|
set_property(TARGET StaticLinkOptions_genex PROPERTY STATIC_LIBRARY_OPTIONS
|
||||||
|
$<$<CONFIG:Release>:${pre}BADFLAG_RELEASE${obj}>
|
||||||
|
"SHELL:" # produces no options
|
||||||
|
)
|
||||||
|
|
||||||
|
# shared library do not use property STATIC_LIBRARY_OPTIONS
|
||||||
|
add_library(SharedLinkOptions SHARED LinkOptionsLib.c)
|
||||||
|
set_property(TARGET SharedLinkOptions PROPERTY STATIC_LIBRARY_OPTIONS ${pre}BADFLAG${obj})
|
||||||
Reference in New Issue
Block a user