xref: /freebsd/contrib/bmake/mk/dirdeps-cache-update.mk (revision 2c3632d14fe37fa35c262ee9fb66835be0a52621)
1*2c3632d1SSimon J. Gerraty# $Id: dirdeps-cache-update.mk,v 1.21 2020/08/19 17:51:53 sjg Exp $
2*2c3632d1SSimon J. Gerraty#
3*2c3632d1SSimon J. Gerraty#	@(#) Copyright (c) 2020, Simon J. Gerraty
4*2c3632d1SSimon J. Gerraty#
5*2c3632d1SSimon J. Gerraty#	This file is provided in the hope that it will
6*2c3632d1SSimon J. Gerraty#	be of use.  There is absolutely NO WARRANTY.
7*2c3632d1SSimon J. Gerraty#	Permission to copy, redistribute or otherwise
8*2c3632d1SSimon J. Gerraty#	use this file is hereby granted provided that
9*2c3632d1SSimon J. Gerraty#	the above copyright notice and this notice are
10*2c3632d1SSimon J. Gerraty#	left intact.
11*2c3632d1SSimon J. Gerraty#
12*2c3632d1SSimon J. Gerraty#	Please send copies of changes and bug-fixes to:
13*2c3632d1SSimon J. Gerraty#	sjg@crufty.net
14*2c3632d1SSimon J. Gerraty#
15*2c3632d1SSimon J. Gerraty
16*2c3632d1SSimon J. Gerraty##
17*2c3632d1SSimon J. Gerraty#
18*2c3632d1SSimon J. Gerraty# This makefile deals with the updating of STATIC_DIRDEPS_CACHE.
19*2c3632d1SSimon J. Gerraty# Some targets are so huge that computing dirdeps takes a significant
20*2c3632d1SSimon J. Gerraty# amount of time.  For such targets a STATIC_DIRDEPS_CACHE can make
21*2c3632d1SSimon J. Gerraty# sense.
22*2c3632d1SSimon J. Gerraty#
23*2c3632d1SSimon J. Gerraty# If the target is represented by targets/pseudo/production
24*2c3632d1SSimon J. Gerraty# it's normal DIRDEPS would be in
25*2c3632d1SSimon J. Gerraty# targets/pseudo/production/Makefile.depend
26*2c3632d1SSimon J. Gerraty# and STATIC_DIRDEPS_CACHE would be
27*2c3632d1SSimon J. Gerraty# targets/pseudo/production/Makefile.dirdeps.cache
28*2c3632d1SSimon J. Gerraty# which is simply initialized by copying dirdeps.cache.production
29*2c3632d1SSimon J. Gerraty# from $OBJTOP
30*2c3632d1SSimon J. Gerraty#
31*2c3632d1SSimon J. Gerraty# When dirdeps-targets.mk is initializing DIRDEPS it will look for
32*2c3632d1SSimon J. Gerraty# Makefile.dirdeps.cache and unless told not to
33*2c3632d1SSimon J. Gerraty# (MK_STATIC_DIRDEPS_CACHE=no) will use it as DIRDEPS_CACHE.
34*2c3632d1SSimon J. Gerraty#
35*2c3632d1SSimon J. Gerraty# If MK_STATIC_DIRDEPS_CACHE_UPDATE is "yes", then this makefile
36*2c3632d1SSimon J. Gerraty# comes into play.
37*2c3632d1SSimon J. Gerraty#
38*2c3632d1SSimon J. Gerraty# We usually get included from local.dirdeps.mk
39*2c3632d1SSimon J. Gerraty# as well as Makefile.depend of RELDIR with a static Makefile.dirdeps.cache
40*2c3632d1SSimon J. Gerraty#
41*2c3632d1SSimon J. Gerraty# If we see that STATIC_DIRDEPS_CACHE is in use, we need to hook a
42*2c3632d1SSimon J. Gerraty# cache-update target into the build to regenerate dirdeps.cache
43*2c3632d1SSimon J. Gerraty# in parallel with the rest of the build.
44*2c3632d1SSimon J. Gerraty# If MK_STATIC_DIRDEPS_CACHE_UPDATE_IMMEDIATE is "yes" we update
45*2c3632d1SSimon J. Gerraty# STATIC_DIRDEPS_CACHE as soon as the update is ready,
46*2c3632d1SSimon J. Gerraty# otherwise it will be done at the end of the build.
47*2c3632d1SSimon J. Gerraty#
48*2c3632d1SSimon J. Gerraty# If STATIC_DIRDEPS_CACHE is not in use, but a DIRDEPS_CACHE is,
49*2c3632d1SSimon J. Gerraty# then we need do nothing except export STATIC_DIRDEPS_CACHE and
50*2c3632d1SSimon J. Gerraty# DYNAMIC_DIRDEPS_CACHE for use when we are include during the visit
51*2c3632d1SSimon J. Gerraty# to the ultimate target (targets/pseudo/production).
52*2c3632d1SSimon J. Gerraty#
53*2c3632d1SSimon J. Gerraty# Regardless of which happens, when included at .MAKE.LEVEL > 0
54*2c3632d1SSimon J. Gerraty# for a target other than cache-update we simply copy
55*2c3632d1SSimon J. Gerraty# DYNAMIC_DIRDEPS_CACHE to STATIC_DIRDEPS_CACHE with some optional
56*2c3632d1SSimon J. Gerraty# filtering.
57*2c3632d1SSimon J. Gerraty#
58*2c3632d1SSimon J. Gerraty# If we are included for the target cache-update we take care of
59*2c3632d1SSimon J. Gerraty# running dirdeps.mk again to generate the DYNAMIC_DIRDEPS_CACHE.
60*2c3632d1SSimon J. Gerraty#
61*2c3632d1SSimon J. Gerraty
62*2c3632d1SSimon J. Gerraty.if !target(_${.PARSEFILE}_)
63*2c3632d1SSimon J. Gerraty_${.PARSEFILE}_: .NOTMAIN
64*2c3632d1SSimon J. Gerraty
65*2c3632d1SSimon J. GerratySTATIC_CACHE_SED += \
66*2c3632d1SSimon J. Gerraty	-e '/Autogenerated/s,-.*,- edit with care!,' \
67*2c3632d1SSimon J. Gerraty	-e '/cache-update/d'
68*2c3632d1SSimon J. Gerraty
69*2c3632d1SSimon J. GerratySTATIC_DIRDEPS_CACHE_UPDATE_SCRIPT ?= \
70*2c3632d1SSimon J. Gerraty	{ echo Saving ${DYNAMIC_DIRDEPS_CACHE} as ${STATIC_DIRDEPS_CACHE}; \
71*2c3632d1SSimon J. Gerraty        sed ${STATIC_CACHE_SED} ${DYNAMIC_DIRDEPS_CACHE} > ${STATIC_DIRDEPS_CACHE}; }
72*2c3632d1SSimon J. Gerraty.endif
73*2c3632d1SSimon J. Gerraty
74*2c3632d1SSimon J. Gerraty.if ${MK_DIRDEPS_CACHE:Uno} == "yes"
75*2c3632d1SSimon J. Gerraty.if ${MK_STATIC_DIRDEPS_CACHE_UPDATE:Uno} == "yes"
76*2c3632d1SSimon J. Gerraty.if ${_debug_reldir:U0} || ${DEBUG_DIRDEPS:U:Mcache*} != ""
77*2c3632d1SSimon J. Gerraty_debug_cache = 1
78*2c3632d1SSimon J. Gerraty.else
79*2c3632d1SSimon J. Gerraty_debug_cache = 0
80*2c3632d1SSimon J. Gerraty.endif
81*2c3632d1SSimon J. Gerraty
82*2c3632d1SSimon J. Gerraty.if ${.MAKE.LEVEL} == 0 && !make(cache-update)
83*2c3632d1SSimon J. Gerraty
84*2c3632d1SSimon J. Gerraty.if ${_debug_cache}
85*2c3632d1SSimon J. Gerraty.info ${MK_STATIC_DIRDEPS_CACHE_UPDATE MK_STATIC_DIRDEPS_CACHE MK_DIRDEPS_CACHE DIRDEPS_CACHE STATIC_DIRDEPS_CACHE:L:@v@$v=${$v}@}
86*2c3632d1SSimon J. Gerraty.endif
87*2c3632d1SSimon J. Gerraty
88*2c3632d1SSimon J. Gerraty.if ${MK_STATIC_DIRDEPS_CACHE} == "yes" && defined(STATIC_DIRDEPS_CACHE) && exists(${STATIC_DIRDEPS_CACHE})
89*2c3632d1SSimon J. Gerraty.if !make(dirdeps)
90*2c3632d1SSimon J. Gerraty# We are using static cache and this is the only look we will get.
91*2c3632d1SSimon J. Gerraty# We want to generate an updated cache while we build
92*2c3632d1SSimon J. Gerraty# so need to hook cache-update to dirdeps now.
93*2c3632d1SSimon J. Gerraty# Note: we are running as a sibling to dirdeps-cached,
94*2c3632d1SSimon J. Gerraty# attempting to do this in that context is problematic.
95*2c3632d1SSimon J. Gerraty
96*2c3632d1SSimon J. Gerraty# One of these should exist - to actually kick off the cache generation
97*2c3632d1SSimon J. Gerraty.for d in ${STATIC_DIRDEPS_CACHE:H}/cache-update ${STATIC_DIRDEPS_CACHE:H:H}/cache-update ${STATIC_DIRDEPS_CACHE:H:H:H}/cache-update
98*2c3632d1SSimon J. Gerraty.if exists($d)
99*2c3632d1SSimon J. Gerratycache_update_dirdep ?= $d.${TARGET_SPEC}
100*2c3632d1SSimon J. Gerraty.endif
101*2c3632d1SSimon J. Gerraty.endfor
102*2c3632d1SSimon J. Gerraty.if !target(${cache_update_dirdep})
103*2c3632d1SSimon J. Gerratydirdeps: ${cache_update_dirdep}
104*2c3632d1SSimon J. Gerraty${cache_update_dirdep}: _DIRDEP_USE
105*2c3632d1SSimon J. GerratyDYNAMIC_DIRDEPS_CACHE := ${OBJTOP}/dirdeps.cache.${STATIC_DIRDEPS_CACHE:H:T}-update
106*2c3632d1SSimon J. Gerraty.export DYNAMIC_DIRDEPS_CACHE STATIC_DIRDEPS_CACHE
107*2c3632d1SSimon J. Gerraty.endif
108*2c3632d1SSimon J. Gerraty.endif	# make(dirdeps)
109*2c3632d1SSimon J. Gerraty.endif	# MK_*
110*2c3632d1SSimon J. Gerraty
111*2c3632d1SSimon J. Gerraty.endif	# .MAKE.LEVEL 0
112*2c3632d1SSimon J. Gerraty
113*2c3632d1SSimon J. Gerraty.if ${.MAKE.LEVEL} > 0 && ${.CURDIR:T} == "cache-update"
114*2c3632d1SSimon J. Gerraty# we are the background update shim
115*2c3632d1SSimon J. Gerraty
116*2c3632d1SSimon J. Gerraty.if ${_debug_cache}
117*2c3632d1SSimon J. Gerraty.info level ${.MAKE.LEVEL}: ${MK_DIRDEPS_CACHE DYNAMIC_DIRDEPS_CACHE STATIC_DIRDEPS_CACHE:L:@v@$v=${$v}@}
118*2c3632d1SSimon J. Gerraty.endif
119*2c3632d1SSimon J. Gerraty
120*2c3632d1SSimon J. Gerratyall: cache-build
121*2c3632d1SSimon J. Gerratycache-build: .META
122*2c3632d1SSimon J. Gerraty	@set -x; MAKELEVEL=0 \
123*2c3632d1SSimon J. Gerraty	${.MAKE} -C ${SRCTOP} -f ${RELDIR}/Makefile cache-update \
124*2c3632d1SSimon J. Gerraty	-DWITHOUT_STATIC_DIRDEPS_CACHE_UPDATE
125*2c3632d1SSimon J. Gerraty
126*2c3632d1SSimon J. Gerraty.endif	# cache-update
127*2c3632d1SSimon J. Gerraty
128*2c3632d1SSimon J. Gerraty.elif ${.MAKE.LEVEL} == 0 && make(cache-update) && !target(cache-update)
129*2c3632d1SSimon J. Gerraty# we were invoked above
130*2c3632d1SSimon J. Gerraty# we just leverage dirdeps.mk
131*2c3632d1SSimon J. GerratyBUILD_DIRDEPS_TARGETS := ${STATIC_DIRDEPS_CACHE:H:T}
132*2c3632d1SSimon J. GerratyDIRDEPS := ${STATIC_DIRDEPS_CACHE:H:S,^${SRCTOP}/,,}.${TARGET_SPEC}
133*2c3632d1SSimon J. GerratyDIRDEPS_CACHE := ${DYNAMIC_DIRDEPS_CACHE}
134*2c3632d1SSimon J. Gerraty
135*2c3632d1SSimon J. Gerraty.if ${DEBUG_DIRDEPS:U:Mcache*} != ""
136*2c3632d1SSimon J. Gerraty.info level 0: ${MK_DIRDEPS_CACHE DIRDEPS_CACHE DIRDEPS:L:@v@$v=${$v}@}
137*2c3632d1SSimon J. Gerraty.endif
138*2c3632d1SSimon J. Gerraty
139*2c3632d1SSimon J. Gerraty# so cache-built below can check on us
140*2c3632d1SSimon J. Gerratyx!= echo; echo ${.MAKE.PID} > ${DIRDEPS_CACHE}.new.pid
141*2c3632d1SSimon J. Gerraty
142*2c3632d1SSimon J. Gerratycache-update: ${DIRDEPS_CACHE}
143*2c3632d1SSimon J. Gerraty	@rm -f ${DIRDEPS_CACHE}.new.pid
144*2c3632d1SSimon J. Gerraty.if ${MK_STATIC_DIRDEPS_CACHE_UPDATE_IMMEDIATE:Uno} == "yes"
145*2c3632d1SSimon J. Gerraty	${STATIC_DIRDEPS_CACHE_UPDATE_SCRIPT}
146*2c3632d1SSimon J. Gerraty.endif
147*2c3632d1SSimon J. Gerraty
148*2c3632d1SSimon J. Gerratyall:
149*2c3632d1SSimon J. Gerraty
150*2c3632d1SSimon J. Gerraty.include <dirdeps.mk>
151*2c3632d1SSimon J. Gerraty
152*2c3632d1SSimon J. Gerraty.endif	# MK_STATIC_DIRDEPS_CACHE_UPDATE
153*2c3632d1SSimon J. Gerraty.endif	# MK_DIRDEPS_CACHE
154*2c3632d1SSimon J. Gerraty
155*2c3632d1SSimon J. Gerraty.if ${.MAKE.LEVEL} > 0 && ${MK_STATIC_DIRDEPS_CACHE_UPDATE:Uno} == "yes" && \
156*2c3632d1SSimon J. Gerraty	${STATIC_DIRDEPS_CACHE:Uno:H} == "${SRCTOP}/${RELDIR}"
157*2c3632d1SSimon J. Gerraty.if !defined(DYNAMIC_DIRDEPS_CACHE)
158*2c3632d1SSimon J. Gerratyall:
159*2c3632d1SSimon J. Gerraty.else
160*2c3632d1SSimon J. Gerraty# This is the easy bit, time to save the cache
161*2c3632d1SSimon J. Gerraty
162*2c3632d1SSimon J. Gerratyall: cache-update
163*2c3632d1SSimon J. Gerraty
164*2c3632d1SSimon J. Gerraty# ensure the cache update is completed
165*2c3632d1SSimon J. Gerratycache-built:
166*2c3632d1SSimon J. Gerraty	@test -s ${DYNAMIC_DIRDEPS_CACHE}.new || exit 0; \
167*2c3632d1SSimon J. Gerraty	pid=`cat ${DYNAMIC_DIRDEPS_CACHE}.new.pid 2> /dev/null`; \
168*2c3632d1SSimon J. Gerraty	test $${pid:-0} -gt 1 || exit 0; \
169*2c3632d1SSimon J. Gerraty	echo "Waiting for $$pid to finish ${DYNAMIC_DIRDEPS_CACHE} ..."; \
170*2c3632d1SSimon J. Gerraty	while 'kill' -0 $$pid; do sleep 30; done > /dev/null 2>&1
171*2c3632d1SSimon J. Gerraty
172*2c3632d1SSimon J. Gerratycache-update: cache-built
173*2c3632d1SSimon J. Gerraty.if ${MK_STATIC_DIRDEPS_CACHE_UPDATE_IMMEDIATE:Uno} == "no"
174*2c3632d1SSimon J. Gerraty	@test ! -s ${DYNAMIC_DIRDEPS_CACHE} || \
175*2c3632d1SSimon J. Gerraty	${STATIC_DIRDEPS_CACHE_UPDATE_SCRIPT}
176*2c3632d1SSimon J. Gerraty.endif
177*2c3632d1SSimon J. Gerraty
178*2c3632d1SSimon J. Gerraty.endif
179*2c3632d1SSimon J. Gerraty.endif
180