1 # $Id: gendirdeps.mk,v 1.33 2016/10/11 22:37:28 sjg Exp $
3 # Copyright (c) 2010-2013, Juniper Networks, Inc.
6 # Redistribution and use in source and binary forms, with or without
7 # modification, are permitted provided that the following conditions
9 # 1. Redistributions of source code must retain the above copyright
10 # notice, this list of conditions and the following disclaimer.
11 # 2. Redistributions in binary form must reproduce the above copyright
12 # notice, this list of conditions and the following disclaimer in the
13 # documentation and/or other materials provided with the distribution.
15 # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
16 # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
17 # LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
18 # A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
19 # OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
20 # SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
21 # LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22 # DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23 # THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
25 # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 # This makefile [re]generates ${.MAKE.DEPENDFILE}
31 .
include <install-new.mk
>
34 # RELDIR is the relative path from ${SRCTOP} to ${_CURDIR}
35 # (SRCTOP is ${SB}/src)
36 # _CURDIR is the absolute version of ${.CURDIR}
37 # _OBJDIR is the absolute version of ${.OBJDIR}
38 # _objroot is realpath of ${_OBJTOP} without ${MACHINE}
39 # this may be different from _OBJROOT if $SB/obj is a
40 # symlink to another filesystem.
41 # _objroot must be a prefix match for _objtop
53 _OBJROOT ?
= ${OBJROOT
:U
${_OBJTOP}}
59 _objroot ?
= ${_OBJROOT
:tA
}${_slash}
61 _this
= ${.PARSEDIR
}/${.PARSEFILE
}
63 # remember what to make
64 _DEPENDFILE
:= ${_CURDIR}/${.MAKE.DEPENDFILE
:T
}
66 # We do _not_ want to read our own output!
67 .MAKE.DEPENDFILE
= /dev
/null
69 # caller should have set this
70 META_FILES ?
= ${.MAKE.META.FILES
}
72 .if
!empty
(META_FILES
)
74 .if
${.MAKE.LEVEL
} > 0 && !empty
(GENDIRDEPS_FILTER
)
75 # so we can compare below
76 .
-include <${_DEPENDFILE}>
77 # yes, I mean :U with no value
78 _DIRDEPS
:= ${DIRDEPS
:U
:O
:u
}
81 META_FILES
:= ${META_FILES
:T
:O
:u
}
84 # pickup customizations
85 .
-include <local.gendirdeps.mk
>
87 # these are actually prefixes that we'll skip
88 # they should all be absolute paths
90 .if
!empty
(SKIP_GENDIRDEPS
)
91 _skip_gendirdeps
= egrep
-v
'^(${SKIP_GENDIRDEPS:O:u:ts|})' |
96 # Below we will turn _{VAR} into ${VAR} which keeps this simple
97 # GENDIRDEPS_FILTER_DIR_VARS is a list of dirs to be substiuted for.
98 # GENDIRDEPS_FILTER_VARS is more general.
99 # In each case order matters.
100 .if
!empty
(GENDIRDEPS_FILTER_DIR_VARS
)
101 GENDIRDEPS_FILTER
+= ${GENDIRDEPS_FILTER_DIR_VARS
:@v@S
,${$v},_
{${v}},@
}
103 .if
!empty
(GENDIRDEPS_FILTER_VARS
)
104 GENDIRDEPS_FILTER
+= ${GENDIRDEPS_FILTER_VARS
:@v@S
,/${$v}/,/_
{${v}}/,@
:NS
,//,*:u
}
107 # this (*should* be set in meta.sys.mk)
108 # is the script that extracts what we want.
109 META2DEPS ?
= ${.PARSEDIR
}/meta2deps.sh
110 META2DEPS
:= ${META2DEPS}
112 .if
${DEBUG_GENDIRDEPS
:Uno
:@x@
${RELDIR
:M
$x}@
} != "" && ${DEBUG_GENDIRDEPS
:Uno
:Mmeta2d
*} != ""
122 .if
${META2DEPS
:E
} == "py"
123 # we can afford to do this all the time.
125 META2DEPS_CMD
= ${_time} ${PYTHON} ${META2DEPS} ${_py_d}
126 .if
${DPDEPS
:tl
} != "no"
127 META2DEPS_CMD
+= -D
${DPDEPS}
129 META2DEPS_FILTER
= sed
's,^src:,${SRCTOP}/,;s,^\([^/]\),${OBJTOP}/\1,' |
130 .elif
${META2DEPS
:E
} == "sh"
131 META2DEPS_CMD
= ${_time} ${_sh_x} ${META2DEPS} OBJTOP
=${_OBJTOP}
133 META2DEPS_CMD ?
= ${META2DEPS}
136 .if
${TARGET_OBJ_SPEC
:U
${MACHINE}} != ${MACHINE}
137 META2DEPS_CMD
+= -T
${TARGET_OBJ_SPEC}
140 -R
${RELDIR} -H
${HOST_TARGET} \
141 ${M2D_OBJROOTS
:O
:u
:@o@
-O
$o@
} \
142 ${M2D_EXCLUDES
:O
:u
:@o@
-X
$o@
} \
145 M2D_OBJROOTS
+= ${OBJTOP} ${_OBJROOT} ${_objroot}
146 .if defined
(SB_OBJROOT
)
147 M2D_OBJROOTS
+= ${SB_OBJROOT}
149 .if defined
(STAGE_ROOT
)
150 M2D_OBJROOTS
+= ${STAGE_ROOT}
152 .if
${.MAKE.DEPENDFILE_PREFERENCE
:U
${.MAKE.DEPENDFILE
}:M
*.
${MACHINE}} == ""
153 # meta2deps.py only groks objroot
154 # so we need to give it what it expects
155 # and tell it not to add machine qualifiers
156 META2DEPS_ARGS
+= MACHINE
=none
158 .if defined
(SB_BACKING_SB
)
159 META2DEPS_CMD
+= -S
${SB_BACKING_SB}/src
160 M2D_OBJROOTS
+= ${SB_BACKING_SB}/${SB_OBJPREFIX}
163 # we are only interested in the dirs
164 # specifically those we read something from.
165 # we canonicalize them to keep things simple
166 # if we are using a split-fs sandbox, it gets a little messier.
167 _objtop
:= ${_OBJTOP
:tA
}
168 dir_list
!= cd
${_OBJDIR} && \
169 ${META2DEPS_CMD} MACHINE
=${MACHINE} \
170 SRCTOP
=${SRCTOP} RELDIR
=${RELDIR} CURDIR
=${_CURDIR} \
172 ${META_FILES
:O
:u
} |
${META2DEPS_FILTER} ${_skip_gendirdeps} \
173 sed
's,//*$$,,;s,\.${HOST_TARGET}$$,.host,'
175 .if
${dir_list
:M
*ERROR\
:*} != ""
176 .warning
${dir_list
:tW
:C
,.
*(ERROR
),\
1,}
177 .warning Skipping
${_DEPENDFILE
:S
,${SRCTOP}/,,}
178 # we are not going to update anything
182 _nonlibs
:= ${DPADD
:T
:Nlib
*:N
*include}
185 .for f in
${_nonlibs
:@x@
${DPADD
:M
*/$x}@
}
186 .if exists
($f.dirdep
)
187 ddep_list
+= $f.dirdep
188 .elif exists
(${f
:H
}.dirdep
)
189 ddep_list
+= ${f
:H
}.dirdep
191 dir_list
+= ${f
:H
:tA
}
192 dpadd_dir_list
+= ${f
:H
:tA
}
195 .if
!empty
(ddep_list
)
196 ddeps
!= cat
${ddep_list
:O
:u
} |
${META2DEPS_FILTER} ${_skip_gendirdeps} \
197 sed
's,//*$$,,;s,\.${HOST_TARGET}$$,.host,;s,\.${MACHINE}$$,,'
199 .if
${DEBUG_GENDIRDEPS
:Uno
:@x@
${RELDIR
:M
$x}@
} != ""
200 .
info ${RELDIR}: raw_dir_list
='${dir_list}'
201 .
info ${RELDIR}: ddeps
='${ddeps}'
208 # DIRDEPS represent things that had to have been built first
209 # so they should all be undir OBJTOP.
210 # Note that ${_OBJTOP}/bsd/include/machine will get reported
211 # to us as $SRCTOP/bsd/sys/$MACHINE_ARCH/include meaning we
212 # will want to visit bsd/include
214 # ${"${dir_list:M*bsd/sys/${MACHINE_ARCH}/include}":?bsd/include:}
215 # to GENDIRDEPS_DIR_LIST_XTRAS
216 _objtops
= ${OBJTOP} ${_OBJTOP} ${_objtop}
217 _objtops
:= ${_objtops
:O
:u
}
219 ${_objtops
:@o@
${dir_list
:M
$o*/*:C
,$o[^
/]*/,,}@
} \
220 ${GENDIRDEPS_DIR_LIST_XTRAS}
223 M2D_OBJROOTS
:= ${M2D_OBJROOTS
:O
:u
:[-1.
.1]}
225 # anything we use from an object dir other than ours
226 # needs to be qualified with its .<machine> suffix
227 # (we used the pseudo machine "host" for the HOST_TARGET).
228 skip_ql
= ${SRCTOP}* ${_objtops
:@o@
$o*@
}
229 .for o in
${M2D_OBJROOTS
:${skip_ql
:${M_ListToSkip}}}
230 # we need := so only skip_ql to this point applies
231 ql.
$o := ${dir_list
:${skip_ql
:${M_ListToSkip}}:M
$o*/*/*:C
,$o([^
/]+)/(.
*),\
2.\
1,:S
,.
${HOST_TARGET},.host
,}
232 qualdir_list
+= ${ql.
$o}
233 .if
${DEBUG_GENDIRDEPS
:Uno
:@x@
${RELDIR
:M
$x}@
} != ""
234 .
info ${RELDIR}: o
=$o ${ql.
$o qualdir_list
:L
:@v@
$v=${$v}@
}
239 dirdep_list
:= ${dirdep_list
:O
:u
}
240 qualdir_list
:= ${qualdir_list
:N
*.
${MACHINE}:O
:u
}
243 ${dirdep_list
:N
${RELDIR}:N
${RELDIR}/*} \
244 ${qualdir_list
:N
${RELDIR}.
*:N
${RELDIR}/*}
246 # We only consider things below $RELDIR/ if they have a makefile.
247 # This is the same test that _DIRDEP_USE applies.
248 # We have do a double test with dirdep_list as it _may_ contain
249 # qualified dirs - if we got anything from a stage dir.
250 # qualdir_list we know are all qualified.
251 # It would be nice do peform this check for all of DIRDEPS,
252 # but we cannot assume that all of the tree is present,
253 # in fact we can only assume that RELDIR is.
255 ${dirdep_list
:M
${RELDIR}/*:@d@
${.MAKE.MAKEFILE_PREFERENCE
:@m@
${exists
(${SRCTOP}/$d/$m):?
$d:${exists
(${SRCTOP}/${d
:R
}/$m):?
$d:}}@
}@
} \
256 ${qualdir_list
:M
${RELDIR}/*:@d@
${.MAKE.MAKEFILE_PREFERENCE
:@m@
${exists
(${SRCTOP}/${d
:R
}/$m):?
$d:}@
}@
}
258 DIRDEPS
:= ${DIRDEPS
:${GENDIRDEPS_FILTER
:UNno
:ts
:}:C
,//+,/,g
:O
:u
}
260 .if
${DEBUG_GENDIRDEPS
:Uno
:@x@
${RELDIR
:M
$x}@
} != ""
261 .
info ${RELDIR}: M2D_OBJROOTS
=${M2D_OBJROOTS}
262 .
info ${RELDIR}: M2D_EXCLUDES
=${M2D_EXCLUDES}
263 .
info ${RELDIR}: dir_list
='${dir_list}'
264 .
info ${RELDIR}: dpadd_dir_list
='${dpadd_dir_list}'
265 .
info ${RELDIR}: dirdep_list
='${dirdep_list}'
266 .
info ${RELDIR}: qualdir_list
='${qualdir_list}'
267 .
info ${RELDIR}: SKIP_GENDIRDEPS
='${SKIP_GENDIRDEPS}'
268 .
info ${RELDIR}: GENDIRDEPS_FILTER
='${GENDIRDEPS_FILTER}'
269 .
info ${RELDIR}: FORCE_DPADD
='${DPADD}'
270 .
info ${RELDIR}: DIRDEPS
='${DIRDEPS}'
273 # SRC_DIRDEPS is for checkout logic
275 ${dir_list
:M
${SRCTOP}/*:S
,${SRCTOP}/,,}
278 ${src_dirdep_list
:N
${RELDIR}:N
${RELDIR}/*:C
,(/h
)/.
*,,}
280 SRC_DIRDEPS
:= ${SRC_DIRDEPS
:${GENDIRDEPS_SRC_FILTER
:UN
/*:ts
:}:C
,//+,/,g
:O
:u
}
282 # if you want to capture SRC_DIRDEPS in .MAKE.DEPENDFILE put
283 # SRC_DIRDEPS_FILE = ${_DEPENDFILE}
284 # in local.gendirdeps.mk
285 .if
${SRC_DIRDEPS_FILE
:Uno
:tl
} != "no"
286 ECHO_SRC_DIRDEPS
= echo
'SRC_DIRDEPS = \'; echo '${SRC_DIRDEPS
:@d@
$d \\${.newline
}@
}'; echo;
288 .if ${SRC_DIRDEPS_FILE:T} == ${_DEPENDFILE:T}
289 _include_src_dirdeps = ${ECHO_SRC_DIRDEPS}
291 all: ${SRC_DIRDEPS_FILE}
292 .if !target(${SRC_DIRDEPS_FILE})
293 ${SRC_DIRDEPS_FILE}: ${META_FILES} ${_this} ${META2DEPS}
294 @(${ECHO_SRC_DIRDEPS}) > $@
298 _include_src_dirdeps ?=
302 # if this is going to exist it would be there by now
304 CAT_DEPEND = /dev/null
306 CAT_DEPEND ?= .depend
308 .if !empty(_DIRDEPS) && ${DIRDEPS} != ${_DIRDEPS}
309 # we may have changed a filter
310 .PHONY: ${_DEPENDFILE}
313 # 'cat .depend
' should suffice, but if we are mixing build modes
314 # .depend may contain things we don't want.
315 # The sed command at the end of the stream, allows for the filters
316 # to output _{VAR} tokens which we will turn into proper ${VAR} references.
317 ${_DEPENDFILE}: .NOMETA
${CAT_DEPEND
:M.depend
} ${META_FILES
:O
:u
:@m@
${exists
($m):?
$m:}@
} ${_this} ${META2DEPS}
318 @
(${GENDIRDEPS_HEADER} echo
'# Autogenerated - do NOT edit!'; echo
; \
319 echo
'DIRDEPS = \'; \
320 echo '${DIRDEPS
:@d@
$d \\${.newline
}@
}'; echo; \
321 ${_include_src_dirdeps} \
322 echo '.
include <dirdeps.mk
>'; \
324 echo '.if
$${DEP_RELDIR} == $${_DEP_RELDIR}'; \
325 echo '# local dependencies - needed for -jN in clean tree'; \
326 [ -s
${CAT_DEPEND} ] && { grep
: ${CAT_DEPEND} | grep
-v
'[/\\]'; }; \
327 echo
'.endif' ) | sed
's,_\([{(]\),$$\1,g' > $@.new
${.MAKE.PID
}
328 @
${InstallNew}; InstallNew
-s
$@.new
${.MAKE.PID
}
330 .
endif # meta2deps failed
333 DIRDEPS
:= ${SUBDIR
:S
,^
,${RELDIR}/,:O
:u
}
337 ${_DEPENDFILE}: .NOMETA
${MAKEFILE} ${_this}
338 @
(${GENDIRDEPS_HEADER} echo
'# Autogenerated - do NOT edit!'; echo
; \
339 echo
'DIRDEPS = \'; \
340 echo '${DIRDEPS
:@d@
$d \\${.newline
}@
}'; echo; \
341 echo '.
include <dirdeps.mk
>'; \
342 echo ) | sed 's
,_\
([{(]\
),$$\
1,g
' > $@.new
343 @${InstallNew}; InstallNew $@.new
351 ${_DEPENDFILE}: .PRECIOUS