hc
2024-12-19 9370bb92b2d16684ee45cf24e879c93c509162da
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
# Cleaning directories generated during a previous build,
# a failed previous build or even no previous build.
# Track build directories through 'cleanfiles'.
 
define _enum-parent-dirs
$(if $(1),$(1) $(if $(filter / ./,$(dir $(1))),,$(call enum-parent-dirs,$(dir $(1)))),)
endef
 
define enum-parent-dirs
$(call _enum-parent-dirs,$(patsubst %/,%,$(1)))
endef
 
define _reverse
$(if $(1),$(call _reverse,$(wordlist 2,$(words $(1)),$(1)))) $(firstword $(1))
endef
 
# Returns the list of all existing output directories up to $(O) including all
# intermediate levels, in depth first order so that rmdir can process them in
# order. May return an empty string.
# Example: if cleanfiles is "foo/a/file1 foo/b/c/d/file2" and O=foo, this will
# return "foo/b/c/d foo/b/c foo/b foo/a" (assuming all exist).
define cleandirs-for-rmdir
$(eval _O:=$(if $(O),$(O),.))$(wildcard $(addprefix $(_O)/,$(call _reverse,
   $(sort $(foreach d,$(patsubst $(_O)/%,%,$(dir $(cleanfiles))),
              $(call enum-parent-dirs,$(d)))))))
endef
 
RMDIR := rmdir --ignore-fail-on-non-empty
 
# Remove files with "rm -f".
# Split (possibly huge) file list into more manageable lines
# (200 files at a time), to minimize the odds of having:
# "/bin/bash: Argument list too long"
define do-rm-f
        $(call _do-rm-f, $(wordlist 1, 200, $(1))) \
        $(eval _tail := $(wordlist 201, $(words $(1)), $(1)))
        $(if $(_tail), $(call do-rm-f, $(_tail)))
endef
 
define _do-rm-f
        ${q}rm -f $1
endef