summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJames Johnston <johnstonj.public@codenest.com>2015-08-17 23:55:38 -0400
committerJames Johnston <johnstonj.public@codenest.com>2015-08-17 23:55:38 -0400
commite89ea3d190492e41b37425ff021311c2b471f1b9 (patch)
tree35c88e18b8ac49fc2f115140c73ba04b8df3f0a1
parenta38ea312c02eec6e4ee61015f70920999bf79ff9 (diff)
downloadcmake-e89ea3d190492e41b37425ff021311c2b471f1b9.tar.gz
get_filename_component: Teach new BASE_DIR parameter.
In the get_filename_component command, add a new BASE_DIR parameter to use with the ABSOLUTE and REALPATH options. This will be used when finding an absolute path from a relative path.
-rw-r--r--Help/command/get_filename_component.rst37
-rw-r--r--Help/release/dev/get-filename-component-base-dir.rst6
-rw-r--r--Source/cmGetFilenameComponentCommand.cxx20
-rw-r--r--Tests/RunCMake/get_filename_component/KnownComponents.cmake33
4 files changed, 87 insertions, 9 deletions
diff --git a/Help/command/get_filename_component.rst b/Help/command/get_filename_component.rst
index 60488dad5d..82f9120021 100644
--- a/Help/command/get_filename_component.rst
+++ b/Help/command/get_filename_component.rst
@@ -3,6 +3,8 @@ get_filename_component
Get a specific component of a full filename.
+------------------------------------------------------------------------------
+
::
get_filename_component(<VAR> <FileName> <COMP> [CACHE])
@@ -15,8 +17,6 @@ Set ``<VAR>`` to a component of ``<FileName>``, where ``<COMP>`` is one of:
NAME = File name without directory
EXT = File name longest extension (.b.c from d/a.b.c)
NAME_WE = File name without directory or longest extension
- ABSOLUTE = Full path to file
- REALPATH = Full path to existing file with symlinks resolved
PATH = Legacy alias for DIRECTORY (use for CMake <= 2.8.11)
Paths are returned with forward slashes and have no trailing slahes.
@@ -24,14 +24,41 @@ The longest file extension is always considered. If the optional
``CACHE`` argument is specified, the result variable is added to the
cache.
+------------------------------------------------------------------------------
+
+::
+
+ get_filename_component(<VAR> <FileName>
+ <COMP> [BASE_DIR <BASE_DIR>]
+ [CACHE])
+
+Set ``<VAR>`` to the absolute path of ``<FileName>``, where ``<COMP>`` is one
+of:
+
+::
+
+ ABSOLUTE = Full path to file
+ REALPATH = Full path to existing file with symlinks resolved
+
+If the provided ``<FileName>`` is a relative path, it is evaluated relative
+to the given base directory ``<BASE_DIR>``. If no base directory is
+provided, the default base directory will be
+:variable:`CMAKE_CURRENT_SOURCE_DIR`.
+
+Paths are returned with forward slashes and have no trailing slahes. If the
+optional ``CACHE`` argument is specified, the result variable is added to the
+cache.
+
+------------------------------------------------------------------------------
+
::
- get_filename_component(<VAR> FileName
+ get_filename_component(<VAR> <FileName>
PROGRAM [PROGRAM_ARGS <ARG_VAR>]
[CACHE])
-The program in ``FileName`` will be found in the system search path or
+The program in ``<FileName>`` will be found in the system search path or
left as a full path. If ``PROGRAM_ARGS`` is present with ``PROGRAM``, then
-any command-line arguments present in the ``FileName`` string are split
+any command-line arguments present in the ``<FileName>`` string are split
from the program name and stored in ``<ARG_VAR>``. This is used to
separate a program name from its arguments in a command line string.
diff --git a/Help/release/dev/get-filename-component-base-dir.rst b/Help/release/dev/get-filename-component-base-dir.rst
new file mode 100644
index 0000000000..c0df759da2
--- /dev/null
+++ b/Help/release/dev/get-filename-component-base-dir.rst
@@ -0,0 +1,6 @@
+get-filename-component-base-dir
+-------------------------------
+
+* The :command:`get_filename_component` command learned a new ``BASE_DIR``
+ subcommand. This is used to specify a base directory when calculating an
+ absolute path from a relative path.
diff --git a/Source/cmGetFilenameComponentCommand.cxx b/Source/cmGetFilenameComponentCommand.cxx
index 13a9afbe73..0f56c8e8fc 100644
--- a/Source/cmGetFilenameComponentCommand.cxx
+++ b/Source/cmGetFilenameComponentCommand.cxx
@@ -93,11 +93,23 @@ bool cmGetFilenameComponentCommand
else if (args[2] == "ABSOLUTE" ||
args[2] == "REALPATH")
{
+ // If the path given is relative, evaluate it relative to the
+ // current source directory unless the user passes a different
+ // base directory.
+ std::string baseDir = this->Makefile->GetCurrentSourceDirectory();
+ for(unsigned int i=3; i < args.size(); ++i)
+ {
+ if(args[i] == "BASE_DIR")
+ {
+ ++i;
+ if(i < args.size())
+ {
+ baseDir = args[i];
+ }
+ }
+ }
// Collapse the path to its simplest form.
- // If the path given is relative evaluate it relative to the
- // current source directory.
- result = cmSystemTools::CollapseFullPath(
- filename, this->Makefile->GetCurrentSourceDirectory());
+ result = cmSystemTools::CollapseFullPath(filename, baseDir);
if(args[2] == "REALPATH")
{
// Resolve symlinks if possible
diff --git a/Tests/RunCMake/get_filename_component/KnownComponents.cmake b/Tests/RunCMake/get_filename_component/KnownComponents.cmake
index 386109f56d..d82225864f 100644
--- a/Tests/RunCMake/get_filename_component/KnownComponents.cmake
+++ b/Tests/RunCMake/get_filename_component/KnownComponents.cmake
@@ -38,6 +38,39 @@ check("ABSOLUTE .. in windows root" "${test_absolute}" "c:/path/to/filename.ext.
list(APPEND non_cache_vars test_absolute)
+# Test finding absolute paths from various base directories.
+
+get_filename_component(test_abs_base "testdir1" ABSOLUTE)
+check("ABSOLUTE .. from default base" "${test_abs_base}"
+ "${CMAKE_CURRENT_SOURCE_DIR}/testdir1")
+
+get_filename_component(test_abs_base "../testdir2" ABSOLUTE
+ BASE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/dummydir")
+check("ABSOLUTE .. from dummy base to parent" "${test_abs_base}"
+ "${CMAKE_CURRENT_SOURCE_DIR}/testdir2")
+
+get_filename_component(test_abs_base "testdir3" ABSOLUTE
+ BASE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/dummydir")
+check("ABSOLUTE .. from dummy base to child" "${test_abs_base}"
+ "${CMAKE_CURRENT_SOURCE_DIR}/dummydir/testdir3")
+
+list(APPEND non_cache_vars test_abs_base)
+
+# Test finding absolute paths with CACHE parameter. (Note that more
+# rigorous testing of the CACHE parameter comes later with PROGRAM).
+
+get_filename_component(test_abs_base_1 "testdir4" ABSOLUTE CACHE)
+check("ABSOLUTE CACHE 1" "${test_abs_base_1}"
+ "${CMAKE_CURRENT_SOURCE_DIR}/testdir4")
+list(APPEND cache_vars test_abs_base_1)
+
+get_filename_component(test_abs_base_2 "testdir5" ABSOLUTE
+ BASE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/dummydir"
+ CACHE)
+check("ABSOLUTE CACHE 2" "${test_abs_base_2}"
+ "${CMAKE_CURRENT_SOURCE_DIR}/dummydir/testdir5")
+list(APPEND cache_vars test_abs_base_2)
+
# Test the PROGRAM component type.
get_filename_component(test_program_name "/ arg1 arg2" PROGRAM)
check("PROGRAM with no args output" "${test_program_name}" "/")