mirror of
https://github.com/Kitware/CMake.git
synced 2026-05-07 06:40:16 -05:00
Genex: Allow TARGET_OBJECTS to be used everywhere
Previously the `TARGET_OBJECTS` generator expression was limited only to use in a buildsystem context so that Xcode's placeholders in object file paths can be evaluated. Lift this restriction so that the expression can at least be used in most settings. Co-Author: Brad King <brad.king@kitware.com>
This commit is contained in:
committed by
Brad King
parent
ac0cf7ff4f
commit
93c89bc75c
@@ -136,6 +136,12 @@ indirectly by using an :ref:`Interface Library <Interface Libraries>`
|
|||||||
whose :prop_tgt:`INTERFACE_SOURCES` target property is set to name
|
whose :prop_tgt:`INTERFACE_SOURCES` target property is set to name
|
||||||
``$<TARGET_OBJECTS:objlib>``.
|
``$<TARGET_OBJECTS:objlib>``.
|
||||||
|
|
||||||
|
Although object libraries may not be used as the ``TARGET``
|
||||||
|
in a use of the :command:`add_custom_command(TARGET)` command signature,
|
||||||
|
the list of objects can be used by :command:`add_custom_command(OUTPUT)` or
|
||||||
|
:command:`file(GENERATE)` by using ``$<TARGET_OBJECTS:objlib>``.
|
||||||
|
|
||||||
|
|
||||||
Build Specification and Usage Requirements
|
Build Specification and Usage Requirements
|
||||||
==========================================
|
==========================================
|
||||||
|
|
||||||
|
|||||||
@@ -290,9 +290,7 @@ Available output expressions are:
|
|||||||
Content of ``...`` converted to a C identifier.
|
Content of ``...`` converted to a C identifier.
|
||||||
``$<TARGET_OBJECTS:objLib>``
|
``$<TARGET_OBJECTS:objLib>``
|
||||||
List of objects resulting from build of ``objLib``. ``objLib`` must be an
|
List of objects resulting from build of ``objLib``. ``objLib`` must be an
|
||||||
object of type ``OBJECT_LIBRARY``. This expression may only be used in
|
object of type ``OBJECT_LIBRARY``.
|
||||||
the sources of :command:`add_library` and :command:`add_executable`
|
|
||||||
commands.
|
|
||||||
``$<SHELL_PATH:...>``
|
``$<SHELL_PATH:...>``
|
||||||
Content of ``...`` converted to shell path style. For example, slashes are
|
Content of ``...`` converted to shell path style. For example, slashes are
|
||||||
converted to backslashes in Windows shells and drive letters are converted
|
converted to backslashes in Windows shells and drive letters are converted
|
||||||
|
|||||||
@@ -0,0 +1,6 @@
|
|||||||
|
add_custom_command-TARGET_OBJECTS
|
||||||
|
---------------------------------
|
||||||
|
|
||||||
|
* The :command:`add_custom_command` command learned to evaluate the
|
||||||
|
``TARGET_OBJECTS``
|
||||||
|
:manual:`generator expression <cmake-generator-expressions(7)>`.
|
||||||
@@ -0,0 +1,6 @@
|
|||||||
|
file-GENERATE-TARGET_OBJECTS
|
||||||
|
----------------------------
|
||||||
|
|
||||||
|
* The :command:`file(GENERATE)` subcommand learned to evaluate the
|
||||||
|
``TARGET_OBJECTS``
|
||||||
|
:manual:`generator expression <cmake-generator-expressions(7)>`.
|
||||||
@@ -64,8 +64,10 @@ void cmGeneratorExpressionEvaluationFile::Generate(
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
std::ostringstream e;
|
std::ostringstream e;
|
||||||
e << "Evaluation file to be written multiple times for different "
|
e << "Evaluation file to be written multiple times with different "
|
||||||
"configurations or languages with different content:\n "
|
"content. "
|
||||||
|
"This is generally caused by the content evaluating the "
|
||||||
|
"configuration type, language, or location of object files:\n "
|
||||||
<< outputFileName;
|
<< outputFileName;
|
||||||
lg->IssueMessage(cmake::FATAL_ERROR, e.str());
|
lg->IssueMessage(cmake::FATAL_ERROR, e.str());
|
||||||
return;
|
return;
|
||||||
|
|||||||
@@ -1243,20 +1243,38 @@ static const struct TargetObjectsNode : public cmGeneratorExpressionNode
|
|||||||
return std::string();
|
return std::string();
|
||||||
}
|
}
|
||||||
if (!context->EvaluateForBuildsystem) {
|
if (!context->EvaluateForBuildsystem) {
|
||||||
std::ostringstream e;
|
cmGlobalGenerator* gg = context->LG->GetGlobalGenerator();
|
||||||
e << "The evaluation of the TARGET_OBJECTS generator expression "
|
std::string reason;
|
||||||
"is only suitable for consumption by CMake. It is not suitable "
|
if (!gg->HasKnownObjectFileLocation(&reason)) {
|
||||||
"for writing out elsewhere.";
|
std::ostringstream e;
|
||||||
reportError(context, content->GetOriginalExpression(), e.str());
|
e << "The evaluation of the TARGET_OBJECTS generator expression "
|
||||||
return std::string();
|
"is only suitable for consumption by CMake (limited"
|
||||||
|
<< reason << "). "
|
||||||
|
"It is not suitable for writing out elsewhere.";
|
||||||
|
reportError(context, content->GetOriginalExpression(), e.str());
|
||||||
|
return std::string();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::string> objects;
|
std::vector<std::string> objects;
|
||||||
gt->GetTargetObjectNames(context->Config, objects);
|
gt->GetTargetObjectNames(context->Config, objects);
|
||||||
|
|
||||||
|
std::string obj_dir;
|
||||||
|
if (context->EvaluateForBuildsystem) {
|
||||||
|
// Use object file directory with buildsystem placeholder.
|
||||||
|
obj_dir = gt->ObjectDirectory;
|
||||||
|
// Here we assume that the set of object files produced
|
||||||
|
// by an object library does not vary with configuration
|
||||||
|
// and do not set HadContextSensitiveCondition to true.
|
||||||
|
} else {
|
||||||
|
// Use object file directory with per-config location.
|
||||||
|
obj_dir = gt->GetObjectDirectory(context->Config);
|
||||||
|
context->HadContextSensitiveCondition = true;
|
||||||
|
}
|
||||||
|
|
||||||
for (std::vector<std::string>::iterator oi = objects.begin();
|
for (std::vector<std::string>::iterator oi = objects.begin();
|
||||||
oi != objects.end(); ++oi) {
|
oi != objects.end(); ++oi) {
|
||||||
*oi = gt->ObjectDirectory + *oi;
|
*oi = obj_dir + *oi;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Create the cmSourceFile instances in the referencing directory.
|
// Create the cmSourceFile instances in the referencing directory.
|
||||||
|
|||||||
@@ -292,3 +292,19 @@ set(CMP0044_TYPE NEW)
|
|||||||
add_subdirectory(CMP0044 ${CMAKE_BINARY_DIR}/CMP0044-NEW)
|
add_subdirectory(CMP0044 ${CMAKE_BINARY_DIR}/CMP0044-NEW)
|
||||||
set(CMP0044_TYPE OLD)
|
set(CMP0044_TYPE OLD)
|
||||||
add_subdirectory(CMP0044 ${CMAKE_BINARY_DIR}/CMP0044-OLD)
|
add_subdirectory(CMP0044 ${CMAKE_BINARY_DIR}/CMP0044-OLD)
|
||||||
|
|
||||||
|
if(NOT CMAKE_GENERATOR STREQUAL Xcode OR NOT CMAKE_OSX_ARCHITECTURES MATCHES "[;$]")
|
||||||
|
add_library(objlib OBJECT objlib1.c objlib2.c)
|
||||||
|
file(GENERATE
|
||||||
|
OUTPUT "${CMAKE_CURRENT_BINARY_DIR}/objlib_files_$<CONFIGURATION>"
|
||||||
|
CONTENT "$<JOIN:$<TARGET_OBJECTS:objlib>,\n>\n"
|
||||||
|
)
|
||||||
|
|
||||||
|
add_custom_target(check_object_files ALL
|
||||||
|
COMMAND ${CMAKE_COMMAND}
|
||||||
|
"-DOBJLIB_LISTFILE=${CMAKE_CURRENT_BINARY_DIR}/objlib_files_$<CONFIGURATION>"
|
||||||
|
-DEXPECTED_NUM_OBJECTFILES=2
|
||||||
|
-P "${CMAKE_CURRENT_SOURCE_DIR}/check_object_files.cmake"
|
||||||
|
DEPENDS objlib
|
||||||
|
)
|
||||||
|
endif()
|
||||||
|
|||||||
@@ -0,0 +1,26 @@
|
|||||||
|
|
||||||
|
if (NOT EXISTS ${OBJLIB_LISTFILE})
|
||||||
|
message(SEND_ERROR "Object listing file \"${OBJLIB_LISTFILE}\" not found!")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
file(STRINGS ${OBJLIB_LISTFILE} objlib_files ENCODING UTF-8)
|
||||||
|
|
||||||
|
list(LENGTH objlib_files num_objectfiles)
|
||||||
|
if (NOT EXPECTED_NUM_OBJECTFILES EQUAL num_objectfiles)
|
||||||
|
message(SEND_ERROR "Unexpected number of entries in object list file (${num_objectfiles} instead of ${EXPECTED_NUM_OBJECTFILES})")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
foreach(objlib_file ${objlib_files})
|
||||||
|
set(file_exists False)
|
||||||
|
if (EXISTS ${objlib_file})
|
||||||
|
set(file_exists True)
|
||||||
|
endif()
|
||||||
|
|
||||||
|
if (NOT file_exists)
|
||||||
|
if(attempts)
|
||||||
|
list(REMOVE_DUPLICATES attempts)
|
||||||
|
set(tried " Tried ${attempts}")
|
||||||
|
endif()
|
||||||
|
message(SEND_ERROR "File \"${objlib_file}\" does not exist!${tried}")
|
||||||
|
endif()
|
||||||
|
endforeach()
|
||||||
@@ -0,0 +1,4 @@
|
|||||||
|
|
||||||
|
void objlib1()
|
||||||
|
{
|
||||||
|
}
|
||||||
@@ -0,0 +1,4 @@
|
|||||||
|
|
||||||
|
void objlib2()
|
||||||
|
{
|
||||||
|
}
|
||||||
@@ -1,5 +1,6 @@
|
|||||||
CMake Error in CMakeLists.txt:
|
CMake Error in CMakeLists.txt:
|
||||||
Evaluation file to be written multiple times for different configurations
|
Evaluation file to be written multiple times with different content. This
|
||||||
or languages with different content:
|
is generally caused by the content evaluating the configuration type,
|
||||||
|
language, or location of object files:
|
||||||
|
|
||||||
.*output.txt
|
.*output.txt
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
|
enable_language(CXX)
|
||||||
|
|
||||||
file(GENERATE
|
file(GENERATE
|
||||||
OUTPUT "${CMAKE_CURRENT_BINARY_DIR}/$<BOOL:$<TARGET_OBJECTS:foo>>somefile.cpp"
|
OUTPUT "${CMAKE_CURRENT_BINARY_DIR}/$<BOOL:$<TARGET_OBJECTS:foo>>somefile.cpp"
|
||||||
|
|||||||
Reference in New Issue
Block a user