diff options
74 files changed, 533 insertions, 142 deletions
diff --git a/Help/command/add_executable.rst b/Help/command/add_executable.rst index c088796..6763620 100644 --- a/Help/command/add_executable.rst +++ b/Help/command/add_executable.rst @@ -7,14 +7,15 @@ Add an executable to the project using the specified source files. add_executable(<name> [WIN32] [MACOSX_BUNDLE] [EXCLUDE_FROM_ALL] - source1 [source2 ...]) + [source1] [source2 ...]) Adds an executable target called ``<name>`` to be built from the source -files listed in the command invocation. The ``<name>`` corresponds to the -logical target name and must be globally unique within a project. The -actual file name of the executable built is constructed based on -conventions of the native platform (such as ``<name>.exe`` or just -``<name>``). +files listed in the command invocation. (The source files can be omitted +here if they are added later using :command:`target_sources`.) The +``<name>`` corresponds to the logical target name and must be globally +unique within a project. The actual file name of the executable built is +constructed based on conventions of the native platform (such as +``<name>.exe`` or just ``<name>``). By default the executable file will be created in the build tree directory corresponding to the source tree directory in which the diff --git a/Help/command/add_library.rst b/Help/command/add_library.rst index de5335e..78b316d 100644 --- a/Help/command/add_library.rst +++ b/Help/command/add_library.rst @@ -14,13 +14,14 @@ Normal Libraries add_library(<name> [STATIC | SHARED | MODULE] [EXCLUDE_FROM_ALL] - source1 [source2 ...]) + [source1] [source2 ...]) Adds a library target called ``<name>`` to be built from the source files -listed in the command invocation. The ``<name>`` corresponds to the -logical target name and must be globally unique within a project. The -actual file name of the library built is constructed based on -conventions of the native platform (such as ``lib<name>.a`` or +listed in the command invocation. (The source files can be omitted here +if they are added later using :command:`target_sources`.) The ``<name>`` +corresponds to the logical target name and must be globally unique within +a project. The actual file name of the library built is constructed based +on conventions of the native platform (such as ``lib<name>.a`` or ``<name>.lib``). ``STATIC``, ``SHARED``, or ``MODULE`` may be given to specify the type of diff --git a/Help/command/cmake_parse_arguments.rst b/Help/command/cmake_parse_arguments.rst index ec4ffed..b334a89 100644 --- a/Help/command/cmake_parse_arguments.rst +++ b/Help/command/cmake_parse_arguments.rst @@ -43,15 +43,18 @@ macro which can be followed by more than one value, like e.g. the ``<multi_value_keywords>``. A warning will be emitted if uniqueness is violated. -When done, ``cmake_parse_arguments`` will have defined for each of the +When done, ``cmake_parse_arguments`` will consider for each of the keywords listed in ``<options>``, ``<one_value_keywords>`` and ``<multi_value_keywords>`` a variable composed of the given ``<prefix>`` followed by ``"_"`` and the name of the respective keyword. These -variables will then hold the respective value from the argument list. -For the ``<options>`` keywords this will be ``TRUE`` or ``FALSE``. +variables will then hold the respective value from the argument list +or be undefined if the associated option could not be found. +For the ``<options>`` keywords, these will always be defined, +to ``TRUE`` or ``FALSE``, whether the option is in the argument list or not. All remaining arguments are collected in a variable -``<prefix>_UNPARSED_ARGUMENTS``, this can be checked afterwards to see +``<prefix>_UNPARSED_ARGUMENTS`` that will be undefined if all argument +where recognized. This can be checked afterwards to see whether your macro was called with unrecognized parameters. As an example here a ``my_install()`` macro, which takes similar arguments @@ -74,16 +77,16 @@ Assume ``my_install()`` has been called like this: my_install(TARGETS foo bar DESTINATION bin OPTIONAL blub) -After the ``cmake_parse_arguments`` call the macro will have set the -following variables:: +After the ``cmake_parse_arguments`` call the macro will have set or undefined +the following variables:: MY_INSTALL_OPTIONAL = TRUE - MY_INSTALL_FAST = FALSE (was not used in call to my_install) + MY_INSTALL_FAST = FALSE # was not used in call to my_install MY_INSTALL_DESTINATION = "bin" - MY_INSTALL_RENAME = "" (was not used) + MY_INSTALL_RENAME <UNDEFINED> # was not used MY_INSTALL_TARGETS = "foo;bar" - MY_INSTALL_CONFIGURATIONS = "" (was not used) - MY_INSTALL_UNPARSED_ARGUMENTS = "blub" (nothing expected after "OPTIONAL") + MY_INSTALL_CONFIGURATIONS <UNDEFINED> # was not used + MY_INSTALL_UNPARSED_ARGUMENTS = "blub" # nothing expected after "OPTIONAL" You can then continue and process these variables. diff --git a/Help/generator/Visual Studio 15 2017.rst b/Help/generator/Visual Studio 15 2017.rst index 2ac0449..2cf1aa0 100644 --- a/Help/generator/Visual Studio 15 2017.rst +++ b/Help/generator/Visual Studio 15 2017.rst @@ -19,13 +19,17 @@ Instance Selection ^^^^^^^^^^^^^^^^^^ VS 2017 supports multiple installations on the same machine. -CMake queries the Visual Studio Installer to locate VS instances. -If more than one instance is installed we do not define which one -is chosen by default. If the ``VS150COMNTOOLS`` environment variable -is set and points to the ``Common7/Tools`` directory within one of -the instances, that instance will be used. The environment variable -must remain consistently set whenever CMake is re-run within a given -build tree. +The :variable:`CMAKE_GENERATOR_INSTANCE` variable may be set as a +cache entry containing the absolute path to a Visual Studio instance. +If the value is not specified explicitly by the user or a toolchain file, +CMake queries the Visual Studio Installer to locate VS instances, chooses +one, and sets the variable as a cache entry to hold the value persistently. + +When CMake first chooses an instance, if the ``VS150COMNTOOLS`` environment +variable is set and points to the ``Common7/Tools`` directory within +one of the instances, that instance will be used. Otherwise, if more +than one instance is installed we do not define which one is chosen +by default. Toolset Selection ^^^^^^^^^^^^^^^^^ diff --git a/Help/manual/cmake-variables.7.rst b/Help/manual/cmake-variables.7.rst index 3880bcf..b37d473 100644 --- a/Help/manual/cmake-variables.7.rst +++ b/Help/manual/cmake-variables.7.rst @@ -42,6 +42,7 @@ Variables that Provide Information /variable/CMAKE_FIND_PACKAGE_SORT_DIRECTION /variable/CMAKE_FIND_PACKAGE_SORT_ORDER /variable/CMAKE_GENERATOR + /variable/CMAKE_GENERATOR_INSTANCE /variable/CMAKE_GENERATOR_PLATFORM /variable/CMAKE_GENERATOR_TOOLSET /variable/CMAKE_HOME_DIRECTORY diff --git a/Help/prop_tgt/CXX_STANDARD.rst b/Help/prop_tgt/CXX_STANDARD.rst index 30a612d..0762033 100644 --- a/Help/prop_tgt/CXX_STANDARD.rst +++ b/Help/prop_tgt/CXX_STANDARD.rst @@ -6,7 +6,8 @@ The C++ standard whose features are requested to build this target. This property specifies the C++ standard whose features are requested to build this target. For some compilers, this results in adding a flag such as ``-std=gnu++11`` to the compile line. For compilers that -have no notion of a standard level, such as MSVC, this has no effect. +have no notion of a standard level, such as Microsoft Visual C++ before +2015 Update 3, this has no effect. Supported values are ``98``, ``11``, ``14``, and ``17``. diff --git a/Help/prop_tgt/C_STANDARD.rst b/Help/prop_tgt/C_STANDARD.rst index 815a686..e7f7904 100644 --- a/Help/prop_tgt/C_STANDARD.rst +++ b/Help/prop_tgt/C_STANDARD.rst @@ -6,7 +6,8 @@ The C standard whose features are requested to build this target. This property specifies the C standard whose features are requested to build this target. For some compilers, this results in adding a flag such as ``-std=gnu11`` to the compile line. For compilers that -have no notion of a standard level, such as MSVC, this has no effect. +have no notion of a standard level, such as Microsoft Visual C++ before +2015 Update 3, this has no effect. Supported values are ``90``, ``99`` and ``11``. diff --git a/Help/release/dev/defer-target-source-check.rst b/Help/release/dev/defer-target-source-check.rst new file mode 100644 index 0000000..65f5488 --- /dev/null +++ b/Help/release/dev/defer-target-source-check.rst @@ -0,0 +1,6 @@ +defer-target-source-check +------------------------- + +* :command:`add_library` and :command:`add_executable` commands can now be + called without any sources and will not complain as long as sources will + be added later via :command:`target_sources`. diff --git a/Help/release/dev/generator-instance.rst b/Help/release/dev/generator-instance.rst new file mode 100644 index 0000000..a3ff658 --- /dev/null +++ b/Help/release/dev/generator-instance.rst @@ -0,0 +1,8 @@ +generator-instance +------------------ + +* A :variable:`CMAKE_GENERATOR_INSTANCE` variable was introduced + to hold the selected instance of the generator's corresponding + native tools if multiple are available. This is used by the + :generator:`Visual Studio 15 2017` generator to hold the + selected instance of Visual Studio persistently. diff --git a/Help/variable/CMAKE_GENERATOR_INSTANCE.rst b/Help/variable/CMAKE_GENERATOR_INSTANCE.rst new file mode 100644 index 0000000..78c81b1 --- /dev/null +++ b/Help/variable/CMAKE_GENERATOR_INSTANCE.rst @@ -0,0 +1,24 @@ +CMAKE_GENERATOR_INSTANCE +------------------------ + +Generator-specific instance specification provided by user. + +Some CMake generators support selection of an instance of the native build +system when multiple instances are available. If the user specifies an +instance (e.g. by setting this cache entry), or after a default instance is +chosen when a build tree is first configured, the value will be available in +this variable. + +The value of this variable should never be modified by project code. +A toolchain file specified by the :variable:`CMAKE_TOOLCHAIN_FILE` +variable may initialize ``CMAKE_GENERATOR_INSTANCE`` as a cache entry. +Once a given build tree has been initialized with a particular value +for this variable, changing the value has undefined behavior. + +Instance specification is supported only on specific generators: + +* For the :generator:`Visual Studio 15 2017` generator (and above) + this specifies the absolute path to the VS installation directory + of the selected VS instance. + +See native build system documentation for allowed instance values. diff --git a/Modules/CheckLanguage.cmake b/Modules/CheckLanguage.cmake index 1ea91d2..70c14d7 100644 --- a/Modules/CheckLanguage.cmake +++ b/Modules/CheckLanguage.cmake @@ -43,11 +43,17 @@ file(WRITE \"\${CMAKE_CURRENT_BINARY_DIR}/result.cmake\" \"set(CMAKE_${lang}_COMPILER \\\"\${CMAKE_${lang}_COMPILER}\\\")\\n\" ) ") + if(CMAKE_GENERATOR_INSTANCE) + set(_D_CMAKE_GENERATOR_INSTANCE "-DCMAKE_GENERATOR_INSTANCE:INTERNAL=${CMAKE_GENERATOR_INSTANCE}") + else() + set(_D_CMAKE_GENERATOR_INSTANCE "") + endif() execute_process( WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/Check${lang} COMMAND ${CMAKE_COMMAND} . -G ${CMAKE_GENERATOR} -A "${CMAKE_GENERATOR_PLATFORM}" -T "${CMAKE_GENERATOR_TOOLSET}" + ${_D_CMAKE_GENERATOR_INSTANCE} OUTPUT_VARIABLE output ERROR_VARIABLE output RESULT_VARIABLE result diff --git a/Modules/ExternalProject.cmake b/Modules/ExternalProject.cmake index 5897e74..67aac4f 100644 --- a/Modules/ExternalProject.cmake +++ b/Modules/ExternalProject.cmake @@ -381,6 +381,11 @@ External Project Definition :variable:`CMAKE_GENERATOR_TOOLSET`). It is an error to provide this option without the ``CMAKE_GENERATOR`` option. + ``CMAKE_GENERATOR_INSTANCE <instance>`` + Pass a generator-specific instance selection to the CMake command (see + :variable:`CMAKE_GENERATOR_INSTANCE`). It is an error to provide this + option without the ``CMAKE_GENERATOR`` option. + ``CMAKE_ARGS <arg>...`` The specified arguments are passed to the ``cmake`` command line. They can be any argument the ``cmake`` command understands, not just cache @@ -2754,6 +2759,7 @@ function(_ep_extract_configure_command var name) endif() get_target_property(cmake_generator ${name} _EP_CMAKE_GENERATOR) + get_target_property(cmake_generator_instance ${name} _EP_CMAKE_GENERATOR_INSTANCE) get_target_property(cmake_generator_platform ${name} _EP_CMAKE_GENERATOR_PLATFORM) get_target_property(cmake_generator_toolset ${name} _EP_CMAKE_GENERATOR_TOOLSET) if(cmake_generator) @@ -2764,6 +2770,9 @@ function(_ep_extract_configure_command var name) if(cmake_generator_toolset) list(APPEND cmd "-T${cmake_generator_toolset}") endif() + if(cmake_generator_instance) + list(APPEND cmd "-DCMAKE_GENERATOR_INSTANCE:INTERNAL=${cmake_generator_instance}") + endif() else() if(CMAKE_EXTRA_GENERATOR) list(APPEND cmd "-G${CMAKE_EXTRA_GENERATOR} - ${CMAKE_GENERATOR}") @@ -2782,6 +2791,12 @@ function(_ep_extract_configure_command var name) if(CMAKE_GENERATOR_TOOLSET) list(APPEND cmd "-T${CMAKE_GENERATOR_TOOLSET}") endif() + if(cmake_generator_instance) + message(FATAL_ERROR "Option CMAKE_GENERATOR_INSTANCE not allowed without CMAKE_GENERATOR.") + endif() + if(CMAKE_GENERATOR_INSTANCE) + list(APPEND cmd "-DCMAKE_GENERATOR_INSTANCE:INTERNAL=${CMAKE_GENERATOR_INSTANCE}") + endif() endif() list(APPEND cmd "<SOURCE_DIR><SOURCE_SUBDIR>") diff --git a/Modules/FindCUDA.cmake b/Modules/FindCUDA.cmake index 1c8ac26..d177e5e 100644 --- a/Modules/FindCUDA.cmake +++ b/Modules/FindCUDA.cmake @@ -18,35 +18,36 @@ # # Tools for building CUDA C files: libraries and build dependencies. # -# This script locates the NVIDIA CUDA C tools. It should work on linux, -# windows, and mac and should be reasonably up to date with CUDA C +# This script locates the NVIDIA CUDA C tools. It should work on Linux, +# Windows, and macOS and should be reasonably up to date with CUDA C # releases. # -# This script makes use of the standard find_package arguments of -# <VERSION>, REQUIRED and QUIET. CUDA_FOUND will report if an +# This script makes use of the standard :command:`find_package` arguments of +# ``<VERSION>``, ``REQUIRED`` and ``QUIET``. ``CUDA_FOUND`` will report if an # acceptable version of CUDA was found. # -# The script will prompt the user to specify CUDA_TOOLKIT_ROOT_DIR if +# The script will prompt the user to specify ``CUDA_TOOLKIT_ROOT_DIR`` if # the prefix cannot be determined by the location of nvcc in the system -# path and REQUIRED is specified to find_package(). To use a different -# installed version of the toolkit set the environment variable -# CUDA_BIN_PATH before running cmake (e.g. -# CUDA_BIN_PATH=/usr/local/cuda1.0 instead of the default -# /usr/local/cuda) or set CUDA_TOOLKIT_ROOT_DIR after configuring. If -# you change the value of CUDA_TOOLKIT_ROOT_DIR, various components that +# path and ``REQUIRED`` is specified to :command:`find_package`. To use +# a different installed version of the toolkit set the environment variable +# ``CUDA_BIN_PATH`` before running cmake (e.g. +# ``CUDA_BIN_PATH=/usr/local/cuda1.0`` instead of the default +# ``/usr/local/cuda``) or set ``CUDA_TOOLKIT_ROOT_DIR`` after configuring. If +# you change the value of ``CUDA_TOOLKIT_ROOT_DIR``, various components that # depend on the path will be relocated. # -# It might be necessary to set CUDA_TOOLKIT_ROOT_DIR manually on certain -# platforms, or to use a cuda runtime not installed in the default -# location. In newer versions of the toolkit the cuda library is -# included with the graphics driver- be sure that the driver version -# matches what is needed by the cuda runtime version. +# It might be necessary to set ``CUDA_TOOLKIT_ROOT_DIR`` manually on certain +# platforms, or to use a CUDA runtime not installed in the default +# location. In newer versions of the toolkit the CUDA library is +# included with the graphics driver -- be sure that the driver version +# matches what is needed by the CUDA runtime version. # # The following variables affect the behavior of the macros in the # script (in alphebetical order). Note that any of these flags can be # changed multiple times in the same directory before calling -# CUDA_ADD_EXECUTABLE, CUDA_ADD_LIBRARY, CUDA_COMPILE, CUDA_COMPILE_PTX, -# CUDA_COMPILE_FATBIN, CUDA_COMPILE_CUBIN or CUDA_WRAP_SRCS:: +# ``CUDA_ADD_EXECUTABLE``, ``CUDA_ADD_LIBRARY``, ``CUDA_COMPILE``, +# ``CUDA_COMPILE_PTX``, ``CUDA_COMPILE_FATBIN``, ``CUDA_COMPILE_CUBIN`` +# or ``CUDA_WRAP_SRCS``:: # # CUDA_64_BIT_DEVICE_CODE (Default matches host bit size) # -- Set to ON to compile for 64 bit device code, OFF for 32 bit device code. diff --git a/Modules/FindMPI.cmake b/Modules/FindMPI.cmake index 578fcd2..7f4c44c 100644 --- a/Modules/FindMPI.cmake +++ b/Modules/FindMPI.cmake @@ -1036,13 +1036,8 @@ set(MPIEXEC_NUMPROC_FLAG "-n" CACHE STRING "Flag used by MPI to specify the num set(MPIEXEC_PREFLAGS "" CACHE STRING "These flags will be directly before the executable that is being run by mpiexec.") set(MPIEXEC_POSTFLAGS "" CACHE STRING "These flags will be placed after all flags passed to mpiexec.") -# Set the number of processes to the processor count and the previous default -# of 2 if that couldn't be determined. -include(${CMAKE_CURRENT_LIST_DIR}/ProcessorCount.cmake) -ProcessorCount(_MPIEXEC_NUMPROCS) -if("${_MPIEXEC_NUMPROCS}" EQUAL "0") - set(_MPIEXEC_NUMPROCS 2) -endif() +# Set the number of processes to the physical processor count +cmake_host_system_information(RESULT _MPIEXEC_NUMPROCS QUERY NUMBER_OF_PHYSICAL_CORES) set(MPIEXEC_MAX_NUMPROCS "${_MPIEXEC_NUMPROCS}" CACHE STRING "Maximum number of processors available to run MPI applications.") unset(_MPIEXEC_NUMPROCS) mark_as_advanced(MPIEXEC_EXECUTABLE MPIEXEC_NUMPROC_FLAG MPIEXEC_PREFLAGS MPIEXEC_POSTFLAGS MPIEXEC_MAX_NUMPROCS) diff --git a/Modules/FindOpenACC.cmake b/Modules/FindOpenACC.cmake index 775cc18..dc8321d 100644 --- a/Modules/FindOpenACC.cmake +++ b/Modules/FindOpenACC.cmake @@ -49,7 +49,9 @@ be returned with OpenACC_<lang>_FLAGS. set(OpenACC_C_CXX_TEST_SOURCE " int main(){ -#ifndef _OPENACC +#ifdef _OPENACC + return 0; +#else breaks_on_purpose #endif } @@ -58,7 +60,9 @@ int main(){ set(OpenACC_Fortran_TEST_SOURCE " program test -#ifndef _OPENACC +#ifdef _OPENACC + return 0; +#else breaks_on_purpose #endif endprogram test @@ -79,6 +83,7 @@ const char accver_str[] = { 'I', 'N', 'F', 'O', ':', 'O', 'p', 'e', 'n', 'A', int main() { puts(accver_str); + return 0; } ") set(OpenACC_Fortran_CHECK_VERSION_SOURCE diff --git a/Modules/FindOpenCL.cmake b/Modules/FindOpenCL.cmake index ba87086..5d79110 100644 --- a/Modules/FindOpenCL.cmake +++ b/Modules/FindOpenCL.cmake @@ -37,7 +37,7 @@ function(_FIND_OPENCL_VERSION) set(CMAKE_REQUIRED_QUIET ${OpenCL_FIND_QUIETLY}) CMAKE_PUSH_CHECK_STATE() - foreach(VERSION "2_0" "1_2" "1_1" "1_0") + foreach(VERSION "2_2" "2_1" "2_0" "1_2" "1_1" "1_0") set(CMAKE_REQUIRED_INCLUDES "${OpenCL_INCLUDE_DIR}") if(APPLE) diff --git a/Modules/FindOpenMP.cmake b/Modules/FindOpenMP.cmake index a39a234..489476b 100644 --- a/Modules/FindOpenMP.cmake +++ b/Modules/FindOpenMP.cmake @@ -123,7 +123,9 @@ set(OpenMP_C_CXX_TEST_SOURCE " #include <omp.h> int main() { -#ifndef _OPENMP +#ifdef _OPENMP + return 0; +#else breaks_on_purpose #endif } @@ -273,6 +275,7 @@ const char ompver_str[] = { 'I', 'N', 'F', 'O', ':', 'O', 'p', 'e', 'n', 'M', int main() { puts(ompver_str); + return 0; } ") diff --git a/Modules/GNUInstallDirs.cmake b/Modules/GNUInstallDirs.cmake index 64bd09e..91361d2 100644 --- a/Modules/GNUInstallDirs.cmake +++ b/Modules/GNUInstallDirs.cmake @@ -123,6 +123,9 @@ # allow users who create additional path variables to also compute # absolute paths where necessary, using the same logic. +cmake_policy(PUSH) +cmake_policy(SET CMP0054 NEW) # if() quoted variables not dereferenced + # Convert a cache variable to PATH type macro(_GNUInstallDirs_cache_convert_to_path var description) @@ -371,3 +374,5 @@ foreach(dir ) GNUInstallDirs_get_absolute_install_dir(CMAKE_INSTALL_FULL_${dir} CMAKE_INSTALL_${dir}) endforeach() + +cmake_policy(POP) diff --git a/Source/CMakeVersion.cmake b/Source/CMakeVersion.cmake index 3c5d10d..306f4c4 100644 --- a/Source/CMakeVersion.cmake +++ b/Source/CMakeVersion.cmake @@ -1,5 +1,5 @@ # CMake version number components. set(CMake_VERSION_MAJOR 3) set(CMake_VERSION_MINOR 10) -set(CMake_VERSION_PATCH 20171023) +set(CMake_VERSION_PATCH 20171025) #set(CMake_VERSION_RC 1) diff --git a/Source/cmAddExecutableCommand.cxx b/Source/cmAddExecutableCommand.cxx index 1d0376f..262e3a1 100644 --- a/Source/cmAddExecutableCommand.cxx +++ b/Source/cmAddExecutableCommand.cxx @@ -18,7 +18,7 @@ class cmExecutionStatus; bool cmAddExecutableCommand::InitialPass(std::vector<std::string> const& args, cmExecutionStatus&) { - if (args.size() < 2) { + if (args.empty()) { this->SetError("called with incorrect number of arguments"); return false; } @@ -191,12 +191,6 @@ bool cmAddExecutableCommand::InitialPass(std::vector<std::string> const& args, } } - if (s == args.end()) { - this->SetError( - "called with incorrect number of arguments, no sources provided"); - return false; - } - std::vector<std::string> srclists(s, args.end()); cmTarget* tgt = this->Makefile->AddExecutable(exename.c_str(), srclists, excludeFromAll); diff --git a/Source/cmAddLibraryCommand.cxx b/Source/cmAddLibraryCommand.cxx index ebf1763..31c2ecf 100644 --- a/Source/cmAddLibraryCommand.cxx +++ b/Source/cmAddLibraryCommand.cxx @@ -362,14 +362,6 @@ bool cmAddLibraryCommand::InitialPass(std::vector<std::string> const& args, return true; } - if (s == args.end()) { - std::string msg = "You have called ADD_LIBRARY for library "; - msg += args[0]; - msg += " without any source files. This typically indicates a problem "; - msg += "with your CMakeLists.txt file"; - cmSystemTools::Message(msg.c_str(), "Warning"); - } - srclists.insert(srclists.end(), s, args.end()); this->Makefile->AddLibrary(libName, type, srclists, excludeFromAll); diff --git a/Source/cmCMakeHostSystemInformationCommand.cxx b/Source/cmCMakeHostSystemInformationCommand.cxx index 5106f52..662dd74 100644 --- a/Source/cmCMakeHostSystemInformationCommand.cxx +++ b/Source/cmCMakeHostSystemInformationCommand.cxx @@ -8,6 +8,9 @@ #include "cmsys/SystemInformation.hxx" #if defined(_WIN32) +#include "cmAlgorithms.h" +#include "cmGlobalGenerator.h" +#include "cmGlobalVisualStudio15Generator.h" #include "cmSystemTools.h" #include "cmVSSetupHelper.h" #define HAVE_VS_SETUP_HELPER @@ -127,6 +130,17 @@ bool cmCMakeHostSystemInformationCommand::GetValue( value = this->ValueToString(info.GetOSPlatform()); #ifdef HAVE_VS_SETUP_HELPER } else if (key == "VS_15_DIR") { + // If generating for the VS 15 IDE, use the same instance. + cmGlobalGenerator* gg = this->Makefile->GetGlobalGenerator(); + if (cmHasLiteralPrefix(gg->GetName(), "Visual Studio 15 ")) { + cmGlobalVisualStudio15Generator* vs15gen = + static_cast<cmGlobalVisualStudio15Generator*>(gg); + if (vs15gen->GetVSInstance(value)) { + return true; + } + } + + // Otherwise, find a VS 15 instance ourselves. cmVSSetupAPIHelper vsSetupAPIHelper; if (vsSetupAPIHelper.GetVSInstanceInfo(value)) { cmSystemTools::ConvertToUnixSlashes(value); diff --git a/Source/cmFilePathChecksum.cxx b/Source/cmFilePathChecksum.cxx index f9afeef..f84360e 100644 --- a/Source/cmFilePathChecksum.cxx +++ b/Source/cmFilePathChecksum.cxx @@ -34,10 +34,10 @@ void cmFilePathChecksum::setupParentDirs(std::string const& currentSrcDir, std::string const& projectSrcDir, std::string const& projectBinDir) { - this->parentDirs[0].first = cmsys::SystemTools::GetRealPath(currentSrcDir); - this->parentDirs[1].first = cmsys::SystemTools::GetRealPath(currentBinDir); - this->parentDirs[2].first = cmsys::SystemTools::GetRealPath(projectSrcDir); - this->parentDirs[3].first = cmsys::SystemTools::GetRealPath(projectBinDir); + this->parentDirs[0].first = cmSystemTools::GetRealPath(currentSrcDir); + this->parentDirs[1].first = cmSystemTools::GetRealPath(currentBinDir); + this->parentDirs[2].first = cmSystemTools::GetRealPath(projectSrcDir); + this->parentDirs[3].first = cmSystemTools::GetRealPath(projectBinDir); this->parentDirs[0].second = "CurrentSource"; this->parentDirs[1].second = "CurrentBinary"; @@ -50,7 +50,7 @@ std::string cmFilePathChecksum::get(std::string const& filePath) const std::string relPath; std::string relSeed; { - std::string const fileReal = cmsys::SystemTools::GetRealPath(filePath); + std::string const fileReal = cmSystemTools::GetRealPath(filePath); std::string parentDir; // Find closest project parent directory for (auto const& pDir : this->parentDirs) { diff --git a/Source/cmGlobalGenerator.cxx b/Source/cmGlobalGenerator.cxx index 38669c9..e0100ce 100644 --- a/Source/cmGlobalGenerator.cxx +++ b/Source/cmGlobalGenerator.cxx @@ -111,6 +111,26 @@ cmGlobalGenerator::~cmGlobalGenerator() delete this->ExtraGenerator; } +bool cmGlobalGenerator::SetGeneratorInstance(std::string const& i, + cmMakefile* mf) +{ + if (i.empty()) { + return true; + } + + std::ostringstream e; + /* clang-format off */ + e << + "Generator\n" + " " << this->GetName() << "\n" + "does not support instance specification, but instance\n" + " " << i << "\n" + "was specified."; + /* clang-format on */ + mf->IssueMessage(cmake::FATAL_ERROR, e.str()); + return false; +} + bool cmGlobalGenerator::SetGeneratorPlatform(std::string const& p, cmMakefile* mf) { @@ -261,6 +281,43 @@ void cmGlobalGenerator::ForceLinkerLanguages() { } +bool cmGlobalGenerator::CheckTargetsForMissingSources() const +{ + bool failed = false; + for (cmLocalGenerator* localGen : this->LocalGenerators) { + const std::vector<cmGeneratorTarget*>& targets = + localGen->GetGeneratorTargets(); + + for (cmGeneratorTarget* target : targets) { + if (target->GetType() == cmStateEnums::TargetType::GLOBAL_TARGET || + target->GetType() == cmStateEnums::TargetType::INTERFACE_LIBRARY || + target->GetType() == cmStateEnums::TargetType::UTILITY) { + continue; + } + + std::vector<std::string> configs; + target->Makefile->GetConfigurations(configs); + std::vector<cmSourceFile*> srcs; + if (configs.empty()) { + target->GetSourceFiles(srcs, ""); + } else { + for (std::vector<std::string>::const_iterator ci = configs.begin(); + ci != configs.end() && srcs.empty(); ++ci) { + target->GetSourceFiles(srcs, *ci); + } + } + if (srcs.empty()) { + std::ostringstream e; + e << "No SOURCES given to target: " << target->GetName(); + this->GetCMakeInstance()->IssueMessage(cmake::FATAL_ERROR, e.str(), + target->GetBacktrace()); + failed = true; + } + } + } + return failed; +} + bool cmGlobalGenerator::IsExportedTargetsFile( const std::string& filename) const { @@ -491,6 +548,13 @@ void cmGlobalGenerator::EnableLanguage( } if (readCMakeSystem) { + // Tell the generator about the instance, if any. + std::string instance = mf->GetSafeDefinition("CMAKE_GENERATOR_INSTANCE"); + if (!this->SetGeneratorInstance(instance, mf)) { + cmSystemTools::SetFatalErrorOccured(); + return; + } + // Find the native build tool for this generator. if (!this->FindMakeProgram(mf)) { return; @@ -1292,6 +1356,11 @@ bool cmGlobalGenerator::Compute() localGen->TraceDependencies(); } + // Make sure that all (non-imported) targets have source files added! + if (this->CheckTargetsForMissingSources()) { + return false; + } + this->ForceLinkerLanguages(); // Compute the manifest of main targets generated. diff --git a/Source/cmGlobalGenerator.h b/Source/cmGlobalGenerator.h index 04e9dc1..c5a5297 100644 --- a/Source/cmGlobalGenerator.h +++ b/Source/cmGlobalGenerator.h @@ -70,6 +70,9 @@ public: /** Tell the generator about the target system. */ virtual bool SetSystemName(std::string const&, cmMakefile*) { return true; } + /** Set the generator-specific instance. Returns true if supported. */ + virtual bool SetGeneratorInstance(std::string const& i, cmMakefile* mf); + /** Set the generator-specific platform name. Returns true if platform is supported and false otherwise. */ virtual bool SetGeneratorPlatform(std::string const& p, cmMakefile* mf); @@ -539,6 +542,8 @@ private: virtual void ForceLinkerLanguages(); + bool CheckTargetsForMissingSources() const; + void CreateLocalGenerators(); void CheckCompilerIdCompatibility(cmMakefile* mf, diff --git a/Source/cmGlobalVisualStudio15Generator.cxx b/Source/cmGlobalVisualStudio15Generator.cxx index d2bf7cc..014d93d 100644 --- a/Source/cmGlobalVisualStudio15Generator.cxx +++ b/Source/cmGlobalVisualStudio15Generator.cxx @@ -111,6 +111,53 @@ void cmGlobalVisualStudio15Generator::WriteSLNHeader(std::ostream& fout) } } +bool cmGlobalVisualStudio15Generator::SetGeneratorInstance( + std::string const& i, cmMakefile* mf) +{ + if (!i.empty()) { + if (!this->vsSetupAPIHelper.SetVSInstance(i)) { + std::ostringstream e; + /* clang-format off */ + e << + "Generator\n" + " " << this->GetName() << "\n" + "could not find specified instance of Visual Studio:\n" + " " << i; + /* clang-format on */ + mf->IssueMessage(cmake::FATAL_ERROR, e.str()); + return false; + } + } + + std::string vsInstance; + if (!this->vsSetupAPIHelper.GetVSInstanceInfo(vsInstance)) { + std::ostringstream e; + /* clang-format off */ + e << + "Generator\n" + " " << this->GetName() << "\n" + "could not find any instance of Visual Studio.\n"; + /* clang-format on */ + mf->IssueMessage(cmake::FATAL_ERROR, e.str()); + return false; + } + + // Save the selected instance persistently. + std::string genInstance = mf->GetSafeDefinition("CMAKE_GENERATOR_INSTANCE"); + if (vsInstance != genInstance) { + this->CMakeInstance->AddCacheEntry( + "CMAKE_GENERATOR_INSTANCE", vsInstance.c_str(), + "Generator instance identifier.", cmStateEnums::INTERNAL); + } + + return true; +} + +bool cmGlobalVisualStudio15Generator::GetVSInstance(std::string& dir) const +{ + return vsSetupAPIHelper.GetVSInstanceInfo(dir); +} + bool cmGlobalVisualStudio15Generator::InitializeWindows(cmMakefile* mf) { // If the Win 8.1 SDK is installed then we can select a SDK matching diff --git a/Source/cmGlobalVisualStudio15Generator.h b/Source/cmGlobalVisualStudio15Generator.h index e934882..852a4e7 100644 --- a/Source/cmGlobalVisualStudio15Generator.h +++ b/Source/cmGlobalVisualStudio15Generator.h @@ -27,6 +27,11 @@ public: virtual void WriteSLNHeader(std::ostream& fout); virtual const char* GetToolsVersion() { return "15.0"; } + + bool SetGeneratorInstance(std::string const& i, cmMakefile* mf) override; + + bool GetVSInstance(std::string& dir) const; + protected: bool InitializeWindows(cmMakefile* mf) override; virtual bool SelectWindowsStoreToolset(std::string& toolset) const; diff --git a/Source/cmMakefile.cxx b/Source/cmMakefile.cxx index 5643c97..b2641d2 100644 --- a/Source/cmMakefile.cxx +++ b/Source/cmMakefile.cxx @@ -3186,6 +3186,7 @@ int cmMakefile::TryCompile(const std::string& srcdir, // do a configure cm.SetHomeDirectory(srcdir); cm.SetHomeOutputDirectory(bindir); + cm.SetGeneratorInstance(this->GetSafeDefinition("CMAKE_GENERATOR_INSTANCE")); cm.SetGeneratorPlatform(this->GetSafeDefinition("CMAKE_GENERATOR_PLATFORM")); cm.SetGeneratorToolset(this->GetSafeDefinition("CMAKE_GENERATOR_TOOLSET")); cm.LoadCache(); diff --git a/Source/cmSystemTools.cxx b/Source/cmSystemTools.cxx index 63c1452..5d1f5f7 100644 --- a/Source/cmSystemTools.cxx +++ b/Source/cmSystemTools.cxx @@ -50,6 +50,8 @@ #include <windows.h> // include wincrypt.h after windows.h #include <wincrypt.h> + +#include "cm_uv.h" #else #include <sys/time.h> #include <unistd.h> @@ -943,6 +945,39 @@ cmSystemTools::WindowsFileRetry cmSystemTools::GetWindowsFileRetry() } return retry; } + +std::string cmSystemTools::GetRealPath(const std::string& path, + std::string* errorMessage) +{ + // uv_fs_realpath uses Windows Vista API so fallback to kwsys if not found + std::string resolved_path; + uv_fs_t req; + int err = uv_fs_realpath(NULL, &req, path.c_str(), NULL); + if (!err) { + resolved_path = std::string((char*)req.ptr); + cmSystemTools::ConvertToUnixSlashes(resolved_path); + // Normalize to upper-case drive letter as GetActualCaseForPath does. + if (resolved_path.size() > 1 && resolved_path[1] == ':') { + resolved_path[0] = toupper(resolved_path[0]); + } + } else if (err == UV_ENOSYS) { + resolved_path = cmsys::SystemTools::GetRealPath(path, errorMessage); + } else if (errorMessage) { + LPSTR message = NULL; + DWORD size = FormatMessageA( + FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | + FORMAT_MESSAGE_IGNORE_INSERTS, + NULL, err, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPSTR)&message, 0, + NULL); + *errorMessage = std::string(message, size); + LocalFree(message); + + resolved_path = ""; + } else { + resolved_path = path; + } + return resolved_path; +} #endif bool cmSystemTools::RenameFile(const char* oldname, const char* newname) diff --git a/Source/cmSystemTools.h b/Source/cmSystemTools.h index e7082e6..2646df9 100644 --- a/Source/cmSystemTools.h +++ b/Source/cmSystemTools.h @@ -497,6 +497,10 @@ public: unsigned int Delay; }; static WindowsFileRetry GetWindowsFileRetry(); + + /** Get the real path for a given path, removing all symlinks. */ + static std::string GetRealPath(const std::string& path, + std::string* errorMessage = 0); #endif private: static bool s_ForceUnixPaths; diff --git a/Source/cmTimestamp.cxx b/Source/cmTimestamp.cxx index 9fb79d9..e747adb 100644 --- a/Source/cmTimestamp.cxx +++ b/Source/cmTimestamp.cxx @@ -33,11 +33,13 @@ std::string cmTimestamp::FileModificationTime(const char* path, const std::string& formatString, bool utcFlag) { - if (!cmsys::SystemTools::FileExists(path)) { + std::string real_path = cmSystemTools::GetRealPath(path); + + if (!cmsys::SystemTools::FileExists(real_path)) { return std::string(); } - time_t mtime = cmsys::SystemTools::ModifiedTime(path); + time_t mtime = cmsys::SystemTools::ModifiedTime(real_path); return CreateTimestampFromTimeT(mtime, formatString, utcFlag); } diff --git a/Source/cmVSSetupHelper.cxx b/Source/cmVSSetupHelper.cxx index ea13649..c2f8deb 100644 --- a/Source/cmVSSetupHelper.cxx +++ b/Source/cmVSSetupHelper.cxx @@ -80,6 +80,14 @@ cmVSSetupAPIHelper::~cmVSSetupAPIHelper() CoUninitialize(); } +bool cmVSSetupAPIHelper::SetVSInstance(std::string const& vsInstallLocation) +{ + this->SpecifiedVSInstallLocation = vsInstallLocation; + cmSystemTools::ConvertToUnixSlashes(this->SpecifiedVSInstallLocation); + chosenInstanceInfo = VSInstanceInfo(); + return this->EnumerateAndChooseVSInstance(); +} + bool cmVSSetupAPIHelper::IsVS2017Installed() { return this->EnumerateAndChooseVSInstance(); @@ -265,13 +273,6 @@ bool cmVSSetupAPIHelper::EnumerateAndChooseVSInstance() if (cmSystemTools::GetEnv("VS150COMNTOOLS", envVSCommonToolsDir)) { cmSystemTools::ConvertToUnixSlashes(envVSCommonToolsDir); } - // FIXME: If the environment variable value changes between runs - // of CMake within a given build tree the results are not defined. - // Instead we should save a CMAKE_GENERATOR_INSTANCE value in the cache - // (similar to CMAKE_GENERATOR_TOOLSET) to hold it persistently. - // Unfortunately doing so will require refactoring elsewhere in - // order to make sure the value is available in time to create - // the generator. std::vector<VSInstanceInfo> vecVSInstances; SmartCOMPtr<IEnumSetupInstances> enumInstances = NULL; @@ -296,16 +297,29 @@ bool cmVSSetupAPIHelper::EnumerateAndChooseVSInstance() instance = instance2 = NULL; if (isInstalled) { - if (!envVSCommonToolsDir.empty()) { + if (!this->SpecifiedVSInstallLocation.empty()) { + // We are looking for a specific instance. std::string currentVSLocation = instanceInfo.GetInstallLocation(); - currentVSLocation += "/Common7/Tools"; if (cmSystemTools::ComparePath(currentVSLocation, - envVSCommonToolsDir)) { + this->SpecifiedVSInstallLocation)) { chosenInstanceInfo = instanceInfo; return true; } + } else { + // We are not looking for a specific instance. + // If we've been given a hint then use it. + if (!envVSCommonToolsDir.empty()) { + std::string currentVSLocation = instanceInfo.GetInstallLocation(); + currentVSLocation += "/Common7/Tools"; + if (cmSystemTools::ComparePath(currentVSLocation, + envVSCommonToolsDir)) { + chosenInstanceInfo = instanceInfo; + return true; + } + } + // Otherwise, add this to the list of candidates. + vecVSInstances.push_back(instanceInfo); } - vecVSInstances.push_back(instanceInfo); } } diff --git a/Source/cmVSSetupHelper.h b/Source/cmVSSetupHelper.h index 74a7ec0..c07cfaf 100644 --- a/Source/cmVSSetupHelper.h +++ b/Source/cmVSSetupHelper.h @@ -126,6 +126,8 @@ public: cmVSSetupAPIHelper(); ~cmVSSetupAPIHelper(); + bool SetVSInstance(std::string const& vsInstallLocation); + bool IsVS2017Installed(); bool GetVSInstanceInfo(std::string& vsInstallLocation); bool IsWin10SDKInstalled(); @@ -150,6 +152,8 @@ private: HRESULT comInitialized; // current best instance of VS selected VSInstanceInfo chosenInstanceInfo; + + std::string SpecifiedVSInstallLocation; }; #endif diff --git a/Source/cmake.cxx b/Source/cmake.cxx index d7ed772..cd714c6 100644 --- a/Source/cmake.cxx +++ b/Source/cmake.cxx @@ -1326,6 +1326,25 @@ int cmake::ActualConfigure() cmStateEnums::INTERNAL); } + if (const char* instance = + this->State->GetInitializedCacheValue("CMAKE_GENERATOR_INSTANCE")) { + if (!this->GeneratorInstance.empty() && + this->GeneratorInstance != instance) { + std::string message = "Error: generator instance: "; + message += this->GeneratorInstance; + message += "\nDoes not match the instance used previously: "; + message += instance; + message += "\nEither remove the CMakeCache.txt file and CMakeFiles " + "directory or choose a different binary directory."; + cmSystemTools::Error(message.c_str()); + return -2; + } + } else { + this->AddCacheEntry( + "CMAKE_GENERATOR_INSTANCE", this->GeneratorInstance.c_str(), + "Generator instance identifier.", cmStateEnums::INTERNAL); + } + if (const char* platformName = this->State->GetInitializedCacheValue("CMAKE_GENERATOR_PLATFORM")) { if (!this->GeneratorPlatform.empty() && @@ -2360,6 +2379,14 @@ int cmake::Build(const std::string& dir, const std::string& target, << "\"\n"; return 1; } + const char* cachedGeneratorInstance = + this->State->GetCacheEntryValue("CMAKE_GENERATOR_INSTANCE"); + if (cachedGeneratorInstance) { + cmMakefile mf(gen.get(), this->GetCurrentSnapshot()); + if (!gen->SetGeneratorInstance(cachedGeneratorInstance, &mf)) { + return 1; + } + } std::string output; std::string projName; const char* cachedProjectName = diff --git a/Source/cmake.h b/Source/cmake.h index ed3ebe0..5c5a90d 100644 --- a/Source/cmake.h +++ b/Source/cmake.h @@ -203,6 +203,12 @@ public: ///! Get the names of the current registered generators void GetRegisteredGenerators(std::vector<GeneratorInfo>& generators) const; + ///! Set the name of the selected generator-specific instance. + void SetGeneratorInstance(std::string const& instance) + { + this->GeneratorInstance = instance; + } + ///! Set the name of the selected generator-specific platform. void SetGeneratorPlatform(std::string const& ts) { @@ -431,6 +437,7 @@ protected: cmGlobalGenerator* GlobalGenerator; std::map<std::string, DiagLevel> DiagLevels; + std::string GeneratorInstance; std::string GeneratorPlatform; std::string GeneratorToolset; diff --git a/Tests/RunCMake/CMakeLists.txt b/Tests/RunCMake/CMakeLists.txt index 7eafa06..b70aeb9 100644 --- a/Tests/RunCMake/CMakeLists.txt +++ b/Tests/RunCMake/CMakeLists.txt @@ -15,6 +15,7 @@ macro(add_RunCMake_test test) add_test(NAME RunCMake.${test} COMMAND ${CMAKE_CMAKE_COMMAND} -DCMAKE_MODULE_PATH=${CMAKE_CURRENT_SOURCE_DIR} -DRunCMake_GENERATOR=${CMAKE_GENERATOR} + -DRunCMake_GENERATOR_INSTANCE=${CMAKE_GENERATOR_INSTANCE} -DRunCMake_GENERATOR_PLATFORM=${CMAKE_GENERATOR_PLATFORM} -DRunCMake_GENERATOR_TOOLSET=${CMAKE_GENERATOR_TOOLSET} -DRunCMake_MAKE_PROGRAM=${CMake_TEST_EXPLICIT_MAKE_PROGRAM} @@ -47,6 +48,7 @@ function(add_RunCMake_test_group test types) -DTEST_TYPE=${type} -DCMAKE_MODULE_PATH=${CMAKE_CURRENT_SOURCE_DIR} -DRunCMake_GENERATOR=${CMAKE_GENERATOR} + -DRunCMake_GENERATOR_INSTANCE=${CMAKE_GENERATOR_INSTANCE} -DRunCMake_GENERATOR_PLATFORM=${CMAKE_GENERATOR_PLATFORM} -DRunCMake_GENERATOR_TOOLSET=${CMAKE_GENERATOR_TOOLSET} -DRunCMake_MAKE_PROGRAM=${CMake_TEST_EXPLICIT_MAKE_PROGRAM} @@ -146,6 +148,7 @@ if(NOT CMAKE_C_COMPILER_ID MATCHES "Watcom") add_RunCMake_test(GenerateExportHeader) endif() add_RunCMake_test(GeneratorExpression) +add_RunCMake_test(GeneratorInstance) add_RunCMake_test(GeneratorPlatform) add_RunCMake_test(GeneratorToolset) add_RunCMake_test(GetPrerequisites) diff --git a/Tests/RunCMake/add_executable/OnlyObjectSources-result.txt b/Tests/RunCMake/GeneratorInstance/BadInstance-result.txt index d00491f..d00491f 100644 --- a/Tests/RunCMake/add_executable/OnlyObjectSources-result.txt +++ b/Tests/RunCMake/GeneratorInstance/BadInstance-result.txt diff --git a/Tests/RunCMake/GeneratorInstance/BadInstance-stderr.txt b/Tests/RunCMake/GeneratorInstance/BadInstance-stderr.txt new file mode 100644 index 0000000..5d01c4f --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/BadInstance-stderr.txt @@ -0,0 +1,10 @@ +CMake Error at CMakeLists.txt:[0-9]+ \(project\): + Generator + + .* + + does not support instance specification, but instance + + Bad Instance + + was specified.$ diff --git a/Tests/RunCMake/GeneratorInstance/BadInstance-toolchain.cmake b/Tests/RunCMake/GeneratorInstance/BadInstance-toolchain.cmake new file mode 100644 index 0000000..1d99259 --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/BadInstance-toolchain.cmake @@ -0,0 +1 @@ +set(CMAKE_GENERATOR_INSTANCE "Bad Instance") diff --git a/Tests/RunCMake/GeneratorInstance/BadInstance.cmake b/Tests/RunCMake/GeneratorInstance/BadInstance.cmake new file mode 100644 index 0000000..2fc38e5 --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/BadInstance.cmake @@ -0,0 +1 @@ +message(FATAL_ERROR "This should not be reached!") diff --git a/Tests/RunCMake/GeneratorInstance/BadInstanceToolchain-result.txt b/Tests/RunCMake/GeneratorInstance/BadInstanceToolchain-result.txt new file mode 100644 index 0000000..d00491f --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/BadInstanceToolchain-result.txt @@ -0,0 +1 @@ +1 diff --git a/Tests/RunCMake/GeneratorInstance/BadInstanceToolchain-stderr.txt b/Tests/RunCMake/GeneratorInstance/BadInstanceToolchain-stderr.txt new file mode 100644 index 0000000..5d01c4f --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/BadInstanceToolchain-stderr.txt @@ -0,0 +1,10 @@ +CMake Error at CMakeLists.txt:[0-9]+ \(project\): + Generator + + .* + + does not support instance specification, but instance + + Bad Instance + + was specified.$ diff --git a/Tests/RunCMake/GeneratorInstance/BadInstanceToolchain.cmake b/Tests/RunCMake/GeneratorInstance/BadInstanceToolchain.cmake new file mode 100644 index 0000000..2fc38e5 --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/BadInstanceToolchain.cmake @@ -0,0 +1 @@ +message(FATAL_ERROR "This should not be reached!") diff --git a/Tests/RunCMake/GeneratorInstance/CMakeLists.txt b/Tests/RunCMake/GeneratorInstance/CMakeLists.txt new file mode 100644 index 0000000..d3137f6 --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/CMakeLists.txt @@ -0,0 +1,3 @@ +cmake_minimum_required(VERSION 3.9) +project(${RunCMake_TEST} NONE) +include(${RunCMake_TEST}.cmake) diff --git a/Tests/RunCMake/GeneratorInstance/DefaultInstance.cmake b/Tests/RunCMake/GeneratorInstance/DefaultInstance.cmake new file mode 100644 index 0000000..7750c2e --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/DefaultInstance.cmake @@ -0,0 +1,13 @@ +if("x${CMAKE_GENERATOR_INSTANCE}" STREQUAL "x") + message(FATAL_ERROR "CMAKE_GENERATOR_INSTANCE is empty but should have a value.") +elseif("x${CMAKE_GENERATOR_INSTANCE}" MATCHES [[\\]]) + message(FATAL_ERROR + "CMAKE_GENERATOR_INSTANCE is\n" + " ${CMAKE_GENERATOR_INSTANCE}\n" + "which contains a backslash.") +elseif(NOT IS_DIRECTORY "${CMAKE_GENERATOR_INSTANCE}") + message(FATAL_ERROR + "CMAKE_GENERATOR_INSTANCE is\n" + " ${CMAKE_GENERATOR_INSTANCE}\n" + "which is not an existing directory.") +endif() diff --git a/Tests/RunCMake/GeneratorInstance/MissingInstance-result.txt b/Tests/RunCMake/GeneratorInstance/MissingInstance-result.txt new file mode 100644 index 0000000..d00491f --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/MissingInstance-result.txt @@ -0,0 +1 @@ +1 diff --git a/Tests/RunCMake/GeneratorInstance/MissingInstance-stderr.txt b/Tests/RunCMake/GeneratorInstance/MissingInstance-stderr.txt new file mode 100644 index 0000000..623bf2e --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/MissingInstance-stderr.txt @@ -0,0 +1,8 @@ +CMake Error at CMakeLists.txt:[0-9]+ \(project\): + Generator + + .* + + could not find specified instance of .*: + + .*/Tests/RunCMake/GeneratorInstance/instance_does_not_exist$ diff --git a/Tests/RunCMake/GeneratorInstance/MissingInstance-toolchain.cmake b/Tests/RunCMake/GeneratorInstance/MissingInstance-toolchain.cmake new file mode 100644 index 0000000..f803f14 --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/MissingInstance-toolchain.cmake @@ -0,0 +1 @@ +set(CMAKE_GENERATOR_INSTANCE "${CMAKE_CURRENT_LIST_DIR}/instance_does_not_exist") diff --git a/Tests/RunCMake/GeneratorInstance/MissingInstance.cmake b/Tests/RunCMake/GeneratorInstance/MissingInstance.cmake new file mode 100644 index 0000000..2fc38e5 --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/MissingInstance.cmake @@ -0,0 +1 @@ +message(FATAL_ERROR "This should not be reached!") diff --git a/Tests/RunCMake/GeneratorInstance/MissingInstanceToolchain-result.txt b/Tests/RunCMake/GeneratorInstance/MissingInstanceToolchain-result.txt new file mode 100644 index 0000000..d00491f --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/MissingInstanceToolchain-result.txt @@ -0,0 +1 @@ +1 diff --git a/Tests/RunCMake/GeneratorInstance/MissingInstanceToolchain-stderr.txt b/Tests/RunCMake/GeneratorInstance/MissingInstanceToolchain-stderr.txt new file mode 100644 index 0000000..623bf2e --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/MissingInstanceToolchain-stderr.txt @@ -0,0 +1,8 @@ +CMake Error at CMakeLists.txt:[0-9]+ \(project\): + Generator + + .* + + could not find specified instance of .*: + + .*/Tests/RunCMake/GeneratorInstance/instance_does_not_exist$ diff --git a/Tests/RunCMake/GeneratorInstance/MissingInstanceToolchain.cmake b/Tests/RunCMake/GeneratorInstance/MissingInstanceToolchain.cmake new file mode 100644 index 0000000..2fc38e5 --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/MissingInstanceToolchain.cmake @@ -0,0 +1 @@ +message(FATAL_ERROR "This should not be reached!") diff --git a/Tests/RunCMake/GeneratorInstance/NoInstance-result.txt b/Tests/RunCMake/GeneratorInstance/NoInstance-result.txt new file mode 100644 index 0000000..d00491f --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/NoInstance-result.txt @@ -0,0 +1 @@ +1 diff --git a/Tests/RunCMake/GeneratorInstance/NoInstance-stderr.txt b/Tests/RunCMake/GeneratorInstance/NoInstance-stderr.txt new file mode 100644 index 0000000..e7b52fd --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/NoInstance-stderr.txt @@ -0,0 +1,4 @@ +CMake Error at NoInstance.cmake:2 \(message\): + CMAKE_GENERATOR_INSTANCE is empty as expected. +Call Stack \(most recent call first\): + CMakeLists.txt:3 \(include\) diff --git a/Tests/RunCMake/GeneratorInstance/NoInstance.cmake b/Tests/RunCMake/GeneratorInstance/NoInstance.cmake new file mode 100644 index 0000000..2e6782e --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/NoInstance.cmake @@ -0,0 +1,7 @@ +if("x${CMAKE_GENERATOR_INSTANCE}" STREQUAL "x") + message(FATAL_ERROR "CMAKE_GENERATOR_INSTANCE is empty as expected.") +else() + message(FATAL_ERROR + "CMAKE_GENERATOR_INSTANCE is \"${CMAKE_GENERATOR_INSTANCE}\" " + "but should be empty!") +endif() diff --git a/Tests/RunCMake/GeneratorInstance/RunCMakeTest.cmake b/Tests/RunCMake/GeneratorInstance/RunCMakeTest.cmake new file mode 100644 index 0000000..e7f9ccb --- /dev/null +++ b/Tests/RunCMake/GeneratorInstance/RunCMakeTest.cmake @@ -0,0 +1,22 @@ +include(RunCMake) + +if("${RunCMake_GENERATOR}" MATCHES "^Visual Studio 1[56789]") + set(RunCMake_GENERATOR_INSTANCE "") + run_cmake(DefaultInstance) + + set(RunCMake_GENERATOR_INSTANCE "${RunCMake_SOURCE_DIR}/instance_does_not_exist") + run_cmake(MissingInstance) + set(RunCMake_TEST_OPTIONS -DCMAKE_TOOLCHAIN_FILE=${RunCMake_SOURCE_DIR}/MissingInstance-toolchain.cmake) + run_cmake(MissingInstanceToolchain) + unset(RunCMake_TEST_OPTIONS) +else() + set(RunCMake_GENERATOR_INSTANCE "") + run_cmake(NoInstance) + + set(RunCMake_GENERATOR_INSTANCE "Bad Instance") + run_cmake(BadInstance) + + set(RunCMake_TEST_OPTIONS -DCMAKE_TOOLCHAIN_FILE=${RunCMake_SOURCE_DIR}/BadInstance-toolchain.cmake) + run_cmake(BadInstanceToolchain) + unset(RunCMake_TEST_OPTIONS) +endif() diff --git a/Tests/RunCMake/RunCMake.cmake b/Tests/RunCMake/RunCMake.cmake index 4fd816e..e688830 100644 --- a/Tests/RunCMake/RunCMake.cmake +++ b/Tests/RunCMake/RunCMake.cmake @@ -79,11 +79,17 @@ function(run_cmake test) ${maybe_timeout} ) else() + if(RunCMake_GENERATOR_INSTANCE) + set(_D_CMAKE_GENERATOR_INSTANCE "-DCMAKE_GENERATOR_INSTANCE=${RunCMake_GENERATOR_INSTANCE}") + else() + set(_D_CMAKE_GENERATOR_INSTANCE "") + endif() execute_process( COMMAND ${CMAKE_COMMAND} "${RunCMake_TEST_SOURCE_DIR}" -G "${RunCMake_GENERATOR}" -A "${RunCMake_GENERATOR_PLATFORM}" -T "${RunCMake_GENERATOR_TOOLSET}" + ${_D_CMAKE_GENERATOR_INSTANCE} -DRunCMake_TEST=${test} --no-warn-unused-cli ${RunCMake_TEST_OPTIONS} diff --git a/Tests/RunCMake/add_executable/NoSources-stderr.txt b/Tests/RunCMake/add_executable/NoSources-stderr.txt index 5985905..4fcfd49 100644 --- a/Tests/RunCMake/add_executable/NoSources-stderr.txt +++ b/Tests/RunCMake/add_executable/NoSources-stderr.txt @@ -1,4 +1,4 @@ ^CMake Error at NoSources.cmake:[0-9]+ \(add_executable\): - add_executable called with incorrect number of arguments + No SOURCES given to target: TestExeWithoutSources Call Stack \(most recent call first\): CMakeLists.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/add_executable/NoSourcesButLinkObjects-stderr.txt b/Tests/RunCMake/add_executable/NoSourcesButLinkObjects-stderr.txt index c8afadb..5561daa 100644 --- a/Tests/RunCMake/add_executable/NoSourcesButLinkObjects-stderr.txt +++ b/Tests/RunCMake/add_executable/NoSourcesButLinkObjects-stderr.txt @@ -1,11 +1,4 @@ ^CMake Error at NoSourcesButLinkObjects.cmake:[0-9]+ \(add_executable\): - add_executable called with incorrect number of arguments -Call Stack \(most recent call first\): - CMakeLists.txt:[0-9]+ \(include\) - - -CMake Error at NoSourcesButLinkObjects.cmake:[0-9]+ \(target_link_libraries\): - Cannot specify link libraries for target \"TestExeWithoutSources\" which is - not built by this project. + No SOURCES given to target: TestExeWithoutSources Call Stack \(most recent call first\): CMakeLists.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/add_executable/OnlyObjectSources-stderr.txt b/Tests/RunCMake/add_executable/OnlyObjectSources-stderr.txt deleted file mode 100644 index ea72d5d..0000000 --- a/Tests/RunCMake/add_executable/OnlyObjectSources-stderr.txt +++ /dev/null @@ -1,11 +0,0 @@ -^CMake Error at OnlyObjectSources.cmake:[0-9]+ \(add_executable\): - add_executable called with incorrect number of arguments -Call Stack \(most recent call first\): - CMakeLists.txt:[0-9]+ \(include\) - - -CMake Error at OnlyObjectSources.cmake:[0-9]+ \(target_sources\): - Cannot specify sources for target \"TestExeWithoutSources\" which is not - built by this project. -Call Stack \(most recent call first\): - CMakeLists.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/add_executable/RunCMakeTest.cmake b/Tests/RunCMake/add_executable/RunCMakeTest.cmake index 70a68f2..88916b7 100644 --- a/Tests/RunCMake/add_executable/RunCMakeTest.cmake +++ b/Tests/RunCMake/add_executable/RunCMakeTest.cmake @@ -2,4 +2,6 @@ include(RunCMake) run_cmake(NoSources) run_cmake(OnlyObjectSources) -run_cmake(NoSourcesButLinkObjects) +if(NOT RunCMake_GENERATOR STREQUAL "Xcode" OR NOT "$ENV{CMAKE_OSX_ARCHITECTURES}" MATCHES "[;$]") + run_cmake(NoSourcesButLinkObjects) +endif() diff --git a/Tests/RunCMake/add_library/MODULEwithNoSources-stderr.txt b/Tests/RunCMake/add_library/MODULEwithNoSources-stderr.txt index 5cf0b1e..41da381 100644 --- a/Tests/RunCMake/add_library/MODULEwithNoSources-stderr.txt +++ b/Tests/RunCMake/add_library/MODULEwithNoSources-stderr.txt @@ -1,3 +1,4 @@ -^You have called ADD_LIBRARY for library TestModuleLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file( -CMake Error: CMake can not determine linker language for target: TestModuleLibWithoutSources)+( -CMake Error: Cannot determine link language for target \"TestModuleLibWithoutSources\".)?$ +^CMake Error at MODULEwithNoSources.cmake:[0-9]+ \(add_library\): + No SOURCES given to target: TestModuleLibWithoutSources +Call Stack \(most recent call first\): + CMakeLists.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/add_library/MODULEwithNoSourcesButLinkObjects-stderr.txt b/Tests/RunCMake/add_library/MODULEwithNoSourcesButLinkObjects-stderr.txt index 951594a..67dd87c 100644 --- a/Tests/RunCMake/add_library/MODULEwithNoSourcesButLinkObjects-stderr.txt +++ b/Tests/RunCMake/add_library/MODULEwithNoSourcesButLinkObjects-stderr.txt @@ -1,3 +1,4 @@ -^You have called ADD_LIBRARY for library TestModuleLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file( -CMake Error: CMake can not determine linker language for target: TestModuleLibWithoutSources)+( -CMake Error: Cannot determine link language for target \"TestModuleLibWithoutSources\".)*$ +^CMake Error at MODULEwithNoSourcesButLinkObjects.cmake:[0-9]+ \(add_library\): + No SOURCES given to target: TestModuleLibWithoutSources +Call Stack \(most recent call first\): + CMakeLists.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/add_library/MODULEwithOnlyObjectSources-stderr.txt b/Tests/RunCMake/add_library/MODULEwithOnlyObjectSources-stderr.txt deleted file mode 100644 index de83755..0000000 --- a/Tests/RunCMake/add_library/MODULEwithOnlyObjectSources-stderr.txt +++ /dev/null @@ -1 +0,0 @@ -^You have called ADD_LIBRARY for library TestModuleLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file$ diff --git a/Tests/RunCMake/add_library/OBJECTwithNoSources-result.txt b/Tests/RunCMake/add_library/OBJECTwithNoSources-result.txt index 9c558e3..d00491f 100644 --- a/Tests/RunCMake/add_library/OBJECTwithNoSources-result.txt +++ b/Tests/RunCMake/add_library/OBJECTwithNoSources-result.txt @@ -1 +1 @@ -. +1 diff --git a/Tests/RunCMake/add_library/OBJECTwithNoSources-stderr.txt b/Tests/RunCMake/add_library/OBJECTwithNoSources-stderr.txt index 099ec4f..20d3a8a 100644 --- a/Tests/RunCMake/add_library/OBJECTwithNoSources-stderr.txt +++ b/Tests/RunCMake/add_library/OBJECTwithNoSources-stderr.txt @@ -1,2 +1,4 @@ -^You have called ADD_LIBRARY for library TestObjectLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file( -CMake Error: CMake can not determine linker language for target: TestObjectLibWithoutSources)*$ +^CMake Error at OBJECTwithNoSources.cmake:[0-9]+ \(add_library\): + No SOURCES given to target: TestObjectLibWithoutSources +Call Stack \(most recent call first\): + CMakeLists.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/add_library/OBJECTwithNoSourcesButLinkObjects-stderr.txt b/Tests/RunCMake/add_library/OBJECTwithNoSourcesButLinkObjects-stderr.txt index 8f20096..cd6f1e0 100644 --- a/Tests/RunCMake/add_library/OBJECTwithNoSourcesButLinkObjects-stderr.txt +++ b/Tests/RunCMake/add_library/OBJECTwithNoSourcesButLinkObjects-stderr.txt @@ -1,5 +1,4 @@ -^You have called ADD_LIBRARY for library TestObjectLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file -CMake Error at OBJECTwithNoSourcesButLinkObjects.cmake:[0-9]+ \(target_link_libraries\): +^CMake Error at OBJECTwithNoSourcesButLinkObjects.cmake:[0-9]+ \(target_link_libraries\): Object library target \"TestObjectLibWithoutSources\" may not link to anything. Call Stack \(most recent call first\): diff --git a/Tests/RunCMake/add_library/OBJECTwithOnlyObjectSources-stderr.txt b/Tests/RunCMake/add_library/OBJECTwithOnlyObjectSources-stderr.txt index f9cbf6b..77a72f1 100644 --- a/Tests/RunCMake/add_library/OBJECTwithOnlyObjectSources-stderr.txt +++ b/Tests/RunCMake/add_library/OBJECTwithOnlyObjectSources-stderr.txt @@ -1,5 +1,4 @@ -^You have called ADD_LIBRARY for library TestObjectLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file -CMake Error at OBJECTwithOnlyObjectSources.cmake:[0-9]+ \(add_library\): +^CMake Error at OBJECTwithOnlyObjectSources.cmake:[0-9]+ \(add_library\): OBJECT library \"TestObjectLibWithoutSources\" contains: [^ diff --git a/Tests/RunCMake/add_library/SHAREDwithNoSources-stderr.txt b/Tests/RunCMake/add_library/SHAREDwithNoSources-stderr.txt index 228d1cc..5cedd62 100644 --- a/Tests/RunCMake/add_library/SHAREDwithNoSources-stderr.txt +++ b/Tests/RunCMake/add_library/SHAREDwithNoSources-stderr.txt @@ -1,3 +1,4 @@ -^You have called ADD_LIBRARY for library TestSharedLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file( -CMake Error: CMake can not determine linker language for target: TestSharedLibWithoutSources)+( -CMake Error: Cannot determine link language for target \"TestSharedLibWithoutSources\".)*$ +^CMake Error at SHAREDwithNoSources.cmake:[0-9]+ \(add_library\): + No SOURCES given to target: TestSharedLibWithoutSources +Call Stack \(most recent call first\): + CMakeLists.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/add_library/SHAREDwithNoSourcesButLinkObjects-stderr.txt b/Tests/RunCMake/add_library/SHAREDwithNoSourcesButLinkObjects-stderr.txt index 228d1cc..d621e76 100644 --- a/Tests/RunCMake/add_library/SHAREDwithNoSourcesButLinkObjects-stderr.txt +++ b/Tests/RunCMake/add_library/SHAREDwithNoSourcesButLinkObjects-stderr.txt @@ -1,3 +1,4 @@ -^You have called ADD_LIBRARY for library TestSharedLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file( -CMake Error: CMake can not determine linker language for target: TestSharedLibWithoutSources)+( -CMake Error: Cannot determine link language for target \"TestSharedLibWithoutSources\".)*$ +^CMake Error at SHAREDwithNoSourcesButLinkObjects.cmake:[0-9]+ \(add_library\): + No SOURCES given to target: TestSharedLibWithoutSources +Call Stack \(most recent call first\): + CMakeLists.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/add_library/SHAREDwithOnlyObjectSources-stderr.txt b/Tests/RunCMake/add_library/SHAREDwithOnlyObjectSources-stderr.txt deleted file mode 100644 index ec350cd..0000000 --- a/Tests/RunCMake/add_library/SHAREDwithOnlyObjectSources-stderr.txt +++ /dev/null @@ -1 +0,0 @@ -^You have called ADD_LIBRARY for library TestSharedLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file$ diff --git a/Tests/RunCMake/add_library/STATICwithNoSources-stderr.txt b/Tests/RunCMake/add_library/STATICwithNoSources-stderr.txt index 830eb22..10b2112 100644 --- a/Tests/RunCMake/add_library/STATICwithNoSources-stderr.txt +++ b/Tests/RunCMake/add_library/STATICwithNoSources-stderr.txt @@ -1,3 +1,4 @@ -^You have called ADD_LIBRARY for library TestStaticLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file( -CMake Error: Cannot determine link language for target \"TestStaticLibWithoutSources\".)?( -CMake Error: CMake can not determine linker language for target: TestStaticLibWithoutSources)+$ +^CMake Error at STATICwithNoSources.cmake:[0-9]+ \(add_library\): + No SOURCES given to target: TestStaticLibWithoutSources +Call Stack \(most recent call first\): + CMakeLists.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/add_library/STATICwithNoSourcesButLinkObjects-stderr.txt b/Tests/RunCMake/add_library/STATICwithNoSourcesButLinkObjects-stderr.txt index 830eb22..33c23b2 100644 --- a/Tests/RunCMake/add_library/STATICwithNoSourcesButLinkObjects-stderr.txt +++ b/Tests/RunCMake/add_library/STATICwithNoSourcesButLinkObjects-stderr.txt @@ -1,3 +1,4 @@ -^You have called ADD_LIBRARY for library TestStaticLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file( -CMake Error: Cannot determine link language for target \"TestStaticLibWithoutSources\".)?( -CMake Error: CMake can not determine linker language for target: TestStaticLibWithoutSources)+$ +^CMake Error at STATICwithNoSourcesButLinkObjects.cmake:[0-9]+ \(add_library\): + No SOURCES given to target: TestStaticLibWithoutSources +Call Stack \(most recent call first\): + CMakeLists.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/add_library/STATICwithOnlyObjectSources-stderr.txt b/Tests/RunCMake/add_library/STATICwithOnlyObjectSources-stderr.txt deleted file mode 100644 index 5cd10d4..0000000 --- a/Tests/RunCMake/add_library/STATICwithOnlyObjectSources-stderr.txt +++ /dev/null @@ -1 +0,0 @@ -^You have called ADD_LIBRARY for library TestStaticLibWithoutSources without any source files. This typically indicates a problem with your CMakeLists.txt file$ |