summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--.gitlab-ci.yml12
-rw-r--r--.gitlab/ci/configure_windows_msvc_cxx_modules_common.cmake2
-rw-r--r--.gitlab/ci/configure_windows_vs2022_x64_ninja.cmake1
-rw-r--r--.gitlab/ci/configure_windows_vs2022_x64_ninja_multi.cmake1
-rw-r--r--.gitlab/ci/cxx_modules_rules_msvc.cmake11
-rw-r--r--.gitlab/os-windows.yml55
-rw-r--r--Auxiliary/cmake-mode.el4
-rw-r--r--Auxiliary/vim/indent/cmake.vim4
-rw-r--r--Auxiliary/vim/syntax/cmake.vim2
-rw-r--r--Help/command/block.rst74
-rw-r--r--Help/command/cmake_language.rst1
-rw-r--r--Help/command/cmake_policy.rst41
-rw-r--r--Help/command/ctest_test.rst8
-rw-r--r--Help/command/endblock.rst11
-rw-r--r--Help/command/set.rst17
-rw-r--r--Help/manual/cmake-commands.7.rst2
-rw-r--r--Help/manual/cmake-variables.7.rst5
-rw-r--r--Help/release/dev/block-command.rst5
-rw-r--r--Help/release/dev/bsd-variables.rst9
-rw-r--r--Help/variable/BSD.rst6
-rw-r--r--Help/variable/DRAGONFLYBSD.rst6
-rw-r--r--Help/variable/FREEBSD.rst6
-rw-r--r--Help/variable/NETBSD.rst6
-rw-r--r--Help/variable/OPENBSD.rst6
-rw-r--r--Modules/Platform/DragonFly.cmake2
-rw-r--r--Modules/Platform/FreeBSD.cmake2
-rw-r--r--Modules/Platform/NetBSD.cmake2
-rw-r--r--Modules/Platform/OpenBSD.cmake2
-rw-r--r--Modules/Platform/kFreeBSD.cmake4
-rw-r--r--Source/CMakeLists.txt2
-rw-r--r--Source/CMakeVersion.cmake2
-rw-r--r--Source/cmBlockCommand.cxx200
-rw-r--r--Source/cmBlockCommand.h14
-rw-r--r--Source/cmCMakeLanguageCommand.cxx5
-rw-r--r--Source/cmCommands.cxx6
-rw-r--r--Source/cmFunctionBlocker.cxx18
-rw-r--r--Source/cmFunctionBlocker.h2
-rw-r--r--Source/cmListFileCache.cxx11
-rw-r--r--Source/cmLocalGenerator.cxx3
-rw-r--r--Source/cmMakefile.cxx13
-rw-r--r--Source/cmMakefile.h18
-rw-r--r--Source/cmQtAutoGenInitializer.cxx3
-rw-r--r--Source/cmSetPropertyCommand.cxx4
-rw-r--r--Source/cmStandardLevelResolver.cxx7
-rw-r--r--Source/cmTarget.cxx37
-rw-r--r--Source/cmTarget.h6
-rw-r--r--Source/cmTargetCompileDefinitionsCommand.cxx4
-rw-r--r--Source/cmTargetIncludeDirectoriesCommand.cxx3
-rw-r--r--Source/cmTargetLinkLibrariesCommand.cxx8
-rw-r--r--Source/cmTargetPrecompileHeadersCommand.cxx4
-rw-r--r--Source/cmTargetSourcesCommand.cxx9
-rw-r--r--Tests/CMakeLib/testCMExtEnumSet.cxx9
-rw-r--r--Tests/RunCMake/CMakeLists.txt1
-rw-r--r--Tests/RunCMake/FileAPI/CMakeLists.txt2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-check.py2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/directories/alias.json2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/directories/custom.json2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/directories/cxx.json2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/directories/dir.json2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/directories/dir_dir.json2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/directories/external.json2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/directories/fileset.json2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/directories/imported.json2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/directories/interface.json2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/directories/subdir.json11
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/directories/top.json32
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/projects/codemodel-v2.json4
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/targets/all_build_top.json4
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/targets/c_shared_lib.json6
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/targets/c_subdir.json150
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe.json2
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_shared_lib.json6
-rw-r--r--Tests/RunCMake/FileAPI/codemodel-v2.cmake3
-rw-r--r--Tests/RunCMake/FileAPI/subdir/CMakeLists.txt4
-rw-r--r--Tests/RunCMake/FileAPI/subdir/empty.c0
-rw-r--r--Tests/RunCMake/block/CMakeLists.txt3
-rw-r--r--Tests/RunCMake/block/EndAlone-result.txt1
-rw-r--r--Tests/RunCMake/block/EndAlone-stderr.txt4
-rw-r--r--Tests/RunCMake/block/EndAlone.cmake1
-rw-r--r--Tests/RunCMake/block/EndAloneWithArgument-result.txt1
-rw-r--r--Tests/RunCMake/block/EndAloneWithArgument-stderr.txt4
-rw-r--r--Tests/RunCMake/block/EndAloneWithArgument.cmake1
-rw-r--r--Tests/RunCMake/block/EndMissing-result.txt1
-rw-r--r--Tests/RunCMake/block/EndMissing-stderr.txt4
-rw-r--r--Tests/RunCMake/block/EndMissing.cmake1
-rw-r--r--Tests/RunCMake/block/EndWithArgument-stderr.txt9
-rw-r--r--Tests/RunCMake/block/EndWithArgument.cmake2
-rw-r--r--Tests/RunCMake/block/InvalidArgument-result.txt1
-rw-r--r--Tests/RunCMake/block/InvalidArgument-stderr.txt4
-rw-r--r--Tests/RunCMake/block/InvalidArgument.cmake2
-rw-r--r--Tests/RunCMake/block/InvalidNesting1-result.txt1
-rw-r--r--Tests/RunCMake/block/InvalidNesting1-stderr.txt4
-rw-r--r--Tests/RunCMake/block/InvalidNesting1.cmake6
-rw-r--r--Tests/RunCMake/block/InvalidNesting2-result.txt1
-rw-r--r--Tests/RunCMake/block/InvalidNesting2-stderr.txt4
-rw-r--r--Tests/RunCMake/block/InvalidNesting2.cmake6
-rw-r--r--Tests/RunCMake/block/InvalidNesting3-result.txt1
-rw-r--r--Tests/RunCMake/block/InvalidNesting3-stderr.txt4
-rw-r--r--Tests/RunCMake/block/InvalidNesting3.cmake5
-rw-r--r--Tests/RunCMake/block/InvalidNesting4-result.txt1
-rw-r--r--Tests/RunCMake/block/InvalidNesting4-stderr.txt4
-rw-r--r--Tests/RunCMake/block/InvalidNesting4.cmake5
-rw-r--r--Tests/RunCMake/block/InvalidNesting5-result.txt1
-rw-r--r--Tests/RunCMake/block/InvalidNesting5-stderr.txt4
-rw-r--r--Tests/RunCMake/block/InvalidNesting5.cmake5
-rw-r--r--Tests/RunCMake/block/InvalidNesting6-result.txt1
-rw-r--r--Tests/RunCMake/block/InvalidNesting6-stderr.txt4
-rw-r--r--Tests/RunCMake/block/InvalidNesting6.cmake5
-rw-r--r--Tests/RunCMake/block/MissingArgument-result.txt1
-rw-r--r--Tests/RunCMake/block/MissingArgument-stderr.txt7
-rw-r--r--Tests/RunCMake/block/MissingArgument.cmake2
-rw-r--r--Tests/RunCMake/block/RunCMakeTest.cmake22
-rw-r--r--Tests/RunCMake/block/Scope-POLICIES.cmake30
-rw-r--r--Tests/RunCMake/block/Scope-VARIABLES.cmake52
-rw-r--r--Tests/RunCMake/block/Scope.cmake52
-rw-r--r--Tests/RunCMake/block/Workflows.cmake78
-rw-r--r--Tests/RunCMake/block/WrongArgument-result.txt1
-rw-r--r--Tests/RunCMake/block/WrongArgument-stderr.txt4
-rw-r--r--Tests/RunCMake/block/WrongArgument.cmake2
-rw-r--r--Tests/RunCMake/block/WrongScope-result.txt1
-rw-r--r--Tests/RunCMake/block/WrongScope-stderr.txt4
-rw-r--r--Tests/RunCMake/block/WrongScope.cmake2
-rw-r--r--Tests/RunCMake/cmake_language/RunCMakeTest.cmake2
-rw-r--r--Utilities/std/cmext/enum_set13
-rwxr-xr-xbootstrap1
125 files changed, 1202 insertions, 113 deletions
diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml
index bfc713f..fa11b15 100644
--- a/.gitlab-ci.yml
+++ b/.gitlab-ci.yml
@@ -1079,7 +1079,7 @@ b:windows-x86_64-package:
- .windows_x86_64_package
- .cmake_build_windows
- .cmake_build_package_artifacts
- - .windows_tags_nonconcurrent_vs2022
+ - .windows_tags_x86_64_package
- .run_only_for_package
dependencies:
- p:doc-package
@@ -1093,7 +1093,7 @@ k:windows-x86_64-package:
- .windows_x86_64_package
- .cmake_package_windows
- .cmake_release_artifacts
- - .windows_tags_nonconcurrent_vs2022
+ - .windows_tags_x86_64_package
- .run_only_for_package
dependencies:
- b:windows-x86_64-package
@@ -1116,7 +1116,7 @@ b:windows-i386-package:
- .windows_i386_package
- .cmake_build_windows
- .cmake_build_package_artifacts
- - .windows_tags_nonconcurrent_vs2022
+ - .windows_tags_x86_64_package
- .run_only_for_package
dependencies:
- p:doc-package
@@ -1130,7 +1130,7 @@ k:windows-i386-package:
- .windows_i386_package
- .cmake_package_windows
- .cmake_release_artifacts
- - .windows_tags_nonconcurrent_vs2022
+ - .windows_tags_x86_64_package
- .run_only_for_package
dependencies:
- b:windows-i386-package
@@ -1153,7 +1153,7 @@ b:windows-arm64-package:
- .windows_arm64_package
- .cmake_build_windows
- .cmake_build_package_artifacts
- - .windows_tags_nonconcurrent_vs2022_arm64
+ - .windows_tags_arm64_package
- .run_only_for_package
dependencies:
- p:doc-package
@@ -1167,7 +1167,7 @@ k:windows-arm64-package:
- .windows_arm64_package
- .cmake_package_windows
- .cmake_release_artifacts
- - .windows_tags_nonconcurrent_vs2022_arm64
+ - .windows_tags_arm64_package
- .run_only_for_package
dependencies:
- b:windows-arm64-package
diff --git a/.gitlab/ci/configure_windows_msvc_cxx_modules_common.cmake b/.gitlab/ci/configure_windows_msvc_cxx_modules_common.cmake
new file mode 100644
index 0000000..8570196
--- /dev/null
+++ b/.gitlab/ci/configure_windows_msvc_cxx_modules_common.cmake
@@ -0,0 +1,2 @@
+set(CMake_TEST_MODULE_COMPILATION "named,partitions,internal_partitions,shared,export_bmi,install_bmi" CACHE STRING "")
+set(CMake_TEST_MODULE_COMPILATION_RULES "${CMAKE_CURRENT_LIST_DIR}/cxx_modules_rules_msvc.cmake" CACHE STRING "")
diff --git a/.gitlab/ci/configure_windows_vs2022_x64_ninja.cmake b/.gitlab/ci/configure_windows_vs2022_x64_ninja.cmake
index 7f57181..f5a6d80 100644
--- a/.gitlab/ci/configure_windows_vs2022_x64_ninja.cmake
+++ b/.gitlab/ci/configure_windows_vs2022_x64_ninja.cmake
@@ -2,4 +2,5 @@ if (NOT "$ENV{CMAKE_CI_NIGHTLY}" STREQUAL "")
set(CMake_TEST_ISPC "ON" CACHE STRING "")
endif()
+include("${CMAKE_CURRENT_LIST_DIR}/configure_windows_msvc_cxx_modules_common.cmake")
include("${CMAKE_CURRENT_LIST_DIR}/configure_windows_vs_common_ninja.cmake")
diff --git a/.gitlab/ci/configure_windows_vs2022_x64_ninja_multi.cmake b/.gitlab/ci/configure_windows_vs2022_x64_ninja_multi.cmake
index 5b2f0b7..2b0c76d 100644
--- a/.gitlab/ci/configure_windows_vs2022_x64_ninja_multi.cmake
+++ b/.gitlab/ci/configure_windows_vs2022_x64_ninja_multi.cmake
@@ -2,4 +2,5 @@ if (NOT "$ENV{CMAKE_CI_NIGHTLY}" STREQUAL "")
set(CMake_TEST_ISPC "ON" CACHE STRING "")
endif()
+include("${CMAKE_CURRENT_LIST_DIR}/configure_windows_msvc_cxx_modules_common.cmake")
include("${CMAKE_CURRENT_LIST_DIR}/configure_windows_msvc_common.cmake")
diff --git a/.gitlab/ci/cxx_modules_rules_msvc.cmake b/.gitlab/ci/cxx_modules_rules_msvc.cmake
new file mode 100644
index 0000000..5f0ae76
--- /dev/null
+++ b/.gitlab/ci/cxx_modules_rules_msvc.cmake
@@ -0,0 +1,11 @@
+set(CMake_TEST_CXXModules_UUID "a246741c-d067-4019-a8fb-3d16b0c9d1d3")
+
+set(CMAKE_EXPERIMENTAL_CXX_MODULE_DYNDEP 1)
+string(CONCAT CMAKE_EXPERIMENTAL_CXX_SCANDEP_SOURCE
+ "<CMAKE_CXX_COMPILER> <DEFINES> <INCLUDES> <FLAGS> <SOURCE> -nologo -TP"
+ " -showIncludes"
+ " -scanDependencies <DYNDEP_FILE>"
+ " -Fo<OBJECT>")
+set(CMAKE_EXPERIMENTAL_CXX_SCANDEP_DEPFILE_FORMAT "msvc")
+set(CMAKE_EXPERIMENTAL_CXX_MODULE_MAP_FORMAT "msvc")
+set(CMAKE_EXPERIMENTAL_CXX_MODULE_MAP_FLAG "@<MODULE_MAP_FILE>")
diff --git a/.gitlab/os-windows.yml b/.gitlab/os-windows.yml
index b9b91fb..282cf1e 100644
--- a/.gitlab/os-windows.yml
+++ b/.gitlab/os-windows.yml
@@ -35,15 +35,27 @@
variables:
VCVARSALL: "${VS170COMNTOOLS}\\..\\..\\VC\\Auxiliary\\Build\\vcvarsall.bat"
VCVARSPLATFORM: "x64"
- VCVARSVERSION: "14.32.31326"
+ VCVARSVERSION: "14.33.31629"
.windows_vcvarsall_vs2022_x86:
variables:
VCVARSALL: "${VS170COMNTOOLS}\\..\\..\\VC\\Auxiliary\\Build\\vcvarsall.bat"
VCVARSPLATFORM: "x86"
+ VCVARSVERSION: "14.33.31629"
+
+.windows_vcvarsall_vs2022_x64_package:
+ variables:
+ VCVARSALL: "${VS170COMNTOOLS}\\..\\..\\VC\\Auxiliary\\Build\\vcvarsall.bat"
+ VCVARSPLATFORM: "x64"
+ VCVARSVERSION: "14.32.31326"
+
+.windows_vcvarsall_vs2022_x86_package:
+ variables:
+ VCVARSALL: "${VS170COMNTOOLS}\\..\\..\\VC\\Auxiliary\\Build\\vcvarsall.bat"
+ VCVARSPLATFORM: "x86"
VCVARSVERSION: "14.32.31326"
-.windows_vcvarsall_vs2022_x64_arm64:
+.windows_vcvarsall_vs2022_x64_arm64_package:
variables:
VCVARSALL: "${VS170COMNTOOLS}\\..\\..\\VC\\Auxiliary\\Build\\vcvarsall.bat"
VCVARSPLATFORM: "x64_arm64"
@@ -68,7 +80,7 @@
.windows_x86_64_package:
extends:
- .windows_package
- - .windows_vcvarsall_vs2022_x64
+ - .windows_vcvarsall_vs2022_x64_package
variables:
CMAKE_CONFIGURATION: windows_x86_64_package
@@ -76,7 +88,7 @@
.windows_i386_package:
extends:
- .windows_package
- - .windows_vcvarsall_vs2022_x86
+ - .windows_vcvarsall_vs2022_x86_package
variables:
CMAKE_CONFIGURATION: windows_i386_package
@@ -84,7 +96,7 @@
.windows_arm64_package:
extends:
- .windows_package
- - .windows_vcvarsall_vs2022_x64_arm64
+ - .windows_vcvarsall_vs2022_x64_arm64_package
variables:
CMAKE_CONFIGURATION: windows_arm64_package
@@ -98,7 +110,7 @@
CMAKE_CONFIGURATION: windows_vs2022_x64
CMAKE_GENERATOR: "Visual Studio 17 2022"
CMAKE_GENERATOR_PLATFORM: "x64"
- CMAKE_GENERATOR_TOOLSET: "v143,version=14.32.31326"
+ CMAKE_GENERATOR_TOOLSET: "v143,version=14.33.31629"
CMAKE_CI_NIGHTLY_IGNORE_DEPS: "true"
.windows_vs2019_x64:
@@ -232,16 +244,7 @@
- windows
- shell
- vs2022
- - msvc-19.32
- - nonconcurrent
-
-.windows_tags_nonconcurrent_vs2022_arm64:
- tags:
- - cmake # Since this is a bare runner, pin to a project.
- - windows
- - shell
- - vs2022
- - msvc-19.32-arm64
+ - msvc-19.33
- nonconcurrent
.windows_tags_concurrent_vs2022:
@@ -250,7 +253,7 @@
- windows
- shell
- vs2022
- - msvc-19.32
+ - msvc-19.33
- concurrent
.windows_tags_concurrent_vs2019:
@@ -269,6 +272,24 @@
- shell
- concurrent
+.windows_tags_x86_64_package:
+ tags:
+ - cmake # Since this is a bare runner, pin to a project.
+ - windows
+ - shell
+ - vs2022
+ - msvc-19.32
+ - nonconcurrent
+
+.windows_tags_arm64_package:
+ tags:
+ - cmake # Since this is a bare runner, pin to a project.
+ - windows
+ - shell
+ - vs2022
+ - msvc-19.32-arm64
+ - nonconcurrent
+
## Windows-specific scripts
.before_script_windows: &before_script_windows
diff --git a/Auxiliary/cmake-mode.el b/Auxiliary/cmake-mode.el
index 2de9b98..a11becb 100644
--- a/Auxiliary/cmake-mode.el
+++ b/Auxiliary/cmake-mode.el
@@ -41,8 +41,8 @@ set the path with these commands:
:group 'cmake)
;; Keywords
-(defconst cmake-keywords-block-open '("IF" "MACRO" "FOREACH" "ELSE" "ELSEIF" "WHILE" "FUNCTION"))
-(defconst cmake-keywords-block-close '("ENDIF" "ENDFOREACH" "ENDMACRO" "ELSE" "ELSEIF" "ENDWHILE" "ENDFUNCTION"))
+(defconst cmake-keywords-block-open '("BLOCK" "IF" "MACRO" "FOREACH" "ELSE" "ELSEIF" "WHILE" "FUNCTION"))
+(defconst cmake-keywords-block-close '("ENDBLOCK" "ENDIF" "ENDFOREACH" "ENDMACRO" "ELSE" "ELSEIF" "ENDWHILE" "ENDFUNCTION"))
(defconst cmake-keywords
(let ((kwds (append cmake-keywords-block-open cmake-keywords-block-close nil)))
(delete-dups kwds)))
diff --git a/Auxiliary/vim/indent/cmake.vim b/Auxiliary/vim/indent/cmake.vim
index 672bdcc..0c662fa 100644
--- a/Auxiliary/vim/indent/cmake.vim
+++ b/Auxiliary/vim/indent/cmake.vim
@@ -59,8 +59,8 @@ fun! CMakeGetIndent(lnum)
let cmake_closing_parens_line = '^\s*\()\+\)\s*$'
- let cmake_indent_begin_regex = '^\s*\(IF\|MACRO\|FOREACH\|ELSE\|ELSEIF\|WHILE\|FUNCTION\)\s*('
- let cmake_indent_end_regex = '^\s*\(ENDIF\|ENDFOREACH\|ENDMACRO\|ELSE\|ELSEIF\|ENDWHILE\|ENDFUNCTION\)\s*('
+ let cmake_indent_begin_regex = '^\s*\(BLOCK\|IF\|MACRO\|FOREACH\|ELSE\|ELSEIF\|WHILE\|FUNCTION\)\s*('
+ let cmake_indent_end_regex = '^\s*\(ENDBLOCK\|ENDIF\|ENDFOREACH\|ENDMACRO\|ELSE\|ELSEIF\|ENDWHILE\|ENDFUNCTION\)\s*('
if this_line =~? cmake_closing_parens_line
if previous_line !~? cmake_indent_open_regex
diff --git a/Auxiliary/vim/syntax/cmake.vim b/Auxiliary/vim/syntax/cmake.vim
index 1273c00..ca257ba 100644
--- a/Auxiliary/vim/syntax/cmake.vim
+++ b/Auxiliary/vim/syntax/cmake.vim
@@ -3832,6 +3832,7 @@ syn keyword cmakeCommand
\ add_subdirectory
\ add_test
\ aux_source_directory
+ \ block
\ break
\ build_command
\ cmake_host_system_information
@@ -3859,6 +3860,7 @@ syn keyword cmakeCommand
\ define_property
\ enable_language
\ enable_testing
+ \ endblock
\ endfunction
\ endmacro
\ execute_process
diff --git a/Help/command/block.rst b/Help/command/block.rst
new file mode 100644
index 0000000..f9d85c8
--- /dev/null
+++ b/Help/command/block.rst
@@ -0,0 +1,74 @@
+block
+-----
+
+.. versionadded:: 3.25
+
+Evaluate a group of commands with a dedicated variable and/or policy scope.
+
+.. code-block:: cmake
+
+ block([SCOPE_FOR (POLICIES|VARIABLES)] [PROPAGATE <var-name>...])
+ <commands>
+ endblock()
+
+All commands between ``block()`` and the matching :command:`endblock` are
+recorded without being invoked. Once the :command:`endblock` is evaluated, the
+recorded list of commands is invoked inside the requested scopes, and, finally,
+the scopes created by ``block()`` command are removed.
+
+``SCOPE_FOR``
+ Specify which scopes must be created.
+
+ ``POLICIES``
+ Create a new policy scope. This is equivalent to
+ :command:`cmake_policy(PUSH)`.
+
+ ``VARIABLES``
+ Create a new variable scope.
+
+ If ``SCOPE_FOR`` is not specified, this is equivalent to:
+
+ .. code-block:: cmake
+
+ block(SCOPE_FOR VARIABLES POLICIES)
+
+``PROPAGATE``
+ When a variable scope is created by :command:`block` command, this option
+ set or unset the specified variables in the parent scope. This is equivalent
+ to :command:`set(PARENT_SCOPE)` or :command:`unset(PARENT_SCOPE)` commands.
+
+ .. code-block:: cmake
+
+ set(VAR1 "INIT1")
+ set(VAR2 "INIT2")
+
+ block(PROPAGATE VAR1 VAR2)
+ set(VAR1 "VALUE1")
+ unset(VAR2)
+ endblock()
+
+ # here, VAR1 holds value VALUE1 and VAR2 is unset
+
+ This option is only allowed when a variable scope is created. An error will
+ be raised in the other cases.
+
+When the ``block`` is local to a :command:`foreach` or :command:`while`
+command, the commands :command:`break` and :command:`continue` can be used
+inside this block.
+
+.. code-block:: cmake
+
+ while(TRUE)
+ block()
+ ...
+ # the break() command will terminate the while() command
+ break()
+ endblock()
+ endwhile()
+
+
+See Also
+^^^^^^^^
+
+ * :command:`endblock`
+ * :command:`cmake_policy`
diff --git a/Help/command/cmake_language.rst b/Help/command/cmake_language.rst
index d0c7c19..8801a9f 100644
--- a/Help/command/cmake_language.rst
+++ b/Help/command/cmake_language.rst
@@ -51,6 +51,7 @@ is equivalent to
To ensure consistency of the code, the following commands are not allowed:
* ``if`` / ``elseif`` / ``else`` / ``endif``
+ * ``block`` / ``endblock``
* ``while`` / ``endwhile``
* ``foreach`` / ``endforeach``
* ``function`` / ``endfunction``
diff --git a/Help/command/cmake_policy.rst b/Help/command/cmake_policy.rst
index 94060d9..54fc548 100644
--- a/Help/command/cmake_policy.rst
+++ b/Help/command/cmake_policy.rst
@@ -103,6 +103,47 @@ Calls to the :command:`cmake_minimum_required(VERSION)`,
``cmake_policy(VERSION)``, or ``cmake_policy(SET)`` commands
influence only the current top of the policy stack.
+.. versionadded:: 3.25
+ The :command:`block` and :command:`endblock` commands offer a more flexible
+ and more secure way to manage the policy stack. The pop action is done
+ automatically when the :command:`endblock` command is executed, so it avoid
+ to call the :command:`cmake_policy(POP)` command before each
+ :command:`return` command.
+
+ .. code-block:: cmake
+
+ # stack management with cmake_policy()
+ function(my_func)
+ cmake_policy(PUSH)
+ cmake_policy(SET ...)
+ if (<cond1>)
+ ...
+ cmake_policy(POP)
+ return()
+ elseif(<cond2>)
+ ...
+ cmake_policy(POP)
+ return()
+ endif()
+ ...
+ cmake_policy(POP)
+ endfunction()
+
+ # stack management with block()/endblock()
+ function(my_func)
+ block(SCOPE_FOR POLICIES)
+ cmake_policy(SET ...)
+ if (<cond1>)
+ ...
+ return()
+ elseif(<cond2>)
+ ...
+ return()
+ endif()
+ ...
+ endblock()
+ endfunction()
+
Commands created by the :command:`function` and :command:`macro`
commands record policy settings when they are created and
use the pre-record policies when they are invoked. If the function or
diff --git a/Help/command/ctest_test.rst b/Help/command/ctest_test.rst
index f058150..4f9f891 100644
--- a/Help/command/ctest_test.rst
+++ b/Help/command/ctest_test.rst
@@ -175,7 +175,11 @@ The options are:
See also the :variable:`CTEST_CUSTOM_MAXIMUM_PASSED_TEST_OUTPUT_SIZE`,
:variable:`CTEST_CUSTOM_MAXIMUM_FAILED_TEST_OUTPUT_SIZE` and
-:variable:`CTEST_CUSTOM_TEST_OUTPUT_TRUNCATION` variables.
+:variable:`CTEST_CUSTOM_TEST_OUTPUT_TRUNCATION` variables, along with their
+corresponding :manual:`ctest(1)` command line options
+:option:`--test-output-size-passed <ctest --test-output-size-passed>`,
+:option:`--test-output-size-failed <ctest --test-output-size-failed>`, and
+:option:`--test-output-truncation <ctest --test-output-truncation>`.
.. _`Additional Test Measurements`:
@@ -237,7 +241,7 @@ The following example demonstrates how to upload test images to CDash.
"/dir/to/valid_img.gif</CTestMeasurementFile>" << std::endl;
std::cout <<
- "<CTestMeasurementFile type=\"image/png\" name=\"AlgoResult\"> <<
+ "<CTestMeasurementFile type=\"image/png\" name=\"AlgoResult\">" <<
"/dir/to/img.png</CTestMeasurementFile>"
<< std::endl;
diff --git a/Help/command/endblock.rst b/Help/command/endblock.rst
new file mode 100644
index 0000000..3b21c12
--- /dev/null
+++ b/Help/command/endblock.rst
@@ -0,0 +1,11 @@
+endblock
+--------
+
+.. versionadded:: 3.25
+
+Ends a list of commands in a :command:`block` and removes the scopes
+created by the :command:`block` command.
+
+.. code-block:: cmake
+
+ endblock()
diff --git a/Help/command/set.rst b/Help/command/set.rst
index af862e4..aa2ea55 100644
--- a/Help/command/set.rst
+++ b/Help/command/set.rst
@@ -22,12 +22,17 @@ Set Normal Variable
Sets the given ``<variable>`` in the current function or directory scope.
If the ``PARENT_SCOPE`` option is given the variable will be set in
-the scope above the current scope. Each new directory or function
-creates a new scope. This command will set the value of a variable
-into the parent directory or calling function (whichever is applicable
-to the case at hand). The previous state of the variable's value stays the
-same in the current scope (e.g., if it was undefined before, it is still
-undefined and if it had a value, it is still that value).
+the scope above the current scope. Each new directory or :command:`function`
+command creates a new scope. A scope can also be created with the
+:command:`block` command. This command will set the value of a variable into
+the parent directory, calling function or encompassing scope (whichever is
+applicable to the case at hand). The previous state of the variable's value
+stays the same in the current scope (e.g., if it was undefined before, it is
+still undefined and if it had a value, it is still that value).
+
+The :command:`block(PROPAGATE)` command can be used as an alternate method to
+:command:`set(PARENT_SCOPE)` and :command:`unset(PARENT_SCOPE)` commands to
+update the parent scope.
Set Cache Entry
^^^^^^^^^^^^^^^
diff --git a/Help/manual/cmake-commands.7.rst b/Help/manual/cmake-commands.7.rst
index 036fa8f..0f35632 100644
--- a/Help/manual/cmake-commands.7.rst
+++ b/Help/manual/cmake-commands.7.rst
@@ -15,6 +15,7 @@ These commands are always available.
.. toctree::
:maxdepth: 1
+ /command/block
/command/break
/command/cmake_host_system_information
/command/cmake_language
@@ -26,6 +27,7 @@ These commands are always available.
/command/continue
/command/else
/command/elseif
+ /command/endblock
/command/endforeach
/command/endfunction
/command/endif
diff --git a/Help/manual/cmake-variables.7.rst b/Help/manual/cmake-variables.7.rst
index 9fc8a79..1380a179 100644
--- a/Help/manual/cmake-variables.7.rst
+++ b/Help/manual/cmake-variables.7.rst
@@ -301,6 +301,7 @@ Variables that Describe the System
/variable/ANDROID
/variable/APPLE
/variable/BORLAND
+ /variable/BSD
/variable/CMAKE_ANDROID_NDK_VERSION
/variable/CMAKE_CL_64
/variable/CMAKE_COMPILER_2005
@@ -320,6 +321,8 @@ Variables that Describe the System
/variable/CMAKE_SYSTEM_PROCESSOR
/variable/CMAKE_SYSTEM_VERSION
/variable/CYGWIN
+ /variable/DRAGONFLYBSD
+ /variable/FREEBSD
/variable/GHSMULTI
/variable/IOS
/variable/LINUX
@@ -338,6 +341,8 @@ Variables that Describe the System
/variable/MSVC_TOOLSET_VERSION
/variable/MSVC_VERSION
/variable/MSYS
+ /variable/NETBSD
+ /variable/OPENBSD
/variable/UNIX
/variable/WIN32
/variable/WINCE
diff --git a/Help/release/dev/block-command.rst b/Help/release/dev/block-command.rst
new file mode 100644
index 0000000..a740c0b
--- /dev/null
+++ b/Help/release/dev/block-command.rst
@@ -0,0 +1,5 @@
+block-command
+-------------
+
+* CMake language gains the commands :command:`block` and :command:`endblock` to
+ manage specific scopes (policy or variable) for group of commands.
diff --git a/Help/release/dev/bsd-variables.rst b/Help/release/dev/bsd-variables.rst
new file mode 100644
index 0000000..9d59edc
--- /dev/null
+++ b/Help/release/dev/bsd-variables.rst
@@ -0,0 +1,9 @@
+bsd-variables
+-------------
+
+* The :variable:`BSD` variable is set to true when the target system
+ is BSD (DragonFlyBSD, FreeBSD, OpenBSD, or NetBSD)
+* The :variable:`DRAGONFLYBSD` variable is set to true when the target system is DragonFlyBSD.
+* The :variable:`FREEBSD` variable is set to true when the target system is FreeBSD.
+* The :variable:`NETBSD` variable is set to true when the target system is NetBSD.
+* The :variable:`OPENBSD` variable is set to true when the target system is OpenBSD.
diff --git a/Help/variable/BSD.rst b/Help/variable/BSD.rst
new file mode 100644
index 0000000..0b3e5dc
--- /dev/null
+++ b/Help/variable/BSD.rst
@@ -0,0 +1,6 @@
+BSD
+---
+
+.. versionadded:: 3.25
+
+Set to true when the target system is BSD (DragonFlyBSD, FreeBSD, OpenBSD, or NetBSD)
diff --git a/Help/variable/DRAGONFLYBSD.rst b/Help/variable/DRAGONFLYBSD.rst
new file mode 100644
index 0000000..f006156
--- /dev/null
+++ b/Help/variable/DRAGONFLYBSD.rst
@@ -0,0 +1,6 @@
+DRAGONFLYBSD
+------------
+
+.. versionadded:: 3.25
+
+Set to true when the target system is DragonFlyBSD.
diff --git a/Help/variable/FREEBSD.rst b/Help/variable/FREEBSD.rst
new file mode 100644
index 0000000..9990948
--- /dev/null
+++ b/Help/variable/FREEBSD.rst
@@ -0,0 +1,6 @@
+FREEBSD
+-------
+
+.. versionadded:: 3.25
+
+Set to true when the target system is FreeBSD.
diff --git a/Help/variable/NETBSD.rst b/Help/variable/NETBSD.rst
new file mode 100644
index 0000000..e7965f8
--- /dev/null
+++ b/Help/variable/NETBSD.rst
@@ -0,0 +1,6 @@
+NETBSD
+------
+
+.. versionadded:: 3.25
+
+Set to true when the target system is NetBSD.
diff --git a/Help/variable/OPENBSD.rst b/Help/variable/OPENBSD.rst
new file mode 100644
index 0000000..dd9b23d
--- /dev/null
+++ b/Help/variable/OPENBSD.rst
@@ -0,0 +1,6 @@
+OPENBSD
+-------
+
+.. versionadded:: 3.25
+
+Set to true when the target system is OpenBSD.
diff --git a/Modules/Platform/DragonFly.cmake b/Modules/Platform/DragonFly.cmake
index 12e5f3c..d8bc05a 100644
--- a/Modules/Platform/DragonFly.cmake
+++ b/Modules/Platform/DragonFly.cmake
@@ -3,6 +3,8 @@
# see http://archive.netbsd.se/?ml=dfbsd-users&a=2007-07&m=4678361
include(Platform/FreeBSD)
+unset(FREEBSD)
+set(DRAGONFLYBSD 1)
# DragonFly BSD requires -z origin to enable $ORIGIN expansion in RPATH.
# This is not required for FreeBSD since 10.2-RELEASE.
diff --git a/Modules/Platform/FreeBSD.cmake b/Modules/Platform/FreeBSD.cmake
index bd5a786..e968a78 100644
--- a/Modules/Platform/FreeBSD.cmake
+++ b/Modules/Platform/FreeBSD.cmake
@@ -1,3 +1,5 @@
+set(FREEBSD 1)
+set(BSD 1)
set(CMAKE_DL_LIBS "")
set(CMAKE_C_COMPILE_OPTIONS_PIC "-fPIC")
set(CMAKE_C_COMPILE_OPTIONS_PIE "-fPIE")
diff --git a/Modules/Platform/NetBSD.cmake b/Modules/Platform/NetBSD.cmake
index ab85923..a64bf0b 100644
--- a/Modules/Platform/NetBSD.cmake
+++ b/Modules/Platform/NetBSD.cmake
@@ -1,3 +1,5 @@
+set(NETBSD 1)
+set(BSD 1)
set(CMAKE_DL_LIBS "")
set(CMAKE_C_COMPILE_OPTIONS_PIC "-fPIC")
set(CMAKE_C_COMPILE_OPTIONS_PIE "-fPIE")
diff --git a/Modules/Platform/OpenBSD.cmake b/Modules/Platform/OpenBSD.cmake
index 97e2a6a..f6b955a 100644
--- a/Modules/Platform/OpenBSD.cmake
+++ b/Modules/Platform/OpenBSD.cmake
@@ -1,4 +1,6 @@
include(Platform/NetBSD)
+unset(NETBSD)
+set(OPENBSD 1)
# On OpenBSD, the compile time linker does not share it's configuration with
# the runtime linker. This will extract the library search paths from the
diff --git a/Modules/Platform/kFreeBSD.cmake b/Modules/Platform/kFreeBSD.cmake
index 01ddfd3..09c240d 100644
--- a/Modules/Platform/kFreeBSD.cmake
+++ b/Modules/Platform/kFreeBSD.cmake
@@ -1,5 +1,5 @@
-# kFreeBSD looks just like Linux.
+# kFreeBSD is a Debian GNU distribution with a kernel from FreeBSD,
+# and should be marked as LINUX
include(Platform/Linux)
-unset(LINUX)
set(CMAKE_LIBRARY_ARCHITECTURE_REGEX "[a-z0-9_]+(-[a-z0-9_]+)?-kfreebsd-gnu[a-z0-9_]*")
diff --git a/Source/CMakeLists.txt b/Source/CMakeLists.txt
index fe92716..b6f7c85 100644
--- a/Source/CMakeLists.txt
+++ b/Source/CMakeLists.txt
@@ -571,6 +571,8 @@ set(SRCS
cmFindProgramCommand.h
cmForEachCommand.cxx
cmForEachCommand.h
+ cmBlockCommand.cxx
+ cmBlockCommand.h
cmFunctionBlocker.cxx
cmFunctionBlocker.h
cmFunctionCommand.cxx
diff --git a/Source/CMakeVersion.cmake b/Source/CMakeVersion.cmake
index 6ba211e..58d1769 100644
--- a/Source/CMakeVersion.cmake
+++ b/Source/CMakeVersion.cmake
@@ -1,7 +1,7 @@
# CMake version number components.
set(CMake_VERSION_MAJOR 3)
set(CMake_VERSION_MINOR 24)
-set(CMake_VERSION_PATCH 20220819)
+set(CMake_VERSION_PATCH 20220823)
#set(CMake_VERSION_RC 0)
set(CMake_VERSION_IS_DIRTY 0)
diff --git a/Source/cmBlockCommand.cxx b/Source/cmBlockCommand.cxx
new file mode 100644
index 0000000..c358aa2
--- /dev/null
+++ b/Source/cmBlockCommand.cxx
@@ -0,0 +1,200 @@
+/* Distributed under the OSI-approved BSD 3-Clause License. See accompanying
+ file Copyright.txt or https://cmake.org/licensing for details. */
+
+#include "cmBlockCommand.h"
+
+#include <cstdint> // IWYU pragma: keep
+#include <utility>
+
+#include <cm/memory>
+#include <cm/optional>
+#include <cm/string_view>
+#include <cmext/enum_set>
+#include <cmext/string_view>
+
+#include "cmArgumentParser.h"
+#include "cmArgumentParserTypes.h"
+#include "cmExecutionStatus.h"
+#include "cmFunctionBlocker.h"
+#include "cmListFileCache.h"
+#include "cmMakefile.h"
+#include "cmStringAlgorithms.h"
+#include "cmSystemTools.h"
+
+namespace {
+enum class ScopeType : std::uint8_t
+{
+ VARIABLES,
+ POLICIES
+};
+using ScopeSet = cm::enum_set<ScopeType>;
+
+class BlockScopePushPop
+{
+public:
+ BlockScopePushPop(cmMakefile* m, const ScopeSet& scopes);
+ ~BlockScopePushPop() = default;
+
+ BlockScopePushPop(const BlockScopePushPop&) = delete;
+ BlockScopePushPop& operator=(const BlockScopePushPop&) = delete;
+
+private:
+ std::unique_ptr<cmMakefile::PolicyPushPop> PolicyScope;
+ std::unique_ptr<cmMakefile::VariablePushPop> VariableScope;
+};
+
+BlockScopePushPop::BlockScopePushPop(cmMakefile* mf, const ScopeSet& scopes)
+{
+ if (scopes.contains(ScopeType::POLICIES)) {
+ this->PolicyScope = cm::make_unique<cmMakefile::PolicyPushPop>(mf);
+ }
+ if (scopes.contains(ScopeType::VARIABLES)) {
+ this->VariableScope = cm::make_unique<cmMakefile::VariablePushPop>(mf);
+ }
+}
+
+class cmBlockFunctionBlocker : public cmFunctionBlocker
+{
+public:
+ cmBlockFunctionBlocker(cmMakefile* mf, const ScopeSet& scopes,
+ std::vector<std::string> variableNames);
+ ~cmBlockFunctionBlocker() override;
+
+ cm::string_view StartCommandName() const override { return "block"_s; }
+ cm::string_view EndCommandName() const override { return "endblock"_s; }
+
+ bool EndCommandSupportsArguments() const override { return false; }
+
+ bool ArgumentsMatch(cmListFileFunction const& lff,
+ cmMakefile& mf) const override;
+
+ bool Replay(std::vector<cmListFileFunction> functions,
+ cmExecutionStatus& inStatus) override;
+
+private:
+ cmMakefile* Makefile;
+ BlockScopePushPop BlockScope;
+ std::vector<std::string> VariableNames;
+};
+
+cmBlockFunctionBlocker::cmBlockFunctionBlocker(
+ cmMakefile* const mf, const ScopeSet& scopes,
+ std::vector<std::string> variableNames)
+ : Makefile{ mf }
+ , BlockScope{ mf, scopes }
+ , VariableNames{ std::move(variableNames) }
+{
+}
+
+cmBlockFunctionBlocker::~cmBlockFunctionBlocker()
+{
+ for (auto const& varName : this->VariableNames) {
+ if (this->Makefile->IsNormalDefinitionSet(varName)) {
+ this->Makefile->RaiseScope(varName,
+ this->Makefile->GetDefinition(varName));
+ } else {
+ // unset variable in parent scope
+ this->Makefile->RaiseScope(varName, nullptr);
+ }
+ }
+}
+
+bool cmBlockFunctionBlocker::ArgumentsMatch(cmListFileFunction const& lff,
+ cmMakefile&) const
+{
+ // no arguments expected for endblock()
+ // but this method should not be called because EndCommandHasArguments()
+ // returns false.
+ return lff.Arguments().empty();
+}
+
+bool cmBlockFunctionBlocker::Replay(std::vector<cmListFileFunction> functions,
+ cmExecutionStatus& inStatus)
+{
+ auto& mf = inStatus.GetMakefile();
+
+ // Invoke all the functions that were collected in the block.
+ for (cmListFileFunction const& fn : functions) {
+ cmExecutionStatus status(mf);
+ mf.ExecuteCommand(fn, status);
+ if (status.GetReturnInvoked()) {
+ inStatus.SetReturnInvoked();
+ return true;
+ }
+ if (status.GetBreakInvoked()) {
+ inStatus.SetBreakInvoked();
+ return true;
+ }
+ if (status.GetContinueInvoked()) {
+ inStatus.SetContinueInvoked();
+ return true;
+ }
+ if (cmSystemTools::GetFatalErrorOccurred()) {
+ return true;
+ }
+ }
+ return true;
+}
+
+} // anonymous namespace
+
+bool cmBlockCommand(std::vector<std::string> const& args,
+ cmExecutionStatus& status)
+{
+ struct Arguments : public ArgumentParser::ParseResult
+ {
+ cm::optional<ArgumentParser::NonEmpty<std::vector<std::string>>> ScopeFor;
+ ArgumentParser::MaybeEmpty<std::vector<std::string>> Propagate;
+ };
+ static auto const parser = cmArgumentParser<Arguments>{}
+ .Bind("SCOPE_FOR"_s, &Arguments::ScopeFor)
+ .Bind("PROPAGATE"_s, &Arguments::Propagate);
+ std::vector<std::string> unrecognizedArguments;
+ auto parsedArgs = parser.Parse(args, &unrecognizedArguments);
+
+ if (!unrecognizedArguments.empty()) {
+ status.SetError(cmStrCat("called with unsupported argument \"",
+ unrecognizedArguments[0], '"'));
+ cmSystemTools::SetFatalErrorOccurred();
+ return false;
+ }
+
+ if (parsedArgs.MaybeReportError(status.GetMakefile())) {
+ cmSystemTools::SetFatalErrorOccurred();
+ return true;
+ }
+
+ ScopeSet scopes;
+
+ if (parsedArgs.ScopeFor) {
+ for (auto const& scope : *parsedArgs.ScopeFor) {
+ if (scope == "VARIABLES"_s) {
+ scopes.insert(ScopeType::VARIABLES);
+ continue;
+ }
+ if (scope == "POLICIES"_s) {
+ scopes.insert(ScopeType::POLICIES);
+ continue;
+ }
+ status.SetError(cmStrCat("SCOPE_FOR unsupported scope \"", scope, '"'));
+ cmSystemTools::SetFatalErrorOccurred();
+ return false;
+ }
+ } else {
+ scopes = { ScopeType::VARIABLES, ScopeType::POLICIES };
+ }
+ if (!scopes.contains(ScopeType::VARIABLES) &&
+ !parsedArgs.Propagate.empty()) {
+ status.SetError(
+ "PROPAGATE cannot be specified without a new scope for VARIABLES");
+ cmSystemTools::SetFatalErrorOccurred();
+ return false;
+ }
+
+ // create a function blocker
+ auto fb = cm::make_unique<cmBlockFunctionBlocker>(
+ &status.GetMakefile(), scopes, parsedArgs.Propagate);
+ status.GetMakefile().AddFunctionBlocker(std::move(fb));
+
+ return true;
+}
diff --git a/Source/cmBlockCommand.h b/Source/cmBlockCommand.h
new file mode 100644
index 0000000..5fd8f42
--- /dev/null
+++ b/Source/cmBlockCommand.h
@@ -0,0 +1,14 @@
+/* Distributed under the OSI-approved BSD 3-Clause License. See accompanying
+ file Copyright.txt or https://cmake.org/licensing for details. */
+#pragma once
+
+#include "cmConfigure.h" // IWYU pragma: keep
+
+#include <string>
+#include <vector>
+
+class cmExecutionStatus;
+
+/// Starts block() ... endblock() block
+bool cmBlockCommand(std::vector<std::string> const& args,
+ cmExecutionStatus& status);
diff --git a/Source/cmCMakeLanguageCommand.cxx b/Source/cmCMakeLanguageCommand.cxx
index 76561c3..68e658c 100644
--- a/Source/cmCMakeLanguageCommand.cxx
+++ b/Source/cmCMakeLanguageCommand.cxx
@@ -36,13 +36,14 @@ bool FatalError(cmExecutionStatus& status, std::string const& error)
return false;
}
-std::array<cm::static_string_view, 12> InvalidCommands{
+std::array<cm::static_string_view, 14> InvalidCommands{
{ // clang-format off
"function"_s, "endfunction"_s,
"macro"_s, "endmacro"_s,
"if"_s, "elseif"_s, "else"_s, "endif"_s,
"while"_s, "endwhile"_s,
- "foreach"_s, "endforeach"_s
+ "foreach"_s, "endforeach"_s,
+ "block"_s, "endblock"_s
} // clang-format on
};
diff --git a/Source/cmCommands.cxx b/Source/cmCommands.cxx
index 5e616b3..3bc4f0e 100644
--- a/Source/cmCommands.cxx
+++ b/Source/cmCommands.cxx
@@ -14,6 +14,7 @@
#include "cmAddLibraryCommand.h"
#include "cmAddSubDirectoryCommand.h"
#include "cmAddTestCommand.h"
+#include "cmBlockCommand.h"
#include "cmBreakCommand.h"
#include "cmBuildCommand.h"
#include "cmCMakeLanguageCommand.h"
@@ -126,6 +127,7 @@ void GetScriptingCommands(cmState* state)
state->AddFlowControlCommand("macro", cmMacroCommand);
state->AddFlowControlCommand("return", cmReturnCommand);
state->AddFlowControlCommand("while", cmWhileCommand);
+ state->AddFlowControlCommand("block", cmBlockCommand);
state->AddBuiltinCommand("cmake_language", cmCMakeLanguageCommand);
state->AddBuiltinCommand("cmake_minimum_required", cmCMakeMinimumRequired);
@@ -198,6 +200,10 @@ void GetScriptingCommands(cmState* state)
"An ENDWHILE command was found outside of a proper "
"WHILE ENDWHILE structure. Or its arguments did not "
"match the opening WHILE command.");
+ state->AddUnexpectedFlowControlCommand(
+ "endblock",
+ "An ENDBLOCK command was found outside of a proper "
+ "BLOCK ENDBLOCK structure.");
#if !defined(CMAKE_BOOTSTRAP)
state->AddBuiltinCommand("cmake_host_system_information",
diff --git a/Source/cmFunctionBlocker.cxx b/Source/cmFunctionBlocker.cxx
index 40e692d..523482a 100644
--- a/Source/cmFunctionBlocker.cxx
+++ b/Source/cmFunctionBlocker.cxx
@@ -24,10 +24,11 @@ bool cmFunctionBlocker::IsFunctionBlocked(const cmListFileFunction& lff,
auto self = mf.RemoveFunctionBlocker();
assert(self.get() == this);
- if (!this->ArgumentsMatch(lff, mf)) {
- cmListFileContext const& lfc = this->GetStartingContext();
- cmListFileContext closingContext =
- cmListFileContext::FromListFileFunction(lff, lfc.FilePath);
+ cmListFileContext const& lfc = this->GetStartingContext();
+ cmListFileContext closingContext =
+ cmListFileContext::FromListFileFunction(lff, lfc.FilePath);
+ if (this->EndCommandSupportsArguments() &&
+ !this->ArgumentsMatch(lff, mf)) {
std::ostringstream e;
/* clang-format off */
e << "A logical block opening on the line\n"
@@ -37,6 +38,15 @@ bool cmFunctionBlocker::IsFunctionBlocked(const cmListFileFunction& lff,
<< "with mis-matching arguments.";
/* clang-format on */
mf.IssueMessage(MessageType::AUTHOR_WARNING, e.str());
+ } else if (!this->EndCommandSupportsArguments() &&
+ !lff.Arguments().empty()) {
+ std::ostringstream e;
+ /* clang-format off */
+ e << "A logical block closing on the line\n"
+ " " << closingContext << "\n"
+ "has unexpected arguments.";
+ /* clang-format on */
+ mf.IssueMessage(MessageType::AUTHOR_WARNING, e.str());
}
return this->Replay(std::move(this->Functions), status);
diff --git a/Source/cmFunctionBlocker.h b/Source/cmFunctionBlocker.h
index 38abeba..3e096f2 100644
--- a/Source/cmFunctionBlocker.h
+++ b/Source/cmFunctionBlocker.h
@@ -38,6 +38,8 @@ private:
virtual cm::string_view StartCommandName() const = 0;
virtual cm::string_view EndCommandName() const = 0;
+ virtual bool EndCommandSupportsArguments() const { return true; }
+
virtual bool ArgumentsMatch(cmListFileFunction const& lff,
cmMakefile& mf) const = 0;
diff --git a/Source/cmListFileCache.cxx b/Source/cmListFileCache.cxx
index 91157cb..6270c82 100644
--- a/Source/cmListFileCache.cxx
+++ b/Source/cmListFileCache.cxx
@@ -347,6 +347,7 @@ enum class NestingStateEnum
Foreach,
Function,
Macro,
+ Block
};
struct NestingState
@@ -434,6 +435,16 @@ cm::optional<cmListFileContext> cmListFileParser::CheckNesting() const
return cmListFileContext::FromListFileFunction(func, this->FileName);
}
stack.pop_back();
+ } else if (name == "block") {
+ stack.push_back({
+ NestingStateEnum::Block,
+ cmListFileContext::FromListFileFunction(func, this->FileName),
+ });
+ } else if (name == "endblock") {
+ if (!TopIs(stack, NestingStateEnum::Block)) {
+ return cmListFileContext::FromListFileFunction(func, this->FileName);
+ }
+ stack.pop_back();
}
}
diff --git a/Source/cmLocalGenerator.cxx b/Source/cmLocalGenerator.cxx
index 64f8996..b44d2a0 100644
--- a/Source/cmLocalGenerator.cxx
+++ b/Source/cmLocalGenerator.cxx
@@ -15,6 +15,7 @@
#include <vector>
#include <cm/memory>
+#include <cm/optional>
#include <cm/string_view>
#include <cmext/algorithm>
#include <cmext/string_view>
@@ -2686,7 +2687,7 @@ void cmLocalGenerator::AddPchDependencies(cmGeneratorTarget* target)
cmStrCat(linkerProperty, configUpper),
cmStrCat(" ",
this->ConvertToOutputFormat(pchSourceObj, SHELL)),
- true);
+ cm::nullopt, true);
} else if (reuseTarget->GetType() ==
cmStateEnums::OBJECT_LIBRARY) {
// FIXME: This can propagate more than one level, unlike
diff --git a/Source/cmMakefile.cxx b/Source/cmMakefile.cxx
index 208d907..b228e2b 100644
--- a/Source/cmMakefile.cxx
+++ b/Source/cmMakefile.cxx
@@ -4543,6 +4543,19 @@ bool cmMakefile::SetPolicyVersion(std::string const& version_min,
cmPolicies::WarnCompat::On);
}
+cmMakefile::VariablePushPop::VariablePushPop(cmMakefile* m)
+ : Makefile(m)
+{
+ this->Makefile->StateSnapshot =
+ this->Makefile->GetState()->CreateVariableScopeSnapshot(
+ this->Makefile->StateSnapshot);
+}
+
+cmMakefile::VariablePushPop::~VariablePushPop()
+{
+ this->Makefile->PopSnapshot();
+}
+
bool cmMakefile::HasCMP0054AlreadyBeenReported(
cmListFileContext const& context) const
{
diff --git a/Source/cmMakefile.h b/Source/cmMakefile.h
index df40c82..10432a8 100644
--- a/Source/cmMakefile.h
+++ b/Source/cmMakefile.h
@@ -376,6 +376,20 @@ public:
};
friend class PolicyPushPop;
+ /** Helper class to push and pop variables scopes automatically. */
+ class VariablePushPop
+ {
+ public:
+ VariablePushPop(cmMakefile* m);
+ ~VariablePushPop();
+
+ VariablePushPop(VariablePushPop const&) = delete;
+ VariablePushPop& operator=(VariablePushPop const&) = delete;
+
+ private:
+ cmMakefile* Makefile;
+ };
+
/**
* Determine if the given context, name pair has already been reported
* in context of CMP0054.
@@ -862,6 +876,10 @@ public:
void PushScope();
void PopScope();
void RaiseScope(const std::string& var, const char* value);
+ void RaiseScope(const std::string& var, cmValue value)
+ {
+ this->RaiseScope(var, value.GetCStr());
+ }
// push and pop loop scopes
void PushLoopBlockBarrier();
diff --git a/Source/cmQtAutoGenInitializer.cxx b/Source/cmQtAutoGenInitializer.cxx
index 40f3ab5..6c500b0 100644
--- a/Source/cmQtAutoGenInitializer.cxx
+++ b/Source/cmQtAutoGenInitializer.cxx
@@ -1847,8 +1847,7 @@ void cmQtAutoGenInitializer::AddToSourceGroup(std::string const& fileName,
void cmQtAutoGenInitializer::AddCleanFile(std::string const& fileName)
{
- this->GenTarget->Target->AppendProperty("ADDITIONAL_CLEAN_FILES", fileName,
- false);
+ this->GenTarget->Target->AppendProperty("ADDITIONAL_CLEAN_FILES", fileName);
}
void cmQtAutoGenInitializer::ConfigFileNames(ConfigString& configString,
diff --git a/Source/cmSetPropertyCommand.cxx b/Source/cmSetPropertyCommand.cxx
index db10cd4..521cf63 100644
--- a/Source/cmSetPropertyCommand.cxx
+++ b/Source/cmSetPropertyCommand.cxx
@@ -9,6 +9,7 @@
#include "cmExecutionStatus.h"
#include "cmGlobalGenerator.h"
#include "cmInstalledFile.h"
+#include "cmListFileCache.h"
#include "cmMakefile.h"
#include "cmMessageType.h"
#include "cmPolicies.h"
@@ -561,7 +562,8 @@ bool HandleTarget(cmTarget* target, cmMakefile& makefile,
{
// Set or append the property.
if (appendMode) {
- target->AppendProperty(propertyName, propertyValue, appendAsString);
+ target->AppendProperty(propertyName, propertyValue,
+ makefile.GetBacktrace(), appendAsString);
} else {
if (remove) {
target->SetProperty(propertyName, nullptr);
diff --git a/Source/cmStandardLevelResolver.cxx b/Source/cmStandardLevelResolver.cxx
index 785f356..be15288 100644
--- a/Source/cmStandardLevelResolver.cxx
+++ b/Source/cmStandardLevelResolver.cxx
@@ -18,6 +18,7 @@
#include "cmGeneratorExpression.h"
#include "cmGeneratorTarget.h"
#include "cmGlobalGenerator.h"
+#include "cmListFileCache.h"
#include "cmMakefile.h"
#include "cmMessageType.h"
#include "cmPolicies.h"
@@ -416,7 +417,8 @@ bool cmStandardLevelResolver::AddRequiredTargetFeature(
cmTarget* target, const std::string& feature, std::string* error) const
{
if (cmGeneratorExpression::Find(feature) != std::string::npos) {
- target->AppendProperty("COMPILE_FEATURES", feature);
+ target->AppendProperty("COMPILE_FEATURES", feature,
+ this->Makefile->GetBacktrace());
return true;
}
@@ -426,7 +428,8 @@ bool cmStandardLevelResolver::AddRequiredTargetFeature(
return false;
}
- target->AppendProperty("COMPILE_FEATURES", feature);
+ target->AppendProperty("COMPILE_FEATURES", feature,
+ this->Makefile->GetBacktrace());
// FIXME: Add a policy to avoid updating the <LANG>_STANDARD target
// property due to COMPILE_FEATURES. The language standard selection
diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index eafea05..050206a 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -295,6 +295,12 @@ public:
cm::string_view fileSetType) const;
cmValue GetFileSetPaths(cmTarget const* self, std::string const& fileSetName,
cm::string_view fileSetType) const;
+
+ cmListFileBacktrace GetBacktrace(
+ cm::optional<cmListFileBacktrace> const& bt) const
+ {
+ return bt ? *bt : this->Makefile->GetBacktrace();
+ }
};
cmTargetInternals::cmTargetInternals()
@@ -1243,7 +1249,8 @@ void cmTarget::AddLinkLibrary(cmMakefile& mf, std::string const& lib,
? targetNameGenex(lib)
: lib;
this->AppendProperty("LINK_LIBRARIES",
- this->GetDebugGeneratorExpressions(libName, llt));
+ this->GetDebugGeneratorExpressions(libName, llt),
+ mf.GetBacktrace());
}
if (cmGeneratorExpression::Find(lib) != std::string::npos ||
@@ -1684,7 +1691,9 @@ void cmTarget::StoreProperty(const std::string& prop, ValueType value)
}
void cmTarget::AppendProperty(const std::string& prop,
- const std::string& value, bool asString)
+ const std::string& value,
+ cm::optional<cmListFileBacktrace> const& bt,
+ bool asString)
{
if (prop == "NAME") {
this->impl->Makefile->IssueMessage(MessageType::FATAL_ERROR,
@@ -1715,32 +1724,32 @@ void cmTarget::AppendProperty(const std::string& prop,
}
if (prop == "INCLUDE_DIRECTORIES") {
if (!value.empty()) {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->IncludeDirectoriesEntries.emplace_back(value, lfbt);
}
} else if (prop == "COMPILE_OPTIONS") {
if (!value.empty()) {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->CompileOptionsEntries.emplace_back(value, lfbt);
}
} else if (prop == "COMPILE_FEATURES") {
if (!value.empty()) {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->CompileFeaturesEntries.emplace_back(value, lfbt);
}
} else if (prop == "COMPILE_DEFINITIONS") {
if (!value.empty()) {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->CompileDefinitionsEntries.emplace_back(value, lfbt);
}
} else if (prop == "LINK_OPTIONS") {
if (!value.empty()) {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->LinkOptionsEntries.emplace_back(value, lfbt);
}
} else if (prop == "LINK_DIRECTORIES") {
if (!value.empty()) {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->LinkDirectoriesEntries.emplace_back(value, lfbt);
}
} else if (prop == "PRECOMPILE_HEADERS") {
@@ -1753,32 +1762,32 @@ void cmTarget::AppendProperty(const std::string& prop,
return;
}
if (!value.empty()) {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->PrecompileHeadersEntries.emplace_back(value, lfbt);
}
} else if (prop == "LINK_LIBRARIES") {
if (!value.empty()) {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->LinkImplementationPropertyEntries.emplace_back(value, lfbt);
}
} else if (prop == propINTERFACE_LINK_LIBRARIES) {
if (!value.empty()) {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->LinkInterfacePropertyEntries.emplace_back(value, lfbt);
}
} else if (prop == propINTERFACE_LINK_LIBRARIES_DIRECT) {
if (!value.empty()) {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->LinkInterfaceDirectPropertyEntries.emplace_back(value, lfbt);
}
} else if (prop == propINTERFACE_LINK_LIBRARIES_DIRECT_EXCLUDE) {
if (!value.empty()) {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->LinkInterfaceDirectExcludePropertyEntries.emplace_back(value,
lfbt);
}
} else if (prop == "SOURCES") {
- cmListFileBacktrace lfbt = this->impl->Makefile->GetBacktrace();
+ cmListFileBacktrace lfbt = this->impl->GetBacktrace(bt);
this->impl->SourceEntries.emplace_back(value, lfbt);
} else if (cmHasLiteralPrefix(prop, "IMPORTED_LIBNAME")) {
this->impl->Makefile->IssueMessage(
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 3d0a06b..1550f5b 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -185,8 +185,10 @@ public:
{
this->SetProperty(prop, cmValue(value));
}
- void AppendProperty(const std::string& prop, const std::string& value,
- bool asString = false);
+ void AppendProperty(
+ const std::string& prop, const std::string& value,
+ cm::optional<cmListFileBacktrace> const& bt = cm::nullopt,
+ bool asString = false);
//! Might return a nullptr if the property is not set or invalid
cmValue GetProperty(const std::string& prop) const;
//! Always returns a valid pointer
diff --git a/Source/cmTargetCompileDefinitionsCommand.cxx b/Source/cmTargetCompileDefinitionsCommand.cxx
index b56b245..268bfac 100644
--- a/Source/cmTargetCompileDefinitionsCommand.cxx
+++ b/Source/cmTargetCompileDefinitionsCommand.cxx
@@ -2,6 +2,7 @@
file Copyright.txt or https://cmake.org/licensing for details. */
#include "cmTargetCompileDefinitionsCommand.h"
+#include "cmListFileCache.h"
#include "cmMakefile.h"
#include "cmMessageType.h"
#include "cmStringAlgorithms.h"
@@ -28,7 +29,8 @@ private:
const std::vector<std::string>& content,
bool /*prepend*/, bool /*system*/) override
{
- tgt->AppendProperty("COMPILE_DEFINITIONS", this->Join(content));
+ tgt->AppendProperty("COMPILE_DEFINITIONS", this->Join(content),
+ this->Makefile->GetBacktrace());
return true; // Successfully handled.
}
diff --git a/Source/cmTargetIncludeDirectoriesCommand.cxx b/Source/cmTargetIncludeDirectoriesCommand.cxx
index b4b4319..cb83873 100644
--- a/Source/cmTargetIncludeDirectoriesCommand.cxx
+++ b/Source/cmTargetIncludeDirectoriesCommand.cxx
@@ -88,7 +88,8 @@ void TargetIncludeDirectoriesImpl::HandleInterfaceContent(
system);
if (system) {
std::string joined = this->Join(content);
- tgt->AppendProperty("INTERFACE_SYSTEM_INCLUDE_DIRECTORIES", joined);
+ tgt->AppendProperty("INTERFACE_SYSTEM_INCLUDE_DIRECTORIES", joined,
+ this->Makefile->GetBacktrace());
}
}
diff --git a/Source/cmTargetLinkLibrariesCommand.cxx b/Source/cmTargetLinkLibrariesCommand.cxx
index ba901d0..fb03b62 100644
--- a/Source/cmTargetLinkLibrariesCommand.cxx
+++ b/Source/cmTargetLinkLibrariesCommand.cxx
@@ -625,7 +625,7 @@ bool TLL::HandleLibrary(ProcessingState currentProcessingState,
void TLL::AppendProperty(std::string const& prop, std::string const& value)
{
this->AffectsProperty(prop);
- this->Target->AppendProperty(prop, value);
+ this->Target->AppendProperty(prop, value, this->Makefile.GetBacktrace());
}
void TLL::AffectsProperty(std::string const& prop)
@@ -636,14 +636,16 @@ void TLL::AffectsProperty(std::string const& prop)
// Add a wrapper to the expression to tell LookupLinkItem to look up
// names in the caller's directory.
if (this->Props.insert(prop).second) {
- this->Target->AppendProperty(prop, this->DirectoryId);
+ this->Target->AppendProperty(prop, this->DirectoryId,
+ this->Makefile.GetBacktrace());
}
}
TLL::~TLL()
{
for (std::string const& prop : this->Props) {
- this->Target->AppendProperty(prop, CMAKE_DIRECTORY_ID_SEP);
+ this->Target->AppendProperty(prop, CMAKE_DIRECTORY_ID_SEP,
+ this->Makefile.GetBacktrace());
}
}
diff --git a/Source/cmTargetPrecompileHeadersCommand.cxx b/Source/cmTargetPrecompileHeadersCommand.cxx
index a5066cc..4dd158d 100644
--- a/Source/cmTargetPrecompileHeadersCommand.cxx
+++ b/Source/cmTargetPrecompileHeadersCommand.cxx
@@ -5,6 +5,7 @@
#include <utility>
#include "cmGeneratorExpression.h"
+#include "cmListFileCache.h"
#include "cmMakefile.h"
#include "cmMessageType.h"
#include "cmStringAlgorithms.h"
@@ -48,7 +49,8 @@ private:
{
std::string const& base = this->Makefile->GetCurrentSourceDirectory();
tgt->AppendProperty("PRECOMPILE_HEADERS",
- this->Join(ConvertToAbsoluteContent(content, base)));
+ this->Join(ConvertToAbsoluteContent(content, base)),
+ this->Makefile->GetBacktrace());
return true;
}
diff --git a/Source/cmTargetSourcesCommand.cxx b/Source/cmTargetSourcesCommand.cxx
index e2b0213..53e25b5 100644
--- a/Source/cmTargetSourcesCommand.cxx
+++ b/Source/cmTargetSourcesCommand.cxx
@@ -79,7 +79,8 @@ private:
{
tgt->AppendProperty("SOURCES",
this->Join(this->ConvertToAbsoluteContent(
- tgt, content, IsInterface::No, CheckCMP0076::Yes)));
+ tgt, content, IsInterface::No, CheckCMP0076::Yes)),
+ this->Makefile->GetBacktrace());
return true; // Successfully handled.
}
@@ -324,11 +325,13 @@ bool TargetSourcesImpl::HandleOneFileSet(
cmStrCat("$<BUILD_INTERFACE:", dir, ">");
if (cmFileSetVisibilityIsForSelf(visibility)) {
this->Target->AppendProperty("INCLUDE_DIRECTORIES",
- interfaceDirectoriesGenex);
+ interfaceDirectoriesGenex,
+ this->Makefile->GetBacktrace());
}
if (cmFileSetVisibilityIsForInterface(visibility)) {
this->Target->AppendProperty("INTERFACE_INCLUDE_DIRECTORIES",
- interfaceDirectoriesGenex);
+ interfaceDirectoriesGenex,
+ this->Makefile->GetBacktrace());
}
}
}
diff --git a/Tests/CMakeLib/testCMExtEnumSet.cxx b/Tests/CMakeLib/testCMExtEnumSet.cxx
index 64c437b..dbb0a54 100644
--- a/Tests/CMakeLib/testCMExtEnumSet.cxx
+++ b/Tests/CMakeLib/testCMExtEnumSet.cxx
@@ -191,6 +191,15 @@ void testEdition()
++failed;
}
}
+ {
+ cm::enum_set<Test> testSet1;
+ cm::enum_set<Test> testSet2{ Test::A, Test::C, Test::B };
+
+ testSet1 = { Test::A, Test::C, Test::B };
+ if (testSet1.size() != 3 || testSet1 != testSet2) {
+ ++failed;
+ }
+ }
}
}
diff --git a/Tests/RunCMake/CMakeLists.txt b/Tests/RunCMake/CMakeLists.txt
index 2485a7e..542742c 100644
--- a/Tests/RunCMake/CMakeLists.txt
+++ b/Tests/RunCMake/CMakeLists.txt
@@ -456,6 +456,7 @@ add_RunCMake_test(find_path)
add_RunCMake_test(find_program -DCMAKE_SYSTEM_NAME=${CMAKE_SYSTEM_NAME})
add_RunCMake_test(foreach)
add_RunCMake_test(function)
+add_RunCMake_test(block)
add_RunCMake_test(get_filename_component)
add_RunCMake_test(get_property)
add_RunCMake_test(if)
diff --git a/Tests/RunCMake/FileAPI/CMakeLists.txt b/Tests/RunCMake/FileAPI/CMakeLists.txt
index 44025d3..9a66cde 100644
--- a/Tests/RunCMake/FileAPI/CMakeLists.txt
+++ b/Tests/RunCMake/FileAPI/CMakeLists.txt
@@ -1,3 +1,3 @@
-cmake_minimum_required(VERSION 3.12)
+cmake_minimum_required(VERSION 3.13)
project(${RunCMake_TEST} NONE)
include(${RunCMake_TEST}.cmake)
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-check.py b/Tests/RunCMake/FileAPI/codemodel-v2-check.py
index 01a004c..b7623de 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-check.py
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-check.py
@@ -664,6 +664,7 @@ def gen_check_directories(c, g):
read_codemodel_json_data("directories/dir_dir.json"),
read_codemodel_json_data("directories/external.json"),
read_codemodel_json_data("directories/fileset.json"),
+ read_codemodel_json_data("directories/subdir.json"),
]
if matches(g["name"], "^Visual Studio "):
@@ -722,6 +723,7 @@ def gen_check_targets(c, g, inSource):
read_codemodel_json_data("targets/c_shared_exe.json"),
read_codemodel_json_data("targets/c_static_lib.json"),
read_codemodel_json_data("targets/c_static_exe.json"),
+ read_codemodel_json_data("targets/c_subdir.json"),
read_codemodel_json_data("targets/all_build_cxx.json"),
read_codemodel_json_data("targets/zero_check_cxx.json"),
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/alias.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/alias.json
index 6514910..de8b177 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/alias.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/alias.json
@@ -10,7 +10,7 @@
"^cxx_alias_exe::@53632cba2752272bb008$"
],
"projectName": "Alias",
- "minimumCMakeVersion": "3.12",
+ "minimumCMakeVersion": "3.13",
"hasInstallRule": null,
"installers": []
}
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/custom.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/custom.json
index c89e4f9..e57191c 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/custom.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/custom.json
@@ -10,7 +10,7 @@
"^custom_tgt::@c11385ffed57b860da63$"
],
"projectName": "Custom",
- "minimumCMakeVersion": "3.12",
+ "minimumCMakeVersion": "3.13",
"hasInstallRule": null,
"installers": []
}
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/cxx.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/cxx.json
index 8052c1a..28f2b99 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/cxx.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/cxx.json
@@ -16,7 +16,7 @@
"^cxx_static_lib::@a56b12a3f5c0529fb296$"
],
"projectName": "Cxx",
- "minimumCMakeVersion": "3.12",
+ "minimumCMakeVersion": "3.13",
"hasInstallRule": true,
"installers": [
{
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/dir.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/dir.json
index 8509f08..2a3756e 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/dir.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/dir.json
@@ -7,7 +7,7 @@
],
"targetIds": null,
"projectName": "codemodel-v2",
- "minimumCMakeVersion": "3.12",
+ "minimumCMakeVersion": "3.13",
"hasInstallRule": null,
"installers": []
}
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/dir_dir.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/dir_dir.json
index 27184cd..12677f2 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/dir_dir.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/dir_dir.json
@@ -5,7 +5,7 @@
"childSources": null,
"targetIds": null,
"projectName": "codemodel-v2",
- "minimumCMakeVersion": "3.12",
+ "minimumCMakeVersion": "3.13",
"hasInstallRule": null,
"installers": []
}
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/external.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/external.json
index 6d2952d..f1199c3 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/external.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/external.json
@@ -9,7 +9,7 @@
"^generated_exe::@[0-9a-f]+$"
],
"projectName": "External",
- "minimumCMakeVersion": "3.12",
+ "minimumCMakeVersion": "3.13",
"hasInstallRule": true,
"installers": [
{
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/fileset.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/fileset.json
index 4774a13..c4df2ec 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/fileset.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/fileset.json
@@ -8,7 +8,7 @@
"^c_headers_2::@6b8db101d64c125f29fe$"
],
"projectName": "codemodel-v2",
- "minimumCMakeVersion": "3.12",
+ "minimumCMakeVersion": "3.13",
"hasInstallRule": true,
"installers": [
{
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/imported.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/imported.json
index 92b9526..8210d7f 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/imported.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/imported.json
@@ -13,7 +13,7 @@
"^link_imported_static_exe::@ba7eb709d0b48779c6c8$"
],
"projectName": "Imported",
- "minimumCMakeVersion": "3.12",
+ "minimumCMakeVersion": "3.13",
"hasInstallRule": true,
"installers": [
{
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/interface.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/interface.json
index 90664dc..08edd64 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/interface.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/interface.json
@@ -9,7 +9,7 @@
"^iface_srcs::@25b7fa8ea00134654b85$"
],
"projectName": "Interface",
- "minimumCMakeVersion": "3.12",
+ "minimumCMakeVersion": "3.13",
"hasInstallRule": null,
"installers": []
}
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/subdir.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/subdir.json
new file mode 100644
index 0000000..996da47
--- /dev/null
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/subdir.json
@@ -0,0 +1,11 @@
+{
+ "source": "^subdir$",
+ "build": "^subdir$",
+ "parentSource": "^\\.$",
+ "childSources": null,
+ "targetIds": null,
+ "projectName": "codemodel-v2",
+ "minimumCMakeVersion": "3.13",
+ "hasInstallRule": null,
+ "installers": []
+}
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/top.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/top.json
index e7b146f..aed07e2 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/top.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/directories/top.json
@@ -11,7 +11,8 @@
"^object$",
"^.*/Tests/RunCMake/FileAPIExternalSource$",
"^dir$",
- "^fileset$"
+ "^fileset$",
+ "^subdir$"
],
"targetIds": [
"^ALL_BUILD::@6890427a1f51a3e7e1df$",
@@ -22,10 +23,11 @@
"^c_shared_lib::@6890427a1f51a3e7e1df$",
"^c_static_exe::@6890427a1f51a3e7e1df$",
"^c_static_lib::@6890427a1f51a3e7e1df$",
+ "^c_subdir::@6890427a1f51a3e7e1df$",
"^interface_exe::@6890427a1f51a3e7e1df$"
],
"projectName": "codemodel-v2",
- "minimumCMakeVersion": "3.12",
+ "minimumCMakeVersion": "3.13",
"hasInstallRule": true,
"installers": [
{
@@ -48,7 +50,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 39,
+ "line": 42,
"command": "install",
"hasParent": true
},
@@ -93,7 +95,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 42,
+ "line": 45,
"command": "install",
"hasParent": true
},
@@ -141,7 +143,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 42,
+ "line": 45,
"command": "install",
"hasParent": true
},
@@ -186,7 +188,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 42,
+ "line": 45,
"command": "install",
"hasParent": true
},
@@ -230,7 +232,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 42,
+ "line": 45,
"command": "install",
"hasParent": true
},
@@ -274,7 +276,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 47,
+ "line": 50,
"command": "install",
"hasParent": true
},
@@ -321,7 +323,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 49,
+ "line": 52,
"command": "install",
"hasParent": true
},
@@ -366,7 +368,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 50,
+ "line": 53,
"command": "install",
"hasParent": true
},
@@ -415,7 +417,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 51,
+ "line": 54,
"command": "install",
"hasParent": true
},
@@ -467,7 +469,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 52,
+ "line": 55,
"command": "install",
"hasParent": true
},
@@ -516,7 +518,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 53,
+ "line": 56,
"command": "install",
"hasParent": true
},
@@ -558,7 +560,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 54,
+ "line": 57,
"command": "install",
"hasParent": true
},
@@ -600,7 +602,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 55,
+ "line": 58,
"command": "install",
"hasParent": true
},
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/projects/codemodel-v2.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/projects/codemodel-v2.json
index 0d6c4a1..151c0a8 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/projects/codemodel-v2.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/projects/codemodel-v2.json
@@ -14,7 +14,8 @@
"^\\.$",
"^dir$",
"^dir/dir$",
- "^fileset$"
+ "^fileset$",
+ "^subdir$"
],
"targetIds": [
"^ALL_BUILD::@6890427a1f51a3e7e1df$",
@@ -26,6 +27,7 @@
"^c_shared_exe::@6890427a1f51a3e7e1df$",
"^c_static_lib::@6890427a1f51a3e7e1df$",
"^c_static_exe::@6890427a1f51a3e7e1df$",
+ "^c_subdir::@6890427a1f51a3e7e1df$",
"^c_headers_1::@6b8db101d64c125f29fe$",
"^c_headers_2::@6b8db101d64c125f29fe$"
]
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/all_build_top.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/all_build_top.json
index 4e772a7..0d45d07 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/all_build_top.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/all_build_top.json
@@ -96,6 +96,10 @@
"backtrace": null
},
{
+ "id": "^c_subdir::@6890427a1f51a3e7e1df$",
+ "backtrace": null
+ },
+ {
"id": "^c_static_exe::@6890427a1f51a3e7e1df$",
"backtrace": null
},
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/c_shared_lib.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/c_shared_lib.json
index b4318dd..9a210ff 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/c_shared_lib.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/c_shared_lib.json
@@ -115,7 +115,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 42,
+ "line": 45,
"command": "install",
"hasParent": true
},
@@ -145,7 +145,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 42,
+ "line": 45,
"command": "install",
"hasParent": true
},
@@ -175,7 +175,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 47,
+ "line": 50,
"command": "install",
"hasParent": true
},
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/c_subdir.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/c_subdir.json
new file mode 100644
index 0000000..12ec917
--- /dev/null
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/c_subdir.json
@@ -0,0 +1,150 @@
+{
+ "name": "c_subdir",
+ "id": "^c_subdir::@6890427a1f51a3e7e1df$",
+ "directorySource": "^\\.$",
+ "projectName": "codemodel-v2",
+ "type": "STATIC_LIBRARY",
+ "isGeneratorProvided": null,
+ "sources": [
+ {
+ "path": "^subdir/empty\\.c$",
+ "isGenerated": null,
+ "sourceGroupName": "Source Files",
+ "compileGroupLanguage": "C",
+ "backtrace": [
+ {
+ "file": "^subdir/CMakeLists\\.txt$",
+ "line": 4,
+ "command": "target_sources",
+ "hasParent": true
+ },
+ {
+ "file": "^subdir/CMakeLists\\.txt$",
+ "line": null,
+ "command": null,
+ "hasParent": false
+ }
+ ]
+ }
+ ],
+ "sourceGroups": [
+ {
+ "name": "Source Files",
+ "sourcePaths": [
+ "^subdir/empty\\.c$"
+ ]
+ }
+ ],
+ "compileGroups": [
+ {
+ "language": "C",
+ "sourcePaths": [
+ "^subdir/empty\\.c$"
+ ],
+ "includes": [
+ {
+ "path": "^.*/Tests/RunCMake/FileAPI/subdir$",
+ "isSystem": null,
+ "backtrace": [
+ {
+ "file": "^subdir/CMakeLists\\.txt$",
+ "line": 2,
+ "command": "target_include_directories",
+ "hasParent": true
+ },
+ {
+ "file": "^subdir/CMakeLists\\.txt$",
+ "line": null,
+ "command": null,
+ "hasParent": false
+ }
+ ]
+ }
+ ],
+ "defines": [
+ {
+ "define": "SUBDIR",
+ "backtrace": [
+ {
+ "file": "^subdir/CMakeLists\\.txt$",
+ "line": 1,
+ "command": "target_compile_definitions",
+ "hasParent": true
+ },
+ {
+ "file": "^subdir/CMakeLists\\.txt$",
+ "line": null,
+ "command": null,
+ "hasParent": false
+ }
+ ]
+ }
+ ],
+ "compileCommandFragments": null
+ }
+ ],
+ "backtrace": [
+ {
+ "file": "^codemodel-v2\\.cmake$",
+ "line": 17,
+ "command": "add_library",
+ "hasParent": true
+ },
+ {
+ "file": "^codemodel-v2\\.cmake$",
+ "line": null,
+ "command": null,
+ "hasParent": true
+ },
+ {
+ "file": "^CMakeLists\\.txt$",
+ "line": 3,
+ "command": "include",
+ "hasParent": true
+ },
+ {
+ "file": "^CMakeLists\\.txt$",
+ "line": null,
+ "command": null,
+ "hasParent": false
+ }
+ ],
+ "folder": null,
+ "nameOnDisk": "^(lib)?c_subdir\\.(a|lib)$",
+ "artifacts": [
+ {
+ "path": "^((Debug|Release|RelWithDebInfo|MinSizeRel)/)?(lib)?c_subdir\\.(a|lib)$",
+ "_dllExtra": false
+ }
+ ],
+ "build": "^\\.$",
+ "source": "^\\.$",
+ "install": null,
+ "link": null,
+ "archive": {
+ "lto": null
+ },
+ "dependencies": [
+ {
+ "id": "^c_lib::@6890427a1f51a3e7e1df$",
+ "backtrace": [
+ {
+ "file": "^subdir/CMakeLists\\.txt$",
+ "line": 3,
+ "command": "target_link_libraries",
+ "hasParent": true
+ },
+ {
+ "file": "^subdir/CMakeLists\\.txt$",
+ "line": null,
+ "command": null,
+ "hasParent": false
+ }
+ ]
+ },
+ {
+ "id": "^ZERO_CHECK::@6890427a1f51a3e7e1df$",
+ "backtrace": null
+ }
+ ]
+}
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe.json
index 5769f0c..16d074a 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_exe.json
@@ -136,7 +136,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 39,
+ "line": 42,
"command": "install",
"hasParent": true
},
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_shared_lib.json b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_shared_lib.json
index 1fe4d67..03f4cb9 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_shared_lib.json
+++ b/Tests/RunCMake/FileAPI/codemodel-v2-data/targets/cxx_shared_lib.json
@@ -91,7 +91,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 42,
+ "line": 45,
"command": "install",
"hasParent": true
},
@@ -121,7 +121,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 42,
+ "line": 45,
"command": "install",
"hasParent": true
},
@@ -151,7 +151,7 @@
"backtrace": [
{
"file": "^codemodel-v2\\.cmake$",
- "line": 47,
+ "line": 50,
"command": "install",
"hasParent": true
},
diff --git a/Tests/RunCMake/FileAPI/codemodel-v2.cmake b/Tests/RunCMake/FileAPI/codemodel-v2.cmake
index 019eb87..09db216 100644
--- a/Tests/RunCMake/FileAPI/codemodel-v2.cmake
+++ b/Tests/RunCMake/FileAPI/codemodel-v2.cmake
@@ -14,6 +14,9 @@ add_library(c_static_lib STATIC empty.c)
add_executable(c_static_exe empty.c)
target_link_libraries(c_static_exe PRIVATE c_static_lib)
+add_library(c_subdir STATIC)
+add_subdirectory(subdir)
+
add_subdirectory(cxx)
add_subdirectory(alias)
add_subdirectory(object)
diff --git a/Tests/RunCMake/FileAPI/subdir/CMakeLists.txt b/Tests/RunCMake/FileAPI/subdir/CMakeLists.txt
new file mode 100644
index 0000000..b8f4550
--- /dev/null
+++ b/Tests/RunCMake/FileAPI/subdir/CMakeLists.txt
@@ -0,0 +1,4 @@
+target_compile_definitions(c_subdir PRIVATE SUBDIR)
+target_include_directories(c_subdir PRIVATE ${CMAKE_CURRENT_SOURCE_DIR})
+target_link_libraries(c_subdir PRIVATE c_lib)
+target_sources(c_subdir PRIVATE empty.c)
diff --git a/Tests/RunCMake/FileAPI/subdir/empty.c b/Tests/RunCMake/FileAPI/subdir/empty.c
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/Tests/RunCMake/FileAPI/subdir/empty.c
diff --git a/Tests/RunCMake/block/CMakeLists.txt b/Tests/RunCMake/block/CMakeLists.txt
new file mode 100644
index 0000000..45cd10e
--- /dev/null
+++ b/Tests/RunCMake/block/CMakeLists.txt
@@ -0,0 +1,3 @@
+cmake_minimum_required(VERSION 3.3...3.25)
+project(${RunCMake_TEST} NONE)
+include(${RunCMake_TEST}.cmake)
diff --git a/Tests/RunCMake/block/EndAlone-result.txt b/Tests/RunCMake/block/EndAlone-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/EndAlone-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/EndAlone-stderr.txt b/Tests/RunCMake/block/EndAlone-stderr.txt
new file mode 100644
index 0000000..a588dd7
--- /dev/null
+++ b/Tests/RunCMake/block/EndAlone-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at EndAlone.cmake:[0-9]+ \(endblock\):
+ Flow control statements are not properly nested.
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/EndAlone.cmake b/Tests/RunCMake/block/EndAlone.cmake
new file mode 100644
index 0000000..0c428a9
--- /dev/null
+++ b/Tests/RunCMake/block/EndAlone.cmake
@@ -0,0 +1 @@
+endblock()
diff --git a/Tests/RunCMake/block/EndAloneWithArgument-result.txt b/Tests/RunCMake/block/EndAloneWithArgument-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/EndAloneWithArgument-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/EndAloneWithArgument-stderr.txt b/Tests/RunCMake/block/EndAloneWithArgument-stderr.txt
new file mode 100644
index 0000000..c3d25a3
--- /dev/null
+++ b/Tests/RunCMake/block/EndAloneWithArgument-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at EndAloneWithArgument.cmake:[0-9]+ \(endblock\):
+ Flow control statements are not properly nested.
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/EndAloneWithArgument.cmake b/Tests/RunCMake/block/EndAloneWithArgument.cmake
new file mode 100644
index 0000000..05df5b0
--- /dev/null
+++ b/Tests/RunCMake/block/EndAloneWithArgument.cmake
@@ -0,0 +1 @@
+endblock(WRONG_ARG)
diff --git a/Tests/RunCMake/block/EndMissing-result.txt b/Tests/RunCMake/block/EndMissing-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/EndMissing-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/EndMissing-stderr.txt b/Tests/RunCMake/block/EndMissing-stderr.txt
new file mode 100644
index 0000000..b9739a5
--- /dev/null
+++ b/Tests/RunCMake/block/EndMissing-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at EndMissing.cmake:[0-9]+ \(block\):
+ Flow control statements are not properly nested.
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/EndMissing.cmake b/Tests/RunCMake/block/EndMissing.cmake
new file mode 100644
index 0000000..335b64e
--- /dev/null
+++ b/Tests/RunCMake/block/EndMissing.cmake
@@ -0,0 +1 @@
+block()
diff --git a/Tests/RunCMake/block/EndWithArgument-stderr.txt b/Tests/RunCMake/block/EndWithArgument-stderr.txt
new file mode 100644
index 0000000..7586453
--- /dev/null
+++ b/Tests/RunCMake/block/EndWithArgument-stderr.txt
@@ -0,0 +1,9 @@
+CMake Warning \(dev\) in EndWithArgument.cmake:
+ A logical block closing on the line
+
+ .+/Tests/RunCMake/block/EndWithArgument.cmake:[0-9]+ \(endblock\)
+
+ has unexpected arguments.
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
+This warning is for project developers. Use -Wno-dev to suppress it.
diff --git a/Tests/RunCMake/block/EndWithArgument.cmake b/Tests/RunCMake/block/EndWithArgument.cmake
new file mode 100644
index 0000000..0641c9a
--- /dev/null
+++ b/Tests/RunCMake/block/EndWithArgument.cmake
@@ -0,0 +1,2 @@
+block()
+endblock(END_ARG)
diff --git a/Tests/RunCMake/block/InvalidArgument-result.txt b/Tests/RunCMake/block/InvalidArgument-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidArgument-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/InvalidArgument-stderr.txt b/Tests/RunCMake/block/InvalidArgument-stderr.txt
new file mode 100644
index 0000000..bee604b
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidArgument-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at InvalidArgument.cmake:[0-9]+ \(block\):
+ block PROPAGATE cannot be specified without a new scope for VARIABLES
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/InvalidArgument.cmake b/Tests/RunCMake/block/InvalidArgument.cmake
new file mode 100644
index 0000000..5269cd0
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidArgument.cmake
@@ -0,0 +1,2 @@
+block(SCOPE_FOR POLICIES PROPAGATE VAR1)
+endblock()
diff --git a/Tests/RunCMake/block/InvalidNesting1-result.txt b/Tests/RunCMake/block/InvalidNesting1-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting1-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/InvalidNesting1-stderr.txt b/Tests/RunCMake/block/InvalidNesting1-stderr.txt
new file mode 100644
index 0000000..6dfe0e1
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting1-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at InvalidNesting1.cmake:[0-9]+ \(else\):
+ Flow control statements are not properly nested.
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/InvalidNesting1.cmake b/Tests/RunCMake/block/InvalidNesting1.cmake
new file mode 100644
index 0000000..27b7944
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting1.cmake
@@ -0,0 +1,6 @@
+
+if (TRUE)
+ block()
+else()
+ endblock()
+endif()
diff --git a/Tests/RunCMake/block/InvalidNesting2-result.txt b/Tests/RunCMake/block/InvalidNesting2-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting2-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/InvalidNesting2-stderr.txt b/Tests/RunCMake/block/InvalidNesting2-stderr.txt
new file mode 100644
index 0000000..71325b6
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting2-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at InvalidNesting2.cmake:[0-9]+ \(endblock\):
+ Flow control statements are not properly nested.
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/InvalidNesting2.cmake b/Tests/RunCMake/block/InvalidNesting2.cmake
new file mode 100644
index 0000000..ae94cdc
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting2.cmake
@@ -0,0 +1,6 @@
+
+block()
+if (TRUE)
+elseif(FALSE)
+endblock()
+endif()
diff --git a/Tests/RunCMake/block/InvalidNesting3-result.txt b/Tests/RunCMake/block/InvalidNesting3-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting3-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/InvalidNesting3-stderr.txt b/Tests/RunCMake/block/InvalidNesting3-stderr.txt
new file mode 100644
index 0000000..344a931
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting3-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at InvalidNesting3.cmake:[0-9]+ \(endwhile\):
+ Flow control statements are not properly nested.
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/InvalidNesting3.cmake b/Tests/RunCMake/block/InvalidNesting3.cmake
new file mode 100644
index 0000000..f692d24
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting3.cmake
@@ -0,0 +1,5 @@
+
+while(TRUE)
+block()
+endwhile()
+endblock()
diff --git a/Tests/RunCMake/block/InvalidNesting4-result.txt b/Tests/RunCMake/block/InvalidNesting4-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting4-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/InvalidNesting4-stderr.txt b/Tests/RunCMake/block/InvalidNesting4-stderr.txt
new file mode 100644
index 0000000..44d6364
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting4-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at InvalidNesting4.cmake:[0-9]+ \(endblock\):
+ Flow control statements are not properly nested.
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/InvalidNesting4.cmake b/Tests/RunCMake/block/InvalidNesting4.cmake
new file mode 100644
index 0000000..6e8e0ae
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting4.cmake
@@ -0,0 +1,5 @@
+
+block()
+foreach(item IN ITEMS A B)
+endblock()
+endforeach()
diff --git a/Tests/RunCMake/block/InvalidNesting5-result.txt b/Tests/RunCMake/block/InvalidNesting5-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting5-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/InvalidNesting5-stderr.txt b/Tests/RunCMake/block/InvalidNesting5-stderr.txt
new file mode 100644
index 0000000..976d2e1
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting5-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at InvalidNesting5.cmake:[0-9]+ \(endfunction\):
+ Flow control statements are not properly nested.
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/InvalidNesting5.cmake b/Tests/RunCMake/block/InvalidNesting5.cmake
new file mode 100644
index 0000000..0479e8d
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting5.cmake
@@ -0,0 +1,5 @@
+
+function(FUNC)
+ block()
+endfunction()
+endblock()
diff --git a/Tests/RunCMake/block/InvalidNesting6-result.txt b/Tests/RunCMake/block/InvalidNesting6-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting6-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/InvalidNesting6-stderr.txt b/Tests/RunCMake/block/InvalidNesting6-stderr.txt
new file mode 100644
index 0000000..2d67b16
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting6-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at InvalidNesting6.cmake:[0-9]+ \(endblock\):
+ Flow control statements are not properly nested.
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/InvalidNesting6.cmake b/Tests/RunCMake/block/InvalidNesting6.cmake
new file mode 100644
index 0000000..a1cb359
--- /dev/null
+++ b/Tests/RunCMake/block/InvalidNesting6.cmake
@@ -0,0 +1,5 @@
+
+ block()
+macro(FUNC)
+endblock()
+endmacro()
diff --git a/Tests/RunCMake/block/MissingArgument-result.txt b/Tests/RunCMake/block/MissingArgument-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/MissingArgument-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/MissingArgument-stderr.txt b/Tests/RunCMake/block/MissingArgument-stderr.txt
new file mode 100644
index 0000000..d3e63ca
--- /dev/null
+++ b/Tests/RunCMake/block/MissingArgument-stderr.txt
@@ -0,0 +1,7 @@
+CMake Error at MissingArgument.cmake:[0-9]+ \(block\):
+ Error after keyword "SCOPE_FOR":
+
+ missing required value
+
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/MissingArgument.cmake b/Tests/RunCMake/block/MissingArgument.cmake
new file mode 100644
index 0000000..6018887
--- /dev/null
+++ b/Tests/RunCMake/block/MissingArgument.cmake
@@ -0,0 +1,2 @@
+block(SCOPE_FOR)
+endblock()
diff --git a/Tests/RunCMake/block/RunCMakeTest.cmake b/Tests/RunCMake/block/RunCMakeTest.cmake
new file mode 100644
index 0000000..4260e76
--- /dev/null
+++ b/Tests/RunCMake/block/RunCMakeTest.cmake
@@ -0,0 +1,22 @@
+include(RunCMake)
+
+run_cmake(WrongArgument)
+run_cmake(InvalidArgument)
+run_cmake(MissingArgument)
+run_cmake(WrongScope)
+run_cmake(EndMissing)
+run_cmake(EndWithArgument)
+run_cmake(EndAlone)
+run_cmake(EndAloneWithArgument)
+
+run_cmake(InvalidNesting1)
+run_cmake(InvalidNesting2)
+run_cmake(InvalidNesting3)
+run_cmake(InvalidNesting4)
+run_cmake(InvalidNesting5)
+run_cmake(InvalidNesting6)
+
+run_cmake(Scope)
+run_cmake(Scope-VARIABLES)
+run_cmake(Scope-POLICIES)
+run_cmake(Workflows)
diff --git a/Tests/RunCMake/block/Scope-POLICIES.cmake b/Tests/RunCMake/block/Scope-POLICIES.cmake
new file mode 100644
index 0000000..789b3d9
--- /dev/null
+++ b/Tests/RunCMake/block/Scope-POLICIES.cmake
@@ -0,0 +1,30 @@
+
+set(VAR1 "OUTER1")
+set(VAR2 "OUTER2")
+
+cmake_policy(SET CMP0139 NEW)
+
+# create a block with a new scope for policies
+block(SCOPE_FOR POLICIES)
+ set(VAR1 "INNER1")
+ unset(VAR2)
+ set(VAR3 "INNER3")
+
+ cmake_policy(SET CMP0139 OLD)
+endblock()
+
+# check final values for variables
+if(NOT DEFINED VAR1 OR NOT VAR1 STREQUAL "INNER1")
+ message(SEND_ERROR "block/endblock: VAR1 has unexpected value: ${VAR1}")
+endif()
+if(DEFINED VAR2)
+ message(SEND_ERROR "block/endblock: VAR2 is unexpectedly defined: ${VAR2}")
+endif()
+if(NOT DEFINED VAR3 OR NOT VAR3 STREQUAL "INNER3")
+ message(SEND_ERROR "block/endblock: VAR3 has unexpected value: ${VAR3}")
+endif()
+
+cmake_policy(GET CMP0139 CMP0139_STATUS)
+if(NOT CMP0139_STATUS STREQUAL "NEW")
+ message(SEND_ERROR "block/endblock: CMP0139 has unexpected value: ${CMP0139_STATUS}")
+endif()
diff --git a/Tests/RunCMake/block/Scope-VARIABLES.cmake b/Tests/RunCMake/block/Scope-VARIABLES.cmake
new file mode 100644
index 0000000..140e638
--- /dev/null
+++ b/Tests/RunCMake/block/Scope-VARIABLES.cmake
@@ -0,0 +1,52 @@
+
+set(VAR1 "OUTER1")
+set(VAR2 "OUTER2")
+set(VAR3 "OUTER3")
+set(VAR4 "OUTER4")
+set(VAR5 "OUTER5")
+
+set(VAR6 "CACHE6" CACHE STRING "")
+set(VAR6 "OUTER6")
+
+cmake_policy(SET CMP0139 NEW)
+
+# create a block with a new scope for variables
+block(SCOPE_FOR VARIABLES PROPAGATE VAR3 VAR4 VAR5 VAR6 VAR7)
+ set(VAR1 "INNER1")
+ set(VAR2 "INNER2" PARENT_SCOPE)
+ set(VAR3 "INNER3")
+ unset(VAR4)
+ unset(VAR6)
+ set(VAR7 "INNER7")
+
+ cmake_policy(SET CMP0139 OLD)
+endblock()
+
+# check final values for variables
+if(NOT DEFINED VAR1 OR NOT VAR1 STREQUAL "OUTER1")
+ message(SEND_ERROR "block/endblock: VAR1 has unexpected value: ${VAR1}")
+endif()
+if(NOT DEFINED VAR2 OR NOT VAR2 STREQUAL "INNER2")
+ message(SEND_ERROR "block/endblock: VAR2 has unexpected value: ${VAR2}")
+endif()
+if(NOT DEFINED VAR3 OR NOT VAR3 STREQUAL "INNER3")
+ message(SEND_ERROR "block/endblock: VAR3 has unexpected value: ${VAR3}")
+endif()
+if(DEFINED VAR4)
+ message(SEND_ERROR "block/endblock: VAR4 is unexpectedly defined: ${VAR4}")
+endif()
+if(NOT DEFINED VAR5 OR NOT VAR5 STREQUAL "OUTER5")
+ message(SEND_ERROR "block/endblock: VAR5 has unexpected value: ${VAR5}")
+endif()
+unset(VAR6 CACHE)
+if (DEFINED VAR6)
+ message(SEND_ERROR "block/endblock: VAR6 is unexpectedly defined: ${VAR6}")
+endif()
+if(NOT DEFINED VAR7 OR NOT VAR7 STREQUAL "INNER7")
+ message(SEND_ERROR "block/endblock: VAR7 has unexpected value: ${VAR7}")
+endif()
+
+cmake_policy(GET CMP0139 CMP0139_STATUS)
+if(NOT CMP0139_STATUS STREQUAL "OLD")
+ message(SEND_ERROR "block/endblock: CMP0139 has unexpected value: ${CMP0139_STATUS}")
+endif()
diff --git a/Tests/RunCMake/block/Scope.cmake b/Tests/RunCMake/block/Scope.cmake
new file mode 100644
index 0000000..e1af50a
--- /dev/null
+++ b/Tests/RunCMake/block/Scope.cmake
@@ -0,0 +1,52 @@
+
+set(VAR1 "OUTER1")
+set(VAR2 "OUTER2")
+set(VAR3 "OUTER3")
+set(VAR4 "OUTER4")
+set(VAR5 "OUTER5")
+
+set(VAR6 "CACHE6" CACHE STRING "")
+set(VAR6 "OUTER6")
+
+cmake_policy(SET CMP0139 NEW)
+
+# create a block with a new scope for variables and policies
+block(PROPAGATE VAR3 VAR4 VAR5 VAR6 VAR7)
+ set(VAR1 "INNER1")
+ set(VAR2 "INNER2" PARENT_SCOPE)
+ set(VAR3 "INNER3")
+ unset(VAR4)
+ unset(VAR6)
+ set(VAR7 "INNER7")
+
+ cmake_policy(SET CMP0139 OLD)
+endblock()
+
+# check final values for variables
+if(NOT DEFINED VAR1 OR NOT VAR1 STREQUAL "OUTER1")
+ message(SEND_ERROR "block/endblock: VAR1 has unexpected value: ${VAR1}")
+endif()
+if(NOT DEFINED VAR2 OR NOT VAR2 STREQUAL "INNER2")
+ message(SEND_ERROR "block/endblock: VAR2 has unexpected value: ${VAR2}")
+endif()
+if(NOT DEFINED VAR3 OR NOT VAR3 STREQUAL "INNER3")
+ message(SEND_ERROR "block/endblock: VAR3 has unexpected value: ${VAR3}")
+endif()
+if(DEFINED VAR4)
+ message(SEND_ERROR "block/endblock: VAR4 is unexpectedly defined: ${VAR4}")
+endif()
+if(NOT DEFINED VAR5 OR NOT VAR5 STREQUAL "OUTER5")
+ message(SEND_ERROR "block/endblock: VAR5 has unexpected value: ${VAR5}")
+endif()
+unset(VAR6 CACHE)
+if (DEFINED VAR6)
+ message(SEND_ERROR "block/endblock: VAR6 is unexpectedly defined: ${VAR6}")
+endif()
+if(NOT DEFINED VAR7 OR NOT VAR7 STREQUAL "INNER7")
+ message(SEND_ERROR "block/endblock: VAR6 has unexpected value: ${VAR7}")
+endif()
+
+cmake_policy(GET CMP0139 CMP0139_STATUS)
+if(NOT CMP0139_STATUS STREQUAL "NEW")
+ message(SEND_ERROR "block/endblock: CMP0139 has unexpected value: ${CMP0139_STATUS}")
+endif()
diff --git a/Tests/RunCMake/block/Workflows.cmake b/Tests/RunCMake/block/Workflows.cmake
new file mode 100644
index 0000000..cbf032e
--- /dev/null
+++ b/Tests/RunCMake/block/Workflows.cmake
@@ -0,0 +1,78 @@
+
+set(VAR1 "OUTER1")
+set(VAR2 "OUTER2")
+set(VAR3 "OUTER3")
+
+while (TRUE)
+ # create a block with a new scope for variables
+ block(SCOPE_FOR VARIABLES PROPAGATE VAR3)
+ set(VAR2 "INNER2" PARENT_SCOPE)
+ set(VAR3 "INNER3")
+ break()
+ endblock()
+endwhile()
+
+# check final values for variables
+if(NOT DEFINED VAR1 OR NOT VAR1 STREQUAL "OUTER1")
+ message(SEND_ERROR "block/endblock: VAR1 has unexpected value: ${VAR1}")
+endif()
+if(NOT DEFINED VAR2 OR NOT VAR2 STREQUAL "INNER2")
+ message(SEND_ERROR "block/endblock: VAR2 has unexpected value: ${VAR2}")
+endif()
+if(NOT DEFINED VAR3 OR NOT VAR3 STREQUAL "INNER3")
+ message(SEND_ERROR "block/endblock: VAR3 has unexpected value: ${VAR3}")
+endif()
+
+
+
+set(VAR1 "OUTER1")
+set(VAR2 "OUTER2")
+set(VAR3 "OUTER3")
+
+function (OUTER)
+ # create a block with a new scope for variables
+ block(SCOPE_FOR VARIABLES PROPAGATE VAR3)
+ set(VAR2 "INNER2" PARENT_SCOPE)
+ set(VAR3 "INNER3")
+ return()
+ endblock()
+ set(VAR1 "INNER1" PARENT_SCOPE)
+endfunction()
+outer()
+
+# check final values for variables
+if(NOT DEFINED VAR1 OR NOT VAR1 STREQUAL "OUTER1")
+ message(SEND_ERROR "block/endblock: VAR1 has unexpected value: ${VAR1}")
+endif()
+if(NOT DEFINED VAR2 OR NOT VAR2 STREQUAL "OUTER2")
+ message(SEND_ERROR "block/endblock: VAR2 has unexpected value: ${VAR2}")
+endif()
+if(NOT DEFINED VAR3 OR NOT VAR3 STREQUAL "OUTER3")
+ message(SEND_ERROR "block/endblock: VAR3 has unexpected value: ${VAR3}")
+endif()
+
+
+
+set(VAR1 "OUTER1")
+set(VAR2 "OUTER2")
+set(VAR3 "OUTER3")
+
+foreach (id IN ITEMS 1 2 3)
+ # create a block with a new scope for variables
+ block(SCOPE_FOR VARIABLES PROPAGATE VAR${id})
+ set(VAR${id} "INNER${id}")
+ continue()
+ set(VAR${id} "BAD${id}")
+ endblock()
+endforeach()
+
+# check final values for variables
+if(NOT DEFINED VAR1 OR NOT VAR1 STREQUAL "INNER1")
+ message(SEND_ERROR "block/endblock: VAR1 has unexpected value: ${VAR1}")
+endif()
+if(NOT DEFINED VAR2 OR NOT VAR2 STREQUAL "INNER2")
+ message(SEND_ERROR "block/endblock: VAR2 has unexpected value: ${VAR2}")
+endif()
+if(NOT DEFINED VAR3 OR NOT VAR3 STREQUAL "INNER3")
+ message(SEND_ERROR "block/endblock: VAR3 has unexpected value: ${VAR3}")
+endif()
diff --git a/Tests/RunCMake/block/WrongArgument-result.txt b/Tests/RunCMake/block/WrongArgument-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/WrongArgument-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/WrongArgument-stderr.txt b/Tests/RunCMake/block/WrongArgument-stderr.txt
new file mode 100644
index 0000000..56faea7
--- /dev/null
+++ b/Tests/RunCMake/block/WrongArgument-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at WrongArgument.cmake:[0-9]+ \(block\):
+ block called with unsupported argument "WRONG_ARG"
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/WrongArgument.cmake b/Tests/RunCMake/block/WrongArgument.cmake
new file mode 100644
index 0000000..e460866
--- /dev/null
+++ b/Tests/RunCMake/block/WrongArgument.cmake
@@ -0,0 +1,2 @@
+block(WRONG_ARG)
+endblock()
diff --git a/Tests/RunCMake/block/WrongScope-result.txt b/Tests/RunCMake/block/WrongScope-result.txt
new file mode 100644
index 0000000..d00491f
--- /dev/null
+++ b/Tests/RunCMake/block/WrongScope-result.txt
@@ -0,0 +1 @@
+1
diff --git a/Tests/RunCMake/block/WrongScope-stderr.txt b/Tests/RunCMake/block/WrongScope-stderr.txt
new file mode 100644
index 0000000..dd2a1ef
--- /dev/null
+++ b/Tests/RunCMake/block/WrongScope-stderr.txt
@@ -0,0 +1,4 @@
+CMake Error at WrongScope.cmake:[0-9]+ \(block\):
+ block SCOPE_FOR unsupported scope "WRONG_SCOPE"
+Call Stack \(most recent call first\):
+ CMakeLists.txt:[0-9]+ \(include\)
diff --git a/Tests/RunCMake/block/WrongScope.cmake b/Tests/RunCMake/block/WrongScope.cmake
new file mode 100644
index 0000000..97a6783
--- /dev/null
+++ b/Tests/RunCMake/block/WrongScope.cmake
@@ -0,0 +1,2 @@
+block(SCOPE_FOR WRONG_SCOPE)
+endblock()
diff --git a/Tests/RunCMake/cmake_language/RunCMakeTest.cmake b/Tests/RunCMake/cmake_language/RunCMakeTest.cmake
index 03a15fc..38ce10b 100644
--- a/Tests/RunCMake/cmake_language/RunCMakeTest.cmake
+++ b/Tests/RunCMake/cmake_language/RunCMakeTest.cmake
@@ -8,6 +8,7 @@ foreach(command IN ITEMS
"if" "elseif" "else" "endif"
"while" "endwhile"
"foreach" "endforeach"
+ "block" "endblock"
)
message(STATUS "Running call_invalid_command for ${command}...")
run_cmake_with_options(call_invalid_command -Dcommand=${command})
@@ -42,6 +43,7 @@ foreach(command IN ITEMS
"if" "elseif" "else" "endif"
"while" "endwhile"
"foreach" "endforeach"
+ "block" "endblock"
"return"
)
message(STATUS "Running defer_call_invalid_command for ${command}...")
diff --git a/Utilities/std/cmext/enum_set b/Utilities/std/cmext/enum_set
index 4225b82..d7b8b39 100644
--- a/Utilities/std/cmext/enum_set
+++ b/Utilities/std/cmext/enum_set
@@ -146,6 +146,7 @@ public:
{
this->Set.reset();
this->insert(list);
+ return *this;
}
// Iterators
@@ -298,17 +299,15 @@ public:
{
if (this->contains(e)) {
return iterator(this, static_cast<size_type>(e));
- } else {
- return this->end();
}
+ return this->end();
}
const_iterator find(key_type e) const
{
if (this->contains(e)) {
return const_iterator(this, static_cast<size_type>(e));
- } else {
- return this->end();
}
+ return this->end();
}
bool contains(key_type e) const
@@ -317,6 +316,10 @@ public:
}
private:
+ template <typename E>
+ friend inline bool operator==(const enum_set<E>& lhs,
+ const enum_set<E>& rhs) noexcept;
+
template <typename E, typename Predicate>
friend inline void erase_if(enum_set<E>& set, Predicate pred);
@@ -369,7 +372,7 @@ template <typename Enum>
inline bool operator==(const enum_set<Enum>& lhs,
const enum_set<Enum>& rhs) noexcept
{
- return lhs == rhs;
+ return lhs.Set == rhs.Set;
}
template <typename Enum>
diff --git a/bootstrap b/bootstrap
index 01ff84f..d5b071e 100755
--- a/bootstrap
+++ b/bootstrap
@@ -301,6 +301,7 @@ CMAKE_CXX_SOURCES="\
cmBinUtilsWindowsPEDumpbinGetRuntimeDependenciesTool \
cmBinUtilsWindowsPELinker \
cmBinUtilsWindowsPEObjdumpGetRuntimeDependenciesTool \
+ cmBlockCommand \
cmBreakCommand \
cmBuildCommand \
cmCMakeLanguageCommand \