diff --git a/RELEASE.txt b/RELEASE.txt old mode 100755 new mode 100644 index 5d32080e33..78fcc16e3e --- a/RELEASE.txt +++ b/RELEASE.txt @@ -72,6 +72,7 @@ DOCUMENTATION - Updated the --hash-format manpage entry. - EnsureSConsVersion, EnsurePythonVersion, Exit, GetLaunchDir and SConscriptChdir are now listed as Global functions only. +- Updated the docs for Glob. - Updated SHELL_ENV_GENERATORS description and added versionadded indicator. DEVELOPMENT @@ -83,4 +84,4 @@ Thanks to the following contributors listed below for their contributions to thi ========================================================================================== .. code-block:: text - git shortlog --no-merges -ns 4.0.1..HEAD + git shortlog --no-merges -ns 4.4.0..HEAD diff --git a/SCons/Environment.xml b/SCons/Environment.xml index b664d60870..2c5d56385a 100644 --- a/SCons/Environment.xml +++ b/SCons/Environment.xml @@ -1901,48 +1901,81 @@ Nodes or strings representing path names. -(pattern, [ondisk, source, strings, exclude]) +(pattern, [ondisk=True, source=False, strings=False, exclude=None]) -Returns Nodes (or strings) that match the specified -pattern, -relative to the directory of the current -&SConscript; -file. +Returns a possibly empty list of Nodes (or strings) that match +pathname specification pattern. +pattern can be absolute, +top-relative, +or (most commonly) relative to the directory of the current +&SConscript; file. +&f-Glob; matches both files stored on disk and Nodes +which &SCons; already knows about, even if any corresponding +file is not currently stored on disk. The evironment method form (&f-env-Glob;) performs string substition on pattern -and returns whatever matches -the resulting expanded pattern. +and returns whatever matches the resulting expanded pattern. +The results are sorted, unlike for the similar &Python; +glob.glob function, +to ensure build order will be stable. -The specified pattern -uses Unix shell style metacharacters for matching: +can contain POSIX-style shell metacharacters for matching: + + + + + + + Pattern + Meaning + + + + + * + matches everything + + + ? + matches any single character + + + [seq] + matches any character in seq + (can be a list or a range). + + + [!seq] + matches any character not in seq + + + + + + +For a literal match, wrap the metacharacter in brackets to +escape the normal behavior. +For example, '[?]' matches the character +'?'. + + + +Filenames starting with a dot are specially handled - +they can only be matched by patterns that start with a dot +(or have a dot immediately following a pathname separator +character, or slash), they are not not matched by the metacharacters. +Metacharacter matches also do not span directory separators. - - * matches everything - ? matches any single character - [seq] matches any character in seq - [!seq] matches any char not in seq - - -If the first character of a filename is a dot, -it must be matched explicitly. -Character matches do -not -span directory separators. - - - -The &f-Glob; -knows about -repositories +understands repositories (see the &f-link-Repository; function) @@ -1950,8 +1983,7 @@ and source directories (see the &f-link-VariantDir; function) -and -returns a Node (or string, if so configured) +and returns a Node (or string, if so configured) match in the local (SConscript) directory if a matching Node is found anywhere in a corresponding @@ -1959,65 +1991,60 @@ repository or source directory. -The +If the optional ondisk -argument may be set to a value which evaluates -False -to disable the search for matches on disk, -thereby only returning matches among -already-configured File or Dir Nodes. -The default behavior is to -return corresponding Nodes -for any on-disk matches found. +argument evaluates false, +the search for matches on disk is disabled, +and only matches from +already-configured File or Dir Nodes are returned. +The default is to return Nodes for +matches on disk as well. -The +If the optional source -argument may be set to a value which evaluates -True -to specify that, -when the local directory is a -&f-VariantDir;, -the returned Nodes should be from the -corresponding source directory, -not the local directory. +argument evaluates true, +and the local directory is a variant directory, +then &f-Glob; returnes Nodes from +the corresponding source directory, +rather than the local directory. + -The +If the optional strings -argument may be set to a value which evaluates -True -to have the +argument evaluates true, &f-Glob; -function return strings, not Nodes, -that represent the matched files or directories. +returns matches as strings, rather than Nodes. The returned strings will be relative to the local (SConscript) directory. -(Note that This may make it easier to perform +(Note that while this may make it easier to perform arbitrary manipulation of file names, -but if the returned strings are +it loses the context &SCons; would have in the Node, +so if the returned strings are passed to a different &SConscript; file, -any Node translation will be relative -to the other +any Node translation there will be relative +to that &SConscript; directory, -not the original +not to the original &SConscript; directory.) -The +The optional exclude argument may be set to a pattern or a list of patterns -(following the same Unix shell semantics) -which must be filtered out of returned elements. -Elements matching a least one pattern of -this list will be excluded. +descibing files or directories +to filter out of the match list. +Elements matching a least one specified pattern will be excluded. +These patterns use the same syntax as for +pattern. @@ -2027,9 +2054,10 @@ Examples: Program("foo", Glob("*.c")) Zip("/tmp/everything", Glob(".??*") + Glob("*")) -sources = Glob("*.cpp", exclude=["os_*_specific_*.cpp"]) + \ - Glob( "os_%s_specific_*.cpp" % currentOS) +sources = Glob("*.cpp", exclude=["os_*_specific_*.cpp"]) \ + + Glob("os_%s_specific_*.cpp" % currentOS) + @@ -2066,24 +2094,26 @@ to call all builders. -The specified dependency file(s) -will be ignored when deciding if -the target file(s) need to be rebuilt. - - - -You can also use -&f-Ignore; -to remove a target from the default build. -In order to do this you must specify the directory the target will -be built in as the target, and the file you want to skip building -as the dependency. +Ignores dependency +when deciding if +target needs to be rebuilt. +target and +dependency +can each be a single filename or Node +or a list of filenames or Nodes. -Note that this will only remove the dependencies listed from -the files built by default. It will still be built if that -dependency is needed by another object being built. +&f-Ignore; can also be used to +remove a target from the default build +by specifying the directory the target will be built in as +target +and the file you want to skip selecting for building as +dependency. +Note that this only removes the target from +the default target selection algorithm: +if it is a dependency of another object being +built &SCons; still builds it normally. See the third and forth examples below. diff --git a/SCons/Node/FS.py b/SCons/Node/FS.py index 7ce306f94b..f5642e28ee 100644 --- a/SCons/Node/FS.py +++ b/SCons/Node/FS.py @@ -2157,49 +2157,52 @@ def walk(self, func, arg): for dirname in [n for n in names if isinstance(entries[n], Dir)]: entries[dirname].walk(func, arg) - def glob(self, pathname, ondisk=True, source=False, strings=False, exclude=None): - """ - Returns a list of Nodes (or strings) matching a specified - pathname pattern. + def glob(self, pathname, ondisk=True, source=False, strings=False, exclude=None) -> list: + """Returns a list of Nodes (or strings) matching a pathname pattern. - Pathname patterns follow UNIX shell semantics: * matches - any-length strings of any characters, ? matches any character, - and [] can enclose lists or ranges of characters. Matches do - not span directory separators. + Pathname patterns follow POSIX shell syntax:: - The matches take into account Repositories, returning local - Nodes if a corresponding entry exists in a Repository (either - an in-memory Node or something on disk). + * matches everything + ? matches any single character + [seq] matches any character in seq (ranges allowed) + [!seq] matches any char not in seq - By defafult, the glob() function matches entries that exist - on-disk, in addition to in-memory Nodes. Setting the "ondisk" - argument to False (or some other non-true value) causes the glob() - function to only match in-memory Nodes. The default behavior is - to return both the on-disk and in-memory Nodes. + The wildcard characters can be escaped by enclosing in brackets. + A leading dot is not matched by a wildcard, and needs to be + explicitly included in the pattern to be matched. Matches also + do not span directory separators. - The "source" argument, when true, specifies that corresponding - source Nodes must be returned if you're globbing in a build - directory (initialized with VariantDir()). The default behavior - is to return Nodes local to the VariantDir(). + The matches take into account Repositories, returning a local + Node if a corresponding entry exists in a Repository (either + an in-memory Node or something on disk). - The "strings" argument, when true, returns the matches as strings, - not Nodes. The strings are path names relative to this directory. + The underlying algorithm is adapted from a rather old version + of :func:`glob.glob` function in the Python standard library + (heavily modified), and uses :func:`fnmatch.fnmatch` under the covers. - The "exclude" argument, if not None, must be a pattern or a list - of patterns following the same UNIX shell semantics. - Elements matching a least one pattern of this list will be excluded - from the result. + This is the internal implementation of the external Glob API. + + Args: + pattern: pathname pattern to match. + ondisk: if false, restricts matches to in-memory Nodes. + By defafult, matches entries that exist on-disk in addition + to in-memory Nodes. + source: if true, corresponding source Nodes are returned if + globbing in a variant directory. The default behavior + is to return Nodes local to the variant directory. + strings: if true, returns the matches as strings instead of + Nodes. The strings are path names relative to this directory. + exclude: if not ``None``, must be a pattern or a list of patterns + following the same POSIX shell semantics. Elements matching at + least one pattern from *exclude* will be excluded from the result. - The underlying algorithm is adapted from the glob.glob() function - in the Python library (but heavily modified), and uses fnmatch() - under the covers. """ dirname, basename = os.path.split(pathname) if not dirname: result = self._glob1(basename, ondisk, source, strings) else: if has_glob_magic(dirname): - list = self.glob(dirname, ondisk, source, False, exclude) + list = self.glob(dirname, ondisk, source, strings=False, exclude=exclude) else: list = [self.Dir(dirname, create=True)] result = [] @@ -2226,7 +2229,8 @@ def _glob1(self, pattern, ondisk=True, source=False, strings=False): corresponding entries and returns a Node (or string) relative to the current directory if an entry is found anywhere. - TODO: handle pattern with no wildcard + TODO: handle pattern with no wildcard. Python's glob.glob uses + a separate _glob0 function to do this. """ search_dir_list = self.get_all_rdirs() for srcdir in self.srcdir_list(): diff --git a/doc/user/less-simple.xml b/doc/user/less-simple.xml index 757ffacd17..3eda19c170 100644 --- a/doc/user/less-simple.xml +++ b/doc/user/less-simple.xml @@ -236,9 +236,10 @@ void file2() { printf("file2.c\n"); } - You can also use the &Glob; function to find all files matching a + You can also use the &f-link-Glob; function to find all files matching a certain template, using the standard shell pattern matching - characters *, ? + characters * (to match everything), + ? (to match a single character) and [abc] to match any of a, b or c. [!abc] is also supported, @@ -254,13 +255,14 @@ Program('program', Glob('*.c')) - The SCons man page has more details on using &Glob; - with variant directories - (see , below) + &f-Glob; has powerful capabilities - it matches even if the + file does not exist, but &SCons; can determine that it would + exist after a build. + You will meet it again reading about + variant directories + (see ) and repositories - (see , below), - excluding some files - and returning strings rather than Nodes. + (see ). diff --git a/doc/user/misc.xml b/doc/user/misc.xml index 1b18d2fe83..b1e150786b 100644 --- a/doc/user/misc.xml +++ b/doc/user/misc.xml @@ -256,11 +256,11 @@ hello.c - The &FindFile; function searches for a file in a list of directories. + The &f-link-FindFile; function searches for a file in a list of directories. If there is only one directory, it can be given as a simple string. The function returns a File node if a matching file exists, or None if no file is found. - (See the documentation for the &Glob; function for an alternative way + (See the documentation for the &f-link-Glob; function for an alternative way of searching for entries in a directory.) diff --git a/doc/user/repositories.xml b/doc/user/repositories.xml index 01edec7346..77d75d3f34 100644 --- a/doc/user/repositories.xml +++ b/doc/user/repositories.xml @@ -203,6 +203,10 @@ int main() { printf("Hello, world!\n"); } + The &f-link-Glob; function understands about repositories, + and will use the same matching algorithm as described for + explicitly-listed sources. +