1 # $NetBSD: check-files.mk,v 1.28 2012/05/22 07:59:31 marino Exp $
3 # This file checks that the list of installed files matches the PLIST.
4 # For that purpose it records the file list of LOCALBASE before and
5 # after the installation of the package and compares these lists with
8 # User-settable variables:
11 # "yes" to enable the check, "no" to disable it.
13 # Default value: "yes" for PKG_DEVELOPERs, "no" otherwise.
16 # When set to "yes", VARBASE and PKG_SYSCONFDIR are checked in
17 # addition to LOCALBASE.
19 # Package-settable variables:
22 # A list of regular expressions (FIXME: all other checks use shell
23 # patterns) that names files to be skipped. This is useful to
24 # avoid getting errors triggered by changes in directories not
25 # really handled by pkgsrc.
28 _VARGROUPS
+= check-files
29 _USER_VARS.check-files
= CHECK_FILES CHECK_FILES_STRICT
30 _PKG_VARS.check-files
= CHECK_FILES_SKIP
32 .if defined
(PKG_DEVELOPER
) && ${PKG_DEVELOPER} != "no"
36 CHECK_FILES_STRICT?
= no
38 # Info index files updated when a new info file is added.
39 .if defined
(INFO_FILES
)
40 CHECK_FILES_SKIP
+= ${PREFIX}/.
*/dir
43 # Perl's perllocal.pod index that is regenerated when a local module
46 CHECK_FILES_SKIP
+= ${PERL5_INSTALLARCHLIB}/perllocal.pod
48 # R's index files that are regenerated when a local module
51 CHECK_FILES_SKIP
+= ${PREFIX}/lib
/R
/doc
/html
/packages.html
52 CHECK_FILES_SKIP
+= ${PREFIX}/lib
/R
/doc
/html
/search
/index.txt
54 CHECK_FILES_SKIP
+= ${PKG_DBDIR}/.
*
56 # We don't care about what's under linux/proc and linux32/proc in Linux
57 # emulation, which just holds run-time generated data.
59 CHECK_FILES_SKIP
+= ${PREFIX}/emul
/linux
/proc.
*
60 CHECK_FILES_SKIP
+= ${PREFIX}/emul
/linux32
/proc.
*
62 # The reference-count meta-data directory used by the pkginstall framework.
63 CHECK_FILES_SKIP
+= ${PKG_DBDIR}.refcount.
*
65 # Some people have their distfiles and binary packages below ${LOCALBASE}.
66 CHECK_FILES_SKIP
+= ${PACKAGES}/.
*
67 CHECK_FILES_SKIP
+= ${DISTDIR}/.
*
69 # For unprivileged builds, VARBASE is below LOCALBASE.
70 .if
!empty
(CHECK_FILES_STRICT
:M
[Nn
][Oo
])
71 CHECK_FILES_SKIP
+= ${VARBASE}/.
*
74 # File that are outside of ${PREFIX} in directories we already know we'll
75 # be using for mutable data.
77 .for d in
${MAKE_DIRS} ${OWN_DIRS}
78 CHECK_FILES_SKIP
+= ${d
:C
/^
([^\
/])/${PREFIX}\
/\
1/}.
*
80 .for d o g m in
${MAKE_DIRS_PERMS} ${OWN_DIRS_PERMS}
81 CHECK_FILES_SKIP
+= ${d
:C
/^
([^\
/])/${PREFIX}\
/\
1/}.
*
84 # Mutable X11 font database files
85 .if
(defined
(FONTS_DIRS.x11
) && !empty
(FONTS_DIRS.x11
:M
*))
86 CHECK_FILES_SKIP
+= ${PREFIX}/.
*/encodings.
dir
87 CHECK_FILES_SKIP
+= ${PREFIX}/.
*/fonts.
dir
89 .if
(defined
(FONTS_DIRS.ttf
) && !empty
(FONTS_DIRS.ttf
:M
*)) || \
90 (defined
(FONTS_DIRS.type1
) && !empty
(FONTS_DIRS.type1
:M
*))
91 CHECK_FILES_SKIP
+= ${PREFIX}/.
*/fonts.scale
93 .if
(defined
(FONTS_DIRS.ttf
) && !empty
(FONTS_DIRS.ttf
:M
*)) || \
94 (defined
(FONTS_DIRS.type1
) && !empty
(FONTS_DIRS.type1
:M
*)) || \
95 (defined
(FONTS_DIRS.x11
) && !empty
(FONTS_DIRS.x11
:M
*))
96 CHECK_FILES_SKIP
+= ${PREFIX}/.
*/fonts.cache-1
99 # Mutable charset.alias file
100 CHECK_FILES_SKIP
+= ${PREFIX}/lib
/charset.alias
102 # Mutable locale.alias file
103 CHECK_FILES_SKIP
+= ${PREFIX}/share
/locale
/locale.alias
105 _CHECK_FILES_SKIP_FILTER
= ${GREP} -vx
${CHECK_FILES_SKIP
:@f@
-e
${DESTDIR
:Q
}${f
:Q
}@
}
107 ###########################################################################
108 # These are the files generated and used by the check-files implementation
109 # used across several check-files targets.
111 # _CHECK_FILES_ERRMSG.* are the files that contain the error
112 # messages discovered during each stage of file-checking.
114 # _CHECK_FILES_PRE.* are the file lists generated before any files
115 # from the package are installed.
117 # _CHECK_FILES_POST.* are the file lists generated after all files
118 # from the package are installed.
120 # The "pre" and "post" file lists are compared against each other to
121 # determine if the package is installing files where it shouldn't be.
123 _CHECK_FILES_ERRMSG.
prefix= ${ERROR_DIR}/check-files-prefix
124 _CHECK_FILES_PRE.
prefix= ${WRKDIR}/.
prefix.pre
125 _CHECK_FILES_POST.
prefix= ${WRKDIR}/.
prefix.post
127 _CHECK_FILES_ERRMSG.sysconfdir
= ${ERROR_DIR}/.check-files-sysconfdir
128 _CHECK_FILES_PRE.sysconfdir
= ${WRKDIR}/.sysconfdir.pre
129 _CHECK_FILES_POST.sysconfdir
= ${WRKDIR}/.sysconfdir.post
131 _CHECK_FILES_ERRMSG.varbase
= ${ERROR_DIR}/.check-files-varbase
132 _CHECK_FILES_PRE.varbase
= ${WRKDIR}/.varbase.pre
133 _CHECK_FILES_POST.varbase
= ${WRKDIR}/.varbase.post
135 _CHECK_FILES_ERRMSGS
= # empty
136 _CHECK_FILES_ERRMSGS
+= ${_CHECK_FILES_ERRMSG.
prefix}
137 .if empty
(CHECK_FILES_STRICT
:M
[nN
][oO
])
138 _CHECK_FILES_ERRMSGS
+= ${_CHECK_FILES_ERRMSG.sysconfdir
}
139 _CHECK_FILES_ERRMSGS
+= ${_CHECK_FILES_ERRMSG.varbase
}
142 ###########################################################################
143 # _CHECK_FILES_PRE holds the list of targets that are built as part of
144 # building the check-files-pre target. These targets should cause the
145 # "pre" file lists to be generated.
147 _CHECK_FILES_PRE
= check-files-pre-message
148 _CHECK_FILES_PRE
+= ${_CHECK_FILES_PRE.
prefix}
149 .if empty
(CHECK_FILES_STRICT
:M
[nN
][oO
])
150 _CHECK_FILES_PRE
+= ${_CHECK_FILES_PRE.sysconfdir
}
151 _CHECK_FILES_PRE
+= ${_CHECK_FILES_PRE.varbase
}
154 ###########################################################################
155 # _CHECK_FILES_POST holds the list of targets that are built as part of
156 # building the check-files-post target. These targets should cause the
157 # "post" file lists to be generated.
159 _CHECK_FILES_POST
= check-files-post-message
160 _CHECK_FILES_POST
+= ${_CHECK_FILES_POST.
prefix}
161 .if empty
(CHECK_FILES_STRICT
:M
[nN
][oO
])
162 _CHECK_FILES_POST
+= ${_CHECK_FILES_POST.sysconfdir
}
163 _CHECK_FILES_POST
+= ${_CHECK_FILES_POST.varbase
}
166 .if empty
(CHECK_FILES
:M
[nN
][oO
])
167 privileged-install-hook
: check-files
170 ###########################################################################
171 # check-files-pre and check-files-post targets and subtargets
173 .PHONY
: check-files-pre check-files-post
174 check-files-pre
: ${_CHECK_FILES_PRE}
175 check-files-post
: ${_CHECK_FILES_POST}
177 .PHONY
: check-files-pre-message check-files-post-message
178 check-files-pre-message
:
179 @
${STEP_MSG} "Generating pre-install file lists"
181 check-files-post-message
:
182 @
${STEP_MSG} "Generating post-install file lists"
184 ${_CHECK_FILES_PRE.
prefix} ${_CHECK_FILES_POST.
prefix}:
186 ${FIND} ${DESTDIR}${PREFIX}/. \
( -type f
-o
-type l \
) -print 2>/dev
/null \
187 |
${SED} -e
's,/\./,/,' \
188 |
${_CHECK_FILES_SKIP_FILTER} \
189 |
${SORT} > ${.TARGET
} \
192 ${_CHECK_FILES_PRE.sysconfdir
} ${_CHECK_FILES_POST.sysconfdir
}:
194 ${FIND} ${DESTDIR}${PKG_SYSCONFDIR}/.
-print 2>/dev
/null \
195 |
${SED} -e
's,/\./,/,' \
196 |
${_CHECK_FILES_SKIP_FILTER} \
197 |
${SORT} > ${.TARGET
} \
200 ${_CHECK_FILES_PRE.varbase
} ${_CHECK_FILES_POST.varbase
}:
202 ${FIND} ${DESTDIR}${VARBASE}/.
-print 2>/dev
/null \
203 |
${SED} -e
's,/\./,/,' \
204 |
${_CHECK_FILES_SKIP_FILTER} \
205 |
${SORT} > ${.TARGET
} \
208 ###########################################################################
209 # check-files targets and subtargets
211 .PHONY
: check-files-prefix check-files-sysconfdir check-files-varbase
212 check-files-prefix
: ${_CHECK_FILES_ERRMSG.
prefix}
213 check-files-sysconfdir
: ${_CHECK_FILES_ERRMSG.sysconfdir
}
214 check-files-varbase
: ${_CHECK_FILES_ERRMSG.varbase
}
216 # The check-files target looks at the cookie files generated by the
217 # check-files-* subtargets, and if they are non-empty, then they
218 # contain the error messages collected during the build of each
222 .if
!empty
(CHECK_FILES_SUPPORTED
:M
[nN
][oO
])
226 check-files
: check-files-message
${_CHECK_FILES_ERRMSGS} error-check
229 .PHONY
: check-files-message
231 @
${STEP_MSG} "Checking file-check results for ${PKGNAME}"
233 # Check ${PREFIX} for files which are not listed in the generated ${PLIST}
236 _CHECK_FILES_DIFF
= ${WRKDIR}/.check_files_diff
237 _CHECK_FILES_ADDED
= ${WRKDIR}/.check_files_added
238 _CHECK_FILES_DELETED
= ${WRKDIR}/.check_files_deleted
239 _CHECK_FILES_EXPECTED
= ${WRKDIR}/.check_files_expected
240 _CHECK_FILES_MISSING
= ${WRKDIR}/.check_files_missing
241 _CHECK_FILES_MISSING_SKIP
= ${WRKDIR}/.check_files_missing_skip
242 _CHECK_FILES_MISSING_REAL
= ${WRKDIR}/.check_files_missing_real
243 _CHECK_FILES_EXTRA
= ${WRKDIR}/.check_files_extra
245 ${_CHECK_FILES_DIFF}: ${_CHECK_FILES_PRE.
prefix} ${_CHECK_FILES_POST.
prefix}
247 ${DIFF} -u
${_CHECK_FILES_PRE.
prefix} \
248 ${_CHECK_FILES_POST.
prefix} \
249 > ${.TARGET
} ||
${TRUE}
251 ${_CHECK_FILES_ADDED}: ${_CHECK_FILES_DIFF}
253 ${GREP} '^+/' ${_CHECK_FILES_DIFF} |
${SED} "s|^+||" |
${SORT} \
256 ${_CHECK_FILES_DELETED}: ${_CHECK_FILES_DIFF}
258 ${GREP} '^-/' ${_CHECK_FILES_DIFF} |
${SED} "s|^-||" |
${SORT} \
261 ${_CHECK_FILES_EXPECTED}: plist
263 ${GREP} '^[^@]' ${PLIST} |
${SED} "s|^|${DESTDIR}${PREFIX}/|" |
${SORT} \
266 ${_CHECK_FILES_MISSING}: ${_CHECK_FILES_EXPECTED} ${_CHECK_FILES_ADDED}
268 ${DIFF} -u
${_CHECK_FILES_EXPECTED} ${_CHECK_FILES_ADDED} | \
269 ${GREP} '^-[^-]' |
${SED} "s|^-||" | \
270 while read file
; do \
271 ${TEST} -f
"$$file" -o
-h
"$$file" ||
${ECHO} "$$file"; \
274 ${_CHECK_FILES_MISSING_REAL}: ${_CHECK_FILES_MISSING}
276 ${CAT} ${_CHECK_FILES_MISSING} |
${_CHECK_FILES_SKIP_FILTER} \
277 > ${.TARGET
} ||
${TRUE}
279 ${_CHECK_FILES_MISSING_SKIP}: \
280 ${_CHECK_FILES_MISSING} \
281 ${_CHECK_FILES_MISSING_REAL}
283 ${DIFF} -u
${_CHECK_FILES_MISSING} \
284 ${_CHECK_FILES_MISSING_REAL} | \
285 ${GREP} '^-[^-]' |
${SED} "s|^-||" \
288 ${_CHECK_FILES_EXTRA}: ${_CHECK_FILES_EXPECTED} ${_CHECK_FILES_ADDED}
290 ${DIFF} -u
${_CHECK_FILES_EXPECTED} ${_CHECK_FILES_ADDED} | \
291 ${GREP} '^+[^+]' |
${SED} "s|^+||" | \
292 while read file
; do \
293 ${TEST} ! -f
"$$file" -a
! -h
"$$file" ||
${ECHO} "$$file"; \
296 ${_CHECK_FILES_ERRMSG.
prefix}: \
297 ${_CHECK_FILES_DELETED} \
298 ${_CHECK_FILES_MISSING} \
299 ${_CHECK_FILES_MISSING_REAL} \
300 ${_CHECK_FILES_MISSING_SKIP} \
301 ${_CHECK_FILES_EXTRA}
302 ${RUN}${RM} -f
${.TARGET
}
304 if
${_NONZERO_FILESIZE_P} ${_CHECK_FILES_DELETED}; then \
305 ${ECHO} "The following files have been deleted" \
307 ${SED} "s|^| |" ${_CHECK_FILES_DELETED}; \
310 if
${_NONZERO_FILESIZE_P} ${_CHECK_FILES_MISSING_REAL}; then \
311 ${ECHO} "************************************************************"; \
312 ${ECHO} "The following files are in the" \
313 "PLIST but not in ${DESTDIR}${PREFIX}:"; \
314 ${SED} "s|^| |" ${_CHECK_FILES_MISSING_REAL}; \
317 if
${_NONZERO_FILESIZE_P} ${_CHECK_FILES_EXTRA}; then \
318 ${ECHO} "************************************************************"; \
319 ${ECHO} "The following files are in" \
320 "${DESTDIR}${PREFIX} but not in the PLIST:"; \
321 ${SED} "s|^| |" ${_CHECK_FILES_EXTRA}; \
324 if
${_NONZERO_FILESIZE_P} ${_CHECK_FILES_MISSING_SKIP}; then \
325 ${ECHO} "************************************************************"; \
326 ${ECHO} "The following files are in both the" \
327 "PLIST and CHECK_FILES_SKIP:"; \
328 ${SED} "s|^| |" ${_CHECK_FILES_MISSING_SKIP}; \
331 # Check ${SYSCONFDIR} for files which are not in the PLIST and are also
332 # not copied into place by the INSTALL scripts.
334 ${_CHECK_FILES_ERRMSG.sysconfdir
}: \
335 ${_CHECK_FILES_PRE.sysconfdir
} \
336 ${_CHECK_FILES_POST.sysconfdir
}
338 if
${CMP} -s
${_CHECK_FILES_PRE.sysconfdir
} \
339 ${_CHECK_FILES_POST.sysconfdir
}; then \
342 ${ECHO} "************************************************************"; \
343 ${ECHO} "The package has modified ${PKG_SYSCONFDIR}" \
344 "contents directly!"; \
345 ${ECHO} " The offending files/directories are:"; \
346 ${DIFF} -u
${_CHECK_FILES_PRE.sysconfdir
} \
347 ${_CHECK_FILES_POST.sysconfdir
} | \
348 ${GREP} '^+[^+]' |
${SED} "s|^+| |"; \
351 # Check ${VARBASE} for files which are not in the PLIST and are also
352 # not created by the INSTALL scripts.
354 ${_CHECK_FILES_ERRMSG.varbase
}: \
355 ${_CHECK_FILES_PRE.varbase
} \
356 ${_CHECK_FILES_POST.varbase
}
358 if
${CMP} -s
${_CHECK_FILES_PRE.varbase
} \
359 ${_CHECK_FILES_POST.varbase
}; then \
362 ${ECHO} "************************************************************"; \
363 ${ECHO} "The package has modified ${VARBASE}" \
364 "contents directly!"; \
365 ${ECHO} " The offending files/directories are:"; \
366 ${DIFF} -u
${_CHECK_FILES_PRE.varbase
} \
367 ${_CHECK_FILES_POST.varbase
} | \
368 ${GREP} '^+[^+]' |
${SED} "s|^+| |"; \
371 ###########################################################################
372 # check-files-clean removes the state files related to the "check-files"
373 # target so that the check-files-{pre,post} targets may be re-run.
375 .PHONY
: check-files-clean
376 check-clean
: check-files-clean
379 ${RM} -f
${_CHECK_FILES_ERRMSGS} \
380 ${_CHECK_FILES_PRE} ${_CHECK_FILES_POST} \
381 ${_CHECK_FILES_DIFF} ${_CHECK_FILES_ADDED} \
382 ${_CHECK_FILES_DELETED} ${_CHECK_FILES_EXPECTED} \
383 ${_CHECK_FILES_MISSING} ${_CHECK_FILES_MISSING_SKIP} \
384 ${_CHECK_FILES_MISSING_REAL} ${_CHECK_FILES_EXTRA}