11.1Sagc#! /bin/sh 21.1Sagc# 31.26Suki# $NetBSD: regpkg,v 1.26 2023/02/11 04:16:57 uki Exp $ 41.1Sagc# 51.17Sagc# Copyright (c) 2003,2009 The NetBSD Foundation, Inc. 61.17Sagc# All rights reserved. 71.17Sagc# 81.17Sagc# This code is derived from software contributed to The NetBSD Foundation 91.17Sagc# by Alistair Crooks (agc@NetBSD.org) 101.1Sagc# 111.1Sagc# Redistribution and use in source and binary forms, with or without 121.1Sagc# modification, are permitted provided that the following conditions 131.1Sagc# are met: 141.1Sagc# 1. Redistributions of source code must retain the above copyright 151.1Sagc# notice, this list of conditions and the following disclaimer. 161.1Sagc# 2. Redistributions in binary form must reproduce the above copyright 171.1Sagc# notice, this list of conditions and the following disclaimer in the 181.1Sagc# documentation and/or other materials provided with the distribution. 191.17Sagc# 201.17Sagc# THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 211.17Sagc# ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 221.17Sagc# TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 231.17Sagc# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 241.17Sagc# BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 251.17Sagc# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 261.17Sagc# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 271.17Sagc# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 281.17Sagc# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 291.17Sagc# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 301.17Sagc# POSSIBILITY OF SUCH DAMAGE. 311.1Sagc# 321.1Sagc 331.9Sapb# Usage: regpkg [options] set pkgname 341.9Sapb# 351.9Sapb# Registers a syspkg in the database directory, 361.9Sapb# and optionally creates a binary package. 371.9Sapb# 381.9Sapb# Options: 391.9Sapb# -q Quiet. 401.9Sapb# -v Verbose. 411.9Sapb# -f Force. 421.9Sapb# -m Ignore errors from missing files. 431.9Sapb# -u Update. 441.9Sapb# -c Use cached information from ${BUILD_INFO_CACHE}. 451.9Sapb# -d destdir Sets DESTDIR. 461.9Sapb# -t binpkgdir Create a binary package (in *.tgz format) in the 471.9Sapb# specified directory. Without this option, a binary 481.9Sapb# package is not created. 491.9Sapb# -M metalog Use the specified metalog file to override file 501.9Sapb# or directory attributes when creating a binary package. 511.9Sapb# -N etcdir Use the specified directory for passwd and group files. 521.9Sapb# 531.9Sapb# When -f is set: If the desired syspkg already exists, it is overwritten. 541.9Sapb# When -u is set: If the desired syspkg already exists, it might be 551.9Sapb# overwritten or left alone, depending on whether it's older 561.9Sapb# or newer than the files that belong to the syspkg. 571.9Sapb# When neither -u nor -f are set: It's an error for the desired syspkg 581.9Sapb# to already exist. 591.1Sagc 601.9Sapbprog="${0##*/}" 611.9Sapbtoppid=$$ 621.8Sapbrundir="$(dirname "$0")" # ${0%/*} isn't good enough when there's no "/" 631.9Sapb. "${rundir}/sets.subr" 641.9Sapb 651.9Sapbbomb() 661.9Sapb{ 671.9Sapb #echo "${prog}: bomb: start, toppid=${toppid} \$\$=$$" 681.9Sapb kill ${toppid} # in case we were invoked from a subshell 691.9Sapb #echo "${prog}: bomb: killed ${toppid}" 701.9Sapb exit 1 711.9Sapb} 721.6Serh 731.9Sapb# A literal newline 741.9Sapbnl=' 751.9Sapb' 761.9Sapb# A literal tab 771.9Sapbtab=' ' 781.9Sapb 791.9Sapb# Prefixes for error messages, warnings, and important informational 801.9Sapb# messages. 811.9SapbERROR="${prog}: ERROR: " 821.9SapbWARNING="${prog}: WARNING: " 831.9SapbNOTE="${prog}: NOTE: " 841.9SapbERRWARN="${ERROR}" # may be changed by "-f" (force) command line flag 851.9SapbERRWARNNOTE="${ERROR}" # may be changed by "-u" (update) command line flag 861.1Sagc 871.9Sapb# 881.9Sapb# All temporary files will go in ${SCRATCH}, which will be deleted on 891.9Sapb# exit. 901.9Sapb# 911.14SapbSCRATCH="$(${MKTEMP} -d "/var/tmp/${0##*/}.XXXXXX")" 921.9Sapbif [ $? -ne 0 -o \! -d "${SCRATCH}" ]; then 931.10Sapb echo >&2 "${prog}: Could not create scratch directory." 941.9Sapb bomb 951.1Sagcfi 961.1Sagc 971.9Sapb# 981.9Sapb# cleanup() always deletes the SCRATCH directory, and might also 991.9Sapb# delete other files or directories. 1001.9Sapb# 1011.9Sapbes=0 1021.9Sapbcleanup_must_delete_binpkgfile=false 1031.9Sapbcleanup_must_delete_dbsubdir=false 1041.14Sapbcleanup() 1051.9Sapb{ 1061.9Sapb trap - 0 1071.9Sapb #echo "${prog}: cleanup start" 1081.9Sapb if ${cleanup_must_delete_binpkgfile:-false} && [ -e "${binpkgfile}" ] 1091.9Sapb then 1101.9Sapb echo >&2 "${prog}: deleting partially-created ${binpkgfile}" 1111.9Sapb rm -f "${binpkgfile}" 1121.9Sapb fi 1131.9Sapb if ${cleanup_must_delete_dbsubdir:-false} \ 1141.9Sapb && [ -e "${SYSPKG_DB_SUBDIR}" ] 1151.9Sapb then 1161.9Sapb echo >&2 "${prog}: deleting partially-created ${SYSPKG_DB_SUBDIR}" 1171.9Sapb rm -rf "${SYSPKG_DB_SUBDIR}" 1181.9Sapb fi 1191.9Sapb rm -rf "${SCRATCH}" 1201.9Sapb #echo "${prog}: cleanup done, exit ${es}" 1211.9Sapb exit ${es} 1221.9Sapb} 1231.9Sapbtrap 'es=128; cleanup' 1 2 3 13 15 # HUP INT QUIT PIPE TERM 1241.9Sapbtrap 'es=$?; cleanup' 0 # EXIT 1251.9Sapb 1261.9Sapb# 1271.9Sapb# Parse command line args. 1281.9Sapb# 1291.9Sapbverbose=false 1301.9Sapbverbosity=0 1311.9Sapbquiet=false 1321.9Sapbforce=false 1331.9Sapbupdate=false 1341.9Sapballowmissing=false 1351.9SapbDESTDIR="${DESTDIR}" 1361.9Sapbbinpkgdir="" 1371.9Sapbmetalog="" 1381.9Sapbetcdir="" 1391.9SapbSYSPKG_DB_TOPDIR="" 1401.9Sapbpkgset="" 1411.9Sapbpkg="" 1421.14Sapbparse_args() 1431.9Sapb{ 1441.9Sapb while [ $# -gt 2 ]; do 1451.9Sapb case "$1" in 1461.14Sapb -q) quiet=true; verbose=false ;; 1471.14Sapb -v) verbose=true; quiet=false 1481.9Sapb verbosity=$(( ${verbosity} + 1 )) 1491.9Sapb ;; 1501.9Sapb -f) force=true ;; 1511.9Sapb -u) update=true ;; 1521.9Sapb -m) allowmissing=true ;; 1531.9Sapb -c) # The -c option is ignored. The BUILD_INFO_CACHE 1541.9Sapb # environment variable is used instead. 1551.9Sapb ;; 1561.14Sapb -d) DESTDIR="$2"; shift ;; 1571.9Sapb -d*) DESTDIR="${1#-?}" ;; 1581.14Sapb -t) binpkgdir="$2"; shift ;; 1591.9Sapb -t*) binpkgdir="${1#-?}" ;; 1601.14Sapb -M) metalog="$2"; shift ;; 1611.9Sapb -M*) metalog="${1#-?}" ;; 1621.14Sapb -N) etcdir="$2"; shift ;; 1631.9Sapb -N*) etcdir="${1#-?}" ;; 1641.9Sapb *) break ;; 1651.9Sapb esac 1661.9Sapb shift 1671.9Sapb done 1681.9Sapb if ${force}; then 1691.9Sapb ERRWARN="${WARNING}" 1701.9Sapb else 1711.9Sapb ERRWARN="${ERROR}" 1721.9Sapb fi 1731.9Sapb if ${update}; then 1741.9Sapb ERRWARNNOTE="${NOTE}" 1751.9Sapb else 1761.9Sapb ERRWARNNOTE="${ERRWARN}" 1771.9Sapb fi 1781.9Sapb DESTDIR="${DESTDIR%/}" # delete trailing "/" if any 1791.9Sapb if [ \! -n "${etcdir}" ]; then 1801.9Sapb etcdir="${DESTDIR}/etc" 1811.9Sapb fi 1821.9Sapb if [ -n "${binpkgdir}" -a \! -d "${binpkgdir}" ]; then 1831.9Sapb echo >&2 "${ERROR}binary pkg directory ${binpkgdir} does not exist" 1841.9Sapb bomb 1851.9Sapb fi 1861.9Sapb # 1871.9Sapb # SYSPKG_DB_TOPDIR is the top level directory for registering 1881.9Sapb # syspkgs. It defaults to ${DESTDIR}/var/db/syspkg, but can be 1891.9Sapb # overridden by environment variables SYSPKG_DBDIR or PKG_DBDIR. 1901.9Sapb # 1911.9Sapb # Note that this corresponds to the default value of PKG_DBDIR 1921.9Sapb # set in .../distrib/syspkg/mk/bsd.syspkg.mk. 1931.9Sapb # 1941.9Sapb SYSPKG_DB_TOPDIR="${SYSPKG_DBDIR:-${PKG_DBDIR:-${DESTDIR}/var/db/syspkg}}" 1951.9Sapb 1961.9Sapb if [ $# -ne 2 ]; then 1971.9Sapb echo "Usage: regpkg [options] set pkgname" 1981.9Sapb bomb 1991.9Sapb fi 2001.9Sapb 2011.9Sapb pkgset="$1" 2021.9Sapb pkg="$2" 2031.9Sapb} 2041.1Sagc 2051.9Sapb# 2061.9Sapb# make_PLIST() creates a skeleton PLIST from the pkgset description. 2071.9Sapb# 2081.9Sapb# The result is stored in the file ${PLIST}. 2091.9Sapb# 2101.9SapbPLIST="${SCRATCH}/PLIST" 2111.14Sapbmake_PLIST() 2121.9Sapb{ 2131.14Sapb if ${verbose}; then 2141.9Sapb echo "Making PLIST for \"${pkg}\" package (part of ${pkgset} set)" 2151.9Sapb fi 2161.9Sapb prefix="${DESTDIR:-/}" 2171.9Sapb realprefix=/ 2181.9Sapb ${HOST_SH} "${rundir}/makeplist" -p "${prefix}" -I "${realprefix}" \ 2191.9Sapb "${pkgset}" "${pkg}" \ 2201.9Sapb >"${PLIST}" 2>"${SCRATCH}/makeplist-errors" 2211.14Sapb if ${EGREP} -v '^DEBUG:' "${SCRATCH}/makeplist-errors"; then 2221.9Sapb # "find" invoked from makeplist sometimes reports 2231.9Sapb # errors about missing files or directories, and 2241.9Sapb # makeplist ignores the errors. Catch them here. 2251.9Sapb echo >&2 "${ERROR}makeplist reported errors for ${pkg}:" 2261.9Sapb cat >&2 "${SCRATCH}/makeplist-errors" 2271.9Sapb echo >&2 "${ERROR}see above for errors from makeplist" 2281.9Sapb if ${allowmissing}; then 2291.9Sapb echo >&2 "${prog}: ${NOTE}: ignoring above errors, due to '-m' option." 2301.9Sapb else 2311.9Sapb ${force} || bomb 2321.9Sapb fi 2331.9Sapb fi 2341.9Sapb} 2351.1Sagc 2361.9Sapb# 2371.9Sapb# init_allfiles() converts the PLIST (which contains relative filenames) 2381.9Sapb# into a list of absolute filenames. Directories are excluded from the 2391.9Sapb# result. 2401.9Sapb# 2411.9Sapb# The result is stored in the variable ${allfiles}. 2421.9Sapb# 2431.9Sapballfiles='' 2441.14Sapbinit_allfiles() 2451.9Sapb{ 2461.9Sapb [ -f "${PLIST}" ] || make_PLIST 2471.14Sapb allfiles="$(${AWK} ' 2481.9Sapb BEGIN { destdir = "'"${DESTDIR%/}"'" } 2491.9Sapb /^@cwd/ { prefix = $2; next } 2501.25Suki /^@pkgdir/ { next } 2511.14Sapb { printf("%s%s%s\n", destdir, prefix, $0) }' "${PLIST}")" 2521.9Sapb} 2531.1Sagc 2541.9Sapb# 2551.9Sapb# init_newestfile() finds the newest file (most recent mtime). 2561.9Sapb# 2571.9Sapb# The result is stored in the variable ${newestfile}. 2581.9Sapb# 2591.9Sapbnewestfile='' 2601.14Sapbinit_newestfile() 2611.9Sapb{ 2621.9Sapb [ -s "${allfiles}" ] || init_allfiles 2631.9Sapb # We assume no shell special characters in ${allfiles}, 2641.9Sapb # and spaces only between file names, not inside file names. 2651.9Sapb # This should be safe, because it has no no user-specified parts. 2661.14Sapb newestfile="$(${LS} -1dt ${allfiles} | ${SED} '1q')" 2671.9Sapb} 2681.1Sagc 2691.9Sapb# 2701.9Sapb# Various ways of getting parts of the syspkg version number: 2711.9Sapb# 2721.9Sapb# get_osvers() - get the OS version number from osrelease.sh or $(uname -r), 2731.9Sapb# return it in ${osvers}, and set ${method}. 2741.9Sapb# get_tinyvers() - get the tiny version number from the "versions" file, 2751.9Sapb# and return it in ${tinyvers}. Does not set ${method}. 2761.9Sapb# get_newest_rcsid_date() - get the newest RCS date, 2771.9Sapb# and return it in ${newest}. Does not set ${method}. 2781.9Sapb# get_newest_mtime_date() - get the newest file modification date, 2791.9Sapb# and return it in ${newest}. Does not set ${method}. 2801.9Sapb# get_newest_date() - get date from rcsid or mtime, return it in ${newest}, 2811.9Sapb# and set ${method}. 2821.9Sapb# 2831.14Sapbget_osvers() 2841.9Sapb{ 2851.3Sagc if [ -f ../../sys/conf/osrelease.sh ]; then 2861.8Sapb osvers="$(${HOST_SH} ../../sys/conf/osrelease.sh)" 2871.4Sdyoung method=osreleases 2881.3Sagc else 2891.8Sapb osvers="$(${UNAME} -r)" 2901.3Sagc method=uname 2911.3Sagc fi 2921.9Sapb #echo "${osvers}" 2931.9Sapb} 2941.14Sapbget_tinyvers() 2951.9Sapb{ 2961.14Sapb tinyvers="$(${AWK} '$1 ~ '/"${pkg}"/' { print $2 }' \ 2971.14Sapb "${rundir}/versions")" 2981.9Sapb case "${tinyvers}" in 2991.9Sapb "") tinyvers=0 3001.9Sapb ;; 3011.9Sapb esac 3021.9Sapb #echo "${tinyvers}" 3031.9Sapb} 3041.9Sapbget_newest_rcsid_date() 3051.9Sapb{ 3061.9Sapb [ -s "${allfiles}" ] || init_allfiles 3071.9Sapb 3081.9Sapb # Old RCS identifiers might have 2-digit years, so we match both 3091.9Sapb # YY/MM/DD and YYYY/MM/DD. We also try to deal with the Y10K 3101.9Sapb # problem by allowing >4 digit years. 3111.9Sapb newest=0 3121.9Sapb case "${allfiles}" in 3131.3Sagc "") ;; 3141.14Sapb *) newest="$(${IDENT} ${allfiles} 2>/dev/null | ${AWK} ' 3151.3Sagc BEGIN { last = 0 } 3161.3Sagc $2 == "crt0.c,v" { next } 3171.9Sapb NF == 8 && \ 3181.9Sapb $4 ~ /^[0-9][0-9]\/[0-9][0-9]\/[0-9][0-9]$/ \ 3191.9Sapb { t = "19" $4; gsub("/", "", t); 3201.9Sapb if (t > last) last = t; } 3211.9Sapb NF == 8 && \ 3221.9Sapb $4 ~ /^[0-9][0-9][0-9][0-9][0-9]*\/[0-9][0-9]\/[0-9][0-9]$/ \ 3231.9Sapb { t = $4; gsub("/", "", t); 3241.9Sapb if (t > last) last = t; } 3251.14Sapb END { print last }')" 3261.3Sagc method=ident 3271.3Sagc ;; 3281.3Sagc esac 3291.9Sapb #echo "${newest}" 3301.9Sapb} 3311.14Sapbget_newest_mtime_date() 3321.9Sapb{ 3331.9Sapb [ -s "${newestfile}" ] || init_newestfile 3341.9Sapb 3351.9Sapb # We could simplify the awk program to take advantage of the 3361.9Sapb # fact thet it should have exactly one line of input. 3371.14Sapb newest="$(${ENV_CMD} TZ=UTC LOCALE=C ${LS} -lT "${newestfile}" \ 3381.9Sapb | ${AWK} ' 3391.9Sapb BEGIN { newest = 0 } 3401.9Sapb { 3411.9Sapb t = $9 ""; 3421.9Sapb if ($6 == "Jan") t = t "01"; 3431.9Sapb if ($6 == "Feb") t = t "02"; 3441.9Sapb if ($6 == "Mar") t = t "03"; 3451.9Sapb if ($6 == "Apr") t = t "04"; 3461.9Sapb if ($6 == "May") t = t "05"; 3471.9Sapb if ($6 == "Jun") t = t "06"; 3481.9Sapb if ($6 == "Jul") t = t "07"; 3491.9Sapb if ($6 == "Aug") t = t "08"; 3501.9Sapb if ($6 == "Sep") t = t "09"; 3511.9Sapb if ($6 == "Oct") t = t "10"; 3521.9Sapb if ($6 == "Nov") t = t "11"; 3531.9Sapb if ($6 == "Dec") t = t "12"; 3541.9Sapb if ($7 < 10) t = t "0"; 3551.9Sapb t = t $7; 3561.9Sapb #these next two lines add the 24h clock onto the date 3571.9Sapb #gsub(":", "", $8); 3581.9Sapb #t = sprintf("%s.%4.4s", t, $8); 3591.9Sapb if (t > newest) newest = t; 3601.9Sapb } 3611.14Sapb END { print newest }')" 3621.9Sapb #echo "${newest}" 3631.9Sapb} 3641.14Sapbget_newest_date() 3651.9Sapb{ 3661.9Sapb get_newest_rcsid_date 3671.9Sapb case "${newest}" in 3681.9Sapb ""|0) get_newest_mtime_date 3691.3Sagc method=ls 3701.3Sagc ;; 3711.9Sapb *) method=rcsid 3721.9Sapb ;; 3731.3Sagc esac 3741.9Sapb #echo "${newest}" 3751.9Sapb} 3761.9Sapb 3771.9Sapb# 3781.9Sapb# choose_version_number() chooses the syspkg version number, 3791.9Sapb# by concatenating several components (OS version, syspkg "tiny" 3801.9Sapb# version and date). We end up with something like 3811.9Sapb# osvers="3.99.15", tinyvers="0", newest="20060104", 3821.9Sapb# and t="3.99.15.0.20060104". 3831.9Sapb# 3841.9Sapb# The result is stored in the variables ${t} and ${method}. 3851.9Sapb# 3861.9Sapbmethod='' 3871.9Sapbt='' 3881.14Sapbchoose_version_number() 3891.9Sapb{ 3901.14Sapb get_osvers; m1="${method}" 3911.9Sapb get_tinyvers # does not set ${method} 3921.14Sapb get_newest_date; m2="${method}" 3931.9Sapb t="${osvers}.${tinyvers}.${newest}" 3941.9Sapb method="${m1}.${m2}" 3951.9Sapb 3961.9Sapb # print version number that we're using 3971.9Sapb if ${verbose}; then 3981.9Sapb echo "${pkg} - ${t} version using ${method} method" 3991.9Sapb fi 4001.9Sapb} 4011.9Sapb 4021.9Sapb# 4031.13Sapb# init_db_opts() sets the dbfile, dbtype and db_opts variables, 4041.13Sapb# used for accessing the pkgdb.byfile.db database. 4051.13Sapb# 4061.14Sapbinit_db_opts() 4071.13Sapb{ 4081.13Sapb dbfile="${SYSPKG_DB_TOPDIR}/pkgdb.byfile.db" 4091.13Sapb dbtype="btree" 4101.13Sapb db_opts='' 4111.14Sapb : ${TARGET_ENDIANNESS:="$(arch_to_endian "${MACHINE_ARCH}")"} 4121.13Sapb case "${TARGET_ENDIANNESS}" in 4131.13Sapb 4321) db_opts="${db_opts} -E B" # big-endian 4141.13Sapb ;; 4151.13Sapb 1234) db_opts="${db_opts} -E L" # little-endian 4161.13Sapb ;; 4171.13Sapb *) 4181.13Sapb echo >&2 "${WARNING}Unknown or unsupported target endianness" 4191.13Sapb echo >&2 "${NOTE}Using host endianness" 4201.13Sapb ;; 4211.13Sapb esac 4221.14Sapb if ${update} || ${force}; then 4231.13Sapb # overwriting an existing entry is not an error 4241.13Sapb db_opts="${db_opts} -R" 4251.13Sapb fi 4261.13Sapb if [ ${verbosity} -lt 2 ]; then 4271.13Sapb # don't print all the keys added to the database 4281.13Sapb db_opts="${db_opts} -q" 4291.13Sapb fi 4301.13Sapb} 4311.13Sapb 4321.13Sapb# 4331.9Sapb# print_dir_exec_lines outputs an "@exec install" line for each 4341.9Sapb# directory in ${PLIST} 4351.9Sapb# 4361.14Sapbprint_dir_exec_lines() 4371.9Sapb{ 4381.9Sapb local dir uname gname mode 4391.9Sapb local dot_slash_dir 4401.9Sapb local no_dot_dir 4411.9Sapb local word line 4421.25Suki ${AWK} '/^@pkgdir/ { print $2 }' <"${PLIST}" | \ 4431.9Sapb ${SORT} | \ 4441.14Sapb while read dir; do 4451.9Sapb # Sanitise the name. ${dir} could be an absolute or 4461.9Sapb # relative name, with or without a leading "./". 4471.9Sapb # ${dot_slash_dir} always has a leading "./" (except when 4481.9Sapb # it's exactly equal to "."). ${no_dot_dir} never has a 4491.9Sapb # leading "." or "/" (except when it's exactly equal to 4501.9Sapb # "."). 4511.9Sapb case "${dir}" in 4521.9Sapb .|./|/) dot_slash_dir=. ;; 4531.9Sapb ./*) dot_slash_dir="${dir}" ;; 4541.9Sapb /*) dot_slash_dir=".${dir}" ;; 4551.9Sapb *) dot_slash_dir="./${dir}" ;; 4561.9Sapb esac 4571.9Sapb no_dot_dir="${dot_slash_dir#./}" 4581.9Sapb # Get the directory's owner, group, and mode 4591.9Sapb # from the live file system, or let it be overridden 4601.9Sapb # by the metalog. 4611.14Sapb eval "$(${STAT} -f 'uname=%Su gname=%Sg mode=%#OLp' \ 4621.14Sapb "${DESTDIR}/${dot_slash_dir}")" 4631.9Sapb if [ -n "${metalog}" ]; then 4641.14Sapb line="$(echo "${dot_slash_dir}" | \ 4651.9Sapb ${AWK} -f "${rundir}/join.awk" \ 4661.14Sapb /dev/stdin "${metalog}")" 4671.14Sapb for word in ${line}; do 4681.9Sapb case "${word}" in 4691.9Sapb uname=*|gname=*|mode=*) eval "${word}" ;; 4701.9Sapb esac 4711.9Sapb done 4721.9Sapb fi 4731.9Sapb # XXX: Work around yet another pkg_add bug: @cwd lines 4741.9Sapb # do not actually cause the working directory to change, 4751.9Sapb # so file names in @exec lines need to be qualified by 4761.9Sapb # %D, which (in our case, since we know there's an 4771.9Sapb # "@cwd /" line) will be the dir name passed to 4781.9Sapb # "pkg_add -p PREFIX". 4791.9Sapb case "${no_dot_dir}" in 4801.9Sapb .) d="%D" ;; 4811.9Sapb *) d="%D/${no_dot_dir}" ;; 4821.9Sapb esac 4831.9Sapb cat <<EOF 4841.9Sapb@exec install -d -o ${uname} -g ${gname} -m ${mode} ${d} 4851.9SapbEOF 4861.9Sapb done 4871.9Sapb} 4881.2Sjwise 4891.9Sapb# 4901.9Sapb# register_syspkg() registers the syspkg in ${SYSPKG_DB_TOPDIR}. 4911.9Sapb# This involves creating the subdirectory ${SYSPKG_DB_SUBDIR} 4921.9Sapb# and populating it with several files. 4931.9Sapb# 4941.14Sapbregister_syspkg() 4951.9Sapb{ 4961.9Sapb cleanup_must_delete_dbsubdir=true 4971.9Sapb [ -n "${SYSPKG_DB_SUBDIR}" ] || bomb 4981.9Sapb mkdir -p "${SYSPKG_DB_SUBDIR}" 4991.9Sapb 5001.9Sapb # 5011.9Sapb # Guess what versions of other packages to depend on. 5021.9Sapb # 5031.9Sapb # If we are using the OS version as part of the pkg 5041.9Sapb # version, then depend on any version ">=${osvers}". For 5051.9Sapb # example, etc-sys-etc-1.6ZI.0.20040206 might depend on 5061.9Sapb # base-sys-root>=1.6ZI. 5071.9Sapb # 5081.9Sapb # Failing that, depend on any version "-[0-9]*". 5091.9Sapb # 5101.9Sapb # XXX: We could extend the format of the "deps" file to carry 5111.9Sapb # this sort of information, so we wouldn't have to guess. 5121.9Sapb # 5131.9Sapb case "${t}" in 5141.9Sapb ${osvers}.*) depversion=">=${osvers}" ;; 5151.9Sapb *) depversion="-[0-9]*" ;; 5161.9Sapb esac 5171.9Sapb 5181.9Sapb # 5191.9Sapb # Add the dependencies. 5201.9Sapb # 5211.9Sapb # We always add a "@pkgdep" line for each prerequisite package. 5221.9Sapb # 5231.9Sapb # If the prerequisite pkg is already registered (as it should be 5241.9Sapb # if our caller is doing things in the right order), then we put 5251.9Sapb # its exact version number in a "@blddep" line. 5261.9Sapb # 5271.9Sapb ${AWK} '$1 ~ '/"${pkg}"/' { print $2 }' "${rundir}/deps" | ${SORT} | \ 5281.14Sapb while read depname; do 5291.9Sapb # ${pkgdepglob} is a shell glob pattern that should match 5301.9Sapb # any version of a pkg. ${pkgdep} uses the special syntax 5311.9Sapb # for pkg dependencies, and is not usable as a shell 5321.9Sapb # glob pattern. 5331.9Sapb pkgdepglob="${depname}-[0-9]*" 5341.9Sapb pkgdep="${depname}${depversion}" 5351.9Sapb echo "@pkgdep ${pkgdep}" 5361.14Sapb blddep="$(cd "${SYSPKG_DB_TOPDIR}" && echo ${pkgdepglob} \ 5371.14Sapb || bomb)" 5381.9Sapb case "${blddep}" in 5391.9Sapb *\*) # pkgdepglob did not match anything 5401.9Sapb echo >&2 "${WARNING}${pkg} depends on '${pkgdep}' but there is no matching syspkg in ${SYSPKG_DB_TOPDIR}" 5411.9Sapb ;; 5421.9Sapb *\ *) # pkgdepglob matched more than once. 5431.9Sapb echo >&2 "${ERRWARN}${pkg} depends on '${pkgdep}' but there are multiple matching syspkgs in ${SYSPKG_DB_TOPDIR}" 5441.9Sapb ${force} || bomb 5451.9Sapb # If ${force} is set, then assume that the last 5461.9Sapb # match is the most recent. 5471.9Sapb # XXX: This might be wrong, because of 5481.9Sapb # differences between lexical sorting and 5491.9Sapb # numeric sorting. 5501.9Sapb lastmatch="${blddep##* }" 5511.9Sapb echo "@blddep ${lastmatch}" 5521.9Sapb ;; 5531.9Sapb *) # exactly one match. 5541.9Sapb # XXX: We ignore the possibility that the 5551.9Sapb # version we found via ${pkgdepglob} might not 5561.9Sapb # satisfy ${pkgdep}. We could conceivably use 5571.9Sapb # "pkg_admin pmatch" to check, but that's not a 5581.9Sapb # host tool so we can't assume that it will be 5591.9Sapb # available. 5601.9Sapb echo "@blddep ${blddep}" 5611.9Sapb ;; 5621.9Sapb esac 5631.9Sapb done >>"${PLIST}" 5641.9Sapb 5651.9Sapb # create the comment (should be one line) 5661.14Sapb comment="$(${AWK} '$1 ~ '/"${pkg}"/' \ 5671.9Sapb { print substr($0, length($1) + 2) }' \ 5681.14Sapb "${rundir}/comments")" 5691.9Sapb case "${comment}" in 5701.9Sapb "") echo >&2 "${WARNING}no comment for \"${pkg}\" (using placeholder)" 5711.9Sapb comment="System package for ${pkg}" 5721.9Sapb ;; 5731.9Sapb *"${nl}"*) 5741.9Sapb echo >&2 "${ERRWARN}multi-line comment for \"${pkg}\"" 5751.9Sapb ${force} || bomb 5761.9Sapb ;; 5771.9Sapb esac 5781.9Sapb echo "${comment}" > "${SYSPKG_DB_SUBDIR}/+COMMENT" 5791.1Sagc 5801.9Sapb # create the description (could be multiple lines) 5811.14Sapb descr="$(${AWK} '$1 ~ '/"${pkg}"/' { 5821.9Sapb print substr($0, length($1) + 2) }' \ 5831.14Sapb "${rundir}/descrs")" 5841.9Sapb case "${descr}" in 5851.9Sapb "") echo >&2 "${WARNING}no description for \"${pkg}\" (re-using comment)" 2>&1 5861.9Sapb descr="${comment}" 5871.9Sapb ;; 5881.9Sapb esac 5891.9Sapb echo "${descr}" > "${SYSPKG_DB_SUBDIR}/+DESC" 5901.9Sapb ${PRINTF} "\nHomepage:\nhttp://www.NetBSD.org/\n" >> "${SYSPKG_DB_SUBDIR}/+DESC" 5911.1Sagc 5921.9Sapb # create the build information 5931.9Sapb if [ x"${BUILD_INFO_CACHE}" = x ]; then 5941.9Sapb { 5951.9Sapb # These variables describe the build 5961.9Sapb # environment, not the target. 5971.9Sapb echo "OPSYS=$(${UNAME} -s)" 5981.9Sapb echo "OS_VERSION=$(${UNAME} -r)" 5991.15Sapb ${MAKE} -B -f- all <<EOF 6001.4Sdyoung.include <bsd.own.mk> 6011.4Sdyoungall: 6021.4Sdyoung @echo OBJECT_FMT=${OBJECT_FMT} 6031.4Sdyoung @echo MACHINE_ARCH=${MACHINE_ARCH} 6041.4Sdyoung @echo MACHINE_GNU_ARCH=${MACHINE_GNU_ARCH} 6051.4SdyoungEOF 6061.9Sapb } > "${SYSPKG_DB_SUBDIR}/+BUILD_INFO" 6071.9Sapb else 6081.9Sapb cp "${BUILD_INFO_CACHE}" "${SYSPKG_DB_SUBDIR}/+BUILD_INFO" 6091.9Sapb fi 6101.9Sapb 6111.9Sapb # test for attributes 6121.9Sapb args="" 6131.14Sapb attrs="$(${AWK} '$1 ~ '/"${pkg}"/' { \ 6141.9Sapb print substr($0, length($1) + 2) }' \ 6151.14Sapb "${rundir}/attrs")" 6161.9Sapb for a in "${attrs}"; do 6171.9Sapb case "${attrs}" in 6181.9Sapb "") ;; 6191.9Sapb preserve) 6201.9Sapb echo "${pkg}-${t}" >"${SYSPKG_DB_SUBDIR}/+PRESERVE" 6211.9Sapb args="${args} -n ${SYSPKG_DB_SUBDIR}/+PRESERVE" 6221.9Sapb ;; 6231.9Sapb esac 6241.9Sapb done 6251.9Sapb 6261.9Sapb # 6271.9Sapb # Create ${SYSPKGSIR}/+CONTENTS from ${PLIST}, by adding an 6281.9Sapb # "@name" line and a lot of "@comment MD5:" lines. 6291.9Sapb # 6301.9Sapb { 6311.26Suki rcsid='$NetBSD: regpkg,v 1.26 2023/02/11 04:16:57 uki Exp $' 6321.14Sapb utcdate="$(${ENV_CMD} TZ=UTC LOCALE=C \ 6331.14Sapb ${DATE} '+%Y-%m-%d %H:%M')" 6341.9Sapb user="${USER:-root}" 6351.19Sapb host="$(${HOSTNAME_CMD})" 6361.9Sapb echo "@name ${pkg}-${t}" 6371.9Sapb echo "@comment Packaged at ${utcdate} UTC by ${user}@${host}" 6381.9Sapb echo "@comment Packaged using ${prog} ${rcsid}" 6391.9Sapb # XXX: "option extract-in-place" might help to get 6401.9Sapb # pkg_add to create directories. 6411.9Sapb # XXX: no, it doesn't work. Yet another pkg_add bug. 6421.9Sapb ## echo "@option extract-in-place" 6431.9Sapb # Move the @pkgdep and @blddep lines up, so that 6441.9Sapb # they are easy to see when people do "less 6451.9Sapb # ${DESTDIR}/var/db/syspkg/*/+CONTENTS". 6461.9Sapb ${EGREP} '^(@pkgdep|@blddep)' "${PLIST}" || true 6471.9Sapb # Now do the remainder of the file. 6481.14Sapb while read line; do 6491.9Sapb case "${line}" in 6501.9Sapb @pkgdep*|@blddep*) 6511.9Sapb # already handled by grep above 6521.9Sapb ;; 6531.9Sapb @cwd*) 6541.9Sapb # There should be exactly one @cwd line. 6551.9Sapb # Just after it, add an "@exec mkdir" 6561.9Sapb # line for every directory. This is to 6571.9Sapb # work around a pkg-add bug (see 6581.9Sapb # <http://mail-index.NetBSD.org/tech-pkg/2003/12/11/0018.html>) 6591.9Sapb echo "${line}" 6601.9Sapb print_dir_exec_lines 6611.9Sapb ;; 6621.9Sapb @*) 6631.9Sapb # just pass through all other @foo lines 6641.9Sapb echo "${line}" 6651.9Sapb ;; 6661.9Sapb *) 6671.9Sapb # This should be a file name. Pass it 6681.26Suki # through, and append "@comment SHA256:". 6691.9Sapb echo "${line}" 6701.26Suki file="${DESTDIR}/${line}" 6711.26Suki if [ -f "${file}" ] && [ -r "${file}" ]; 6721.9Sapb then 6731.26Suki sha256sum="$(${CKSUM} -a sha256 -n "${file}" \ 6741.9Sapb | ${AWK} '{print $1}' 6751.9Sapb )" 6761.26Suki echo "@comment SHA256:${sha256sum}" 6771.9Sapb fi 6781.9Sapb ;; 6791.9Sapb esac 6801.9Sapb done <"${PLIST}" 6811.9Sapb } >"${SYSPKG_DB_SUBDIR}/+CONTENTS" 6821.9Sapb 6831.9Sapb # 6841.9Sapb # Update ${SYSPKG_DB_TOPDIR}/pkgdb.byfile.db. 6851.9Sapb # 6861.9Sapb { 6871.13Sapb init_db_opts # sets dbfile, dbtype, and db_opts 6881.9Sapb 6891.9Sapb # Transform ${PLIST} into a form to be used as keys in 6901.9Sapb # ${dbfile}. The results look like absolute paths, 6911.9Sapb # but they are really relative to ${DESTDIR}. 6921.9Sapb # 6931.25Suki # "@pkgdir ." -> "/" 6941.25Suki # "@pkgdir foo/bar" -> "/foo/bar" 6951.25Suki # "@pkgdir ./foo/bar" -> "/foo/bar" 6961.9Sapb # "foo/bar/baz" -> "/foo/bar/baz" 6971.9Sapb # "./foo/bar/baz" -> "/foo/bar/baz" 6981.9Sapb # 6991.9Sapb dblist="${SCRATCH}/dblist" 7001.25Suki ${AWK} '/^@pkgdir \.\// {gsub("^.", "", $2); print $2; next} 7011.25Suki /^@pkgdir \.$/ {print "/"; next} 7021.25Suki /^@pkgdir/ {print "/" $2; next} 7031.9Sapb /^@/ {next} 7041.9Sapb /^\.\// {gsub("^.", "", $0); print $0; next} 7051.9Sapb /./ {print "/" $0; next}' \ 7061.9Sapb <"${PLIST}" >"${dblist}" 7071.9Sapb # Add all the path names to the database. 7081.9Sapb ${AWK} '{print $1 "\t" "'"${pkg}-${t}"'"}' <"${dblist}" \ 7091.9Sapb | ${DB} -w ${db_opts} -F "${tab}" -f - "${dbtype}" "${dbfile}" 7101.9Sapb } 7111.9Sapb 7121.14Sapb if ${verbose}; then 7131.9Sapb echo "Registered ${pkg}-${t} in ${SYSPKG_DB_TOPDIR}" 7141.14Sapb elif ! ${quiet}; then 7151.9Sapb echo "Registered ${pkg}-${t}" 7161.9Sapb fi 7171.9Sapb 7181.9Sapb cleanup_must_delete_dbsubdir=false 7191.9Sapb} 7201.9Sapb 7211.9Sapb# 7221.9Sapb# create_syspkg_tgz() creates the *.tgz file for the package. 7231.9Sapb# 7241.9Sapb# The output file is ${binpkgdir}/${pkg}-${t}.tgz. 7251.9Sapb# 7261.14Sapbcreate_syspkg_tgz() 7271.9Sapb{ 7281.9Sapb # 7291.9Sapb # pkg_create does not understand metalog files, so we have to 7301.9Sapb # use pax directly. 7311.9Sapb # 7321.9Sapb # We create two specfiles: specfile_overhead describes the 7331.9Sapb # special files that are part of the package system's metadata 7341.9Sapb # (+CONTENTS, +COMMENT, +DESCR, and more); and specfile_payload 7351.9Sapb # describes the files and directories that we actually want as 7361.9Sapb # part of the package's payload. 7371.9Sapb # 7381.9Sapb # We then use the specfiles to create a compressed tarball that 7391.9Sapb # contains both the overhead files and the payload files. 7401.9Sapb # 7411.9Sapb # There's no trivial way to get a single pax run to do 7421.9Sapb # everything we want, so we run pax twice, with a different 7431.9Sapb # working directory and a different specfile each time. 7441.9Sapb # 7451.9Sapb # We could conceivably make clever use of pax's "-s" option to 7461.9Sapb # get what we want from a single pax run with a single (more 7471.9Sapb # complicated) specfile, but the extra trouble doesn't seem 7481.9Sapb # warranted. 7491.9Sapb # 7501.9Sapb cleanup_must_delete_binpkgfile=true 7511.9Sapb specfile_overhead="${SCRATCH}/spec_overhead" 7521.9Sapb specfile_payload="${SCRATCH}/spec_payload" 7531.9Sapb tarball_uncompressed="${SCRATCH}/tarball_uncompressed" 7541.9Sapb 7551.9Sapb # Create a specfile for all the overhead files (+CONTENTS and 7561.9Sapb # friends). 7571.9Sapb { 7581.9Sapb plusnames_first="${SCRATCH}/plusnames_first" 7591.9Sapb plusnames_rest="${SCRATCH}/plusnames_rest" 7601.9Sapb 7611.9Sapb # Ensure that the first few files are in the same order 7621.9Sapb # that "pkg_create" would have used, just in case anything 7631.9Sapb # depends on that. Other files in alphabetical order. 7641.9Sapb SHOULD_BE_FIRST="+CONTENTS +COMMENT +DESC" 7651.9Sapb ( 7661.9Sapb cd "${SYSPKG_DB_SUBDIR}" || bomb 7671.9Sapb for file in ${SHOULD_BE_FIRST}; do 7681.9Sapb [ -e "./${file}" ] && echo "${file}" 7691.9Sapb done >"${plusnames_first}" 7701.9Sapb ${LS} -1 | ${FGREP} -v -f "${plusnames_first}" \ 7711.9Sapb >"${plusnames_rest}" \ 7721.9Sapb || true 7731.9Sapb ) 7741.9Sapb 7751.9Sapb # Convert the file list to specfile format, and override the 7761.9Sapb # uid/gid/mode. 7771.9Sapb { 7781.9Sapb echo ". optional type=dir" 7791.9Sapb ${AWK} '{print "./" $0 " type=file uid=0 gid=0 mode=0444" 7801.9Sapb }' "${plusnames_first}" "${plusnames_rest}" 7811.9Sapb } >"${specfile_overhead}" 7821.9Sapb } 7831.9Sapb 7841.9Sapb # Create a specfile for the payload of the package. 7851.9Sapb { 7861.9Sapb spec1="${SCRATCH}/spec1" 7871.9Sapb spec2="${SCRATCH}/spec2" 7881.9Sapb 7891.9Sapb # Transform ${PLIST} into simple specfile format: 7901.9Sapb # 7911.25Suki # "@pkgdir ." -> ". type=dir" 7921.25Suki # "@pkgdir foo/bar" -> "./foo/bar type=dir" 7931.25Suki # "@pkgdir ./foo/bar" -> "./foo/bar type=dir" 7941.9Sapb # "foo/bar/baz" -> "./foo/bar/baz" 7951.9Sapb # "./foo/bar/baz" -> "./foo/bar/baz" 7961.9Sapb # 7971.9Sapb # Ignores @cwd lines. This should be safe, given how 7981.9Sapb # makeplist works. 7991.25Suki ${AWK} '/^@pkgdir \.\// {print $2 " type=dir"; next} 8001.25Suki /^@pkgdir \.$/ {print ". type=dir"; next} 8011.25Suki /^@pkgdir/ {print "./" $2 " type=dir"; next} 8021.9Sapb /^@/ {next} 8031.9Sapb /^\.\// {print $0; next} 8041.9Sapb /./ {print "./" $0; next}' \ 8051.21Suebayasi <"${PLIST}" | 8061.21Suebayasi # Escape some characters to match the new mtree(8) format. 8071.21Suebayasi # C.f. usr.sbin/mtree/spec.c:vispath() 8081.21Suebayasi # XXX escape only '[' for now 8091.22Suebayasi ${SED} -e 's,\[,\\133,g' \ 8101.21Suebayasi >"${spec1}" 8111.9Sapb 8121.9Sapb # If metalog was specified, attributes from metalog override 8131.9Sapb # attributes in the file system. We also fake up an 8141.9Sapb # entry for the ./etc/mtree/set.${pkgset} file. 8151.9Sapb { 8161.9Sapb if [ -n "${metalog}" ]; then 8171.9Sapb ${AWK} -f "${rundir}/join.awk" \ 8181.9Sapb "${spec1}" "${metalog}" 8191.9Sapb ${AWK} -f "${rundir}/join.awk" \ 8201.9Sapb "${spec1}" /dev/stdin <<EOF 8211.9Sapb./etc/mtree/set.${pkgset} type=file mode=0444 uname=root gname=wheel 8221.9SapbEOF 8231.9Sapb else 8241.9Sapb cat "${spec1}" 8251.9Sapb fi 8261.9Sapb } >"${spec2}" 8271.9Sapb 8281.9Sapb # 8291.9Sapb # If a file or directory to was mentioned explicitly 8301.9Sapb # in ${PLIST} but not mentioned in ${metalog}, then the 8311.9Sapb # file or directory will not be mentioned in ${spec2}. 8321.9Sapb # This is an error, and means that the metalog was 8331.9Sapb # not built correctly. 8341.9Sapb # 8351.9Sapb if [ -n "${metalog}" ]; then 8361.9Sapb names1="${SCRATCH}/names1" 8371.9Sapb names2="${SCRATCH}/names2" 8381.24Srhialto ${AWK} '{print $1}' <"${spec1}" | ${SORT} >"${names1}" 8391.24Srhialto ${AWK} '{print $1}' <"${spec2}" | ${SORT} >"${names2}" 8401.9Sapb if ${FGREP} -v -f "${names2}" "${spec1}" >/dev/null 8411.9Sapb then 8421.9Sapb cat >&2 <<EOM 8431.9Sapb${ERRWARN}The metalog file (${metalog}) does not 8441.9Sapb contain entries for the following files or directories 8451.9Sapb which should be part of the ${pkg} syspkg: 8461.9SapbEOM 8471.9Sapb ${FGREP} -v -f "${names2}" "${spec1}" >&2 8481.9Sapb ${force} || bomb 8491.9Sapb fi 8501.9Sapb if ${FGREP} -v -f "${names1}" "${spec2}" >/dev/null 8511.9Sapb then 8521.9Sapb cat >&2 <<EOM 8531.9Sapb${ERRWARN}The following lines are in the metalog file 8541.9Sapb (${metalog}), and the corresponding files or directories 8551.9Sapb should be in the ${pkg} syspkg, but something is wrong: 8561.9SapbEOM 8571.9Sapb ${FGREP} -v -f "${names1}" "${spec2}" >&2 8581.9Sapb bomb 8591.9Sapb fi 8601.9Sapb fi 8611.9Sapb 8621.9Sapb # Add lines (tagged "optional") for any implicit directories. 8631.9Sapb # 8641.9Sapb # For example, if we have a file ./foo/bar/baz, then we add 8651.9Sapb # "./foo/bar optional type=dir", "./foo optional type=dir", 8661.9Sapb # and ". optional type=dir", unless those directories were 8671.9Sapb # already mentioned explicitly. 8681.9Sapb # 8691.9Sapb ${AWK} -f "${rundir}/getdirs.awk" "${spec2}" \ 8701.9Sapb | ${SORT} -u >"${specfile_payload}" 8711.9Sapb } 8721.9Sapb 8731.9Sapb # Use two pax invocations followed by gzip to create 8741.9Sapb # the tgz file. 8751.9Sapb # 8761.9Sapb # Remove any leading "./" from path names, because that 8771.9Sapb # could confuse tools that work with binary packages. 8781.9Sapb ( 8791.9Sapb cd "${SYSPKG_DB_SUBDIR}" && \ 8801.9Sapb ${PAX} -O -w -d -N"${etcdir}" -M '-s,^\./,,' \ 8811.9Sapb -f "${tarball_uncompressed}" \ 8821.9Sapb <"${specfile_overhead}" \ 8831.9Sapb || bomb 8841.9Sapb ) 8851.9Sapb ( 8861.9Sapb cd "${DESTDIR:-/}" && \ 8871.9Sapb ${PAX} -O -w -d -N"${etcdir}" -M '-s,^\./,,' \ 8881.9Sapb -a -f "${tarball_uncompressed}" \ 8891.9Sapb <"${specfile_payload}" \ 8901.9Sapb || bomb 8911.9Sapb ) 8921.16Sperry ${GZIP_CMD} -9n <"${tarball_uncompressed}" >"${binpkgfile}" || bomb 8931.9Sapb 8941.9Sapb # (Extra space is to make message line up with "Registered" message.) 8951.14Sapb if ${verbose}; then 8961.9Sapb echo " Packaged ${binpkgfile}" 8971.14Sapb elif ! ${quiet}; then 8981.9Sapb echo " Packaged ${binpkgfile##*/}" 8991.9Sapb fi 9001.9Sapb 9011.9Sapb cleanup_must_delete_binpkgfile=false 9021.9Sapb 9031.9Sapb} 9041.9Sapb 9051.9Sapb# 9061.9Sapb# do_register_syspkg() registers the syspkg if appropriate. 9071.9Sapb# 9081.9Sapb# If SYSPKG_DB_SUBDIR already exists, that might be an error, depending 9091.9Sapb# on ${force} and ${update} flags. 9101.9Sapb# 9111.14Sapbdo_register_syspkg() 9121.9Sapb{ 9131.9Sapb # Check that necessary variables are defined 9141.9Sapb [ -n "${SYSPKG_DB_TOPDIR}" ] || bomb 9151.9Sapb [ -n "${SYSPKG_DB_SUBDIR}" ] || bomb 9161.9Sapb 9171.9Sapb # Create SYSPKG_DB_TOPDIR if necessary 9181.9Sapb [ -d "${SYSPKG_DB_TOPDIR}" ] || mkdir -p "${SYSPKG_DB_TOPDIR}" || bomb 9191.9Sapb 9201.13Sapb # A function to delete db entries referring to any version of ${pkg} 9211.14Sapb delete_old_db_entries() 9221.13Sapb { 9231.13Sapb init_db_opts # sets dbfile, dbtype, and db_opts 9241.13Sapb dblist="${SCRATCH}/dblist" 9251.13Sapb ${DB} ${db_opts} -O "${tab}" "${dbtype}" "${dbfile}" \ 9261.13Sapb | ${AWK} -F "${tab}" '$2 ~ /^'"${pkg}"'-[0-9]/ { print $1 }' \ 9271.13Sapb >"${dblist}" 9281.13Sapb ${DB} -d ${db_opts} -f "${dblist}" "${dbtype}" "${dbfile}" 9291.13Sapb } 9301.13Sapb 9311.13Sapb # A function to delete any old version of ${pkg} 9321.14Sapb delete_old_pkg() 9331.9Sapb { 9341.13Sapb pattern="${pkg}-[0-9]*" 9351.14Sapb matches="$(cd "${SYSPKG_DB_TOPDIR}" && echo ${pattern} \ 9361.14Sapb || bomb)" 9371.13Sapb echo >&2 "${NOTE}deleting old pkg (${matches})" 9381.9Sapb cleanup_must_delete_dbsubdir=true 9391.13Sapb delete_old_db_entries 9401.13Sapb ( cd "${SYSPKG_DB_TOPDIR}" && rm -rf ${matches} ) 9411.9Sapb } 9421.9Sapb 9431.9Sapb # Check whether another version of ${pkg} is already registered. 9441.9Sapb pattern="${pkg}-[0-9]*" 9451.14Sapb matches="$(cd "${SYSPKG_DB_TOPDIR}" && echo ${pattern} || bomb)" 9461.9Sapb case "${matches}" in 9471.9Sapb *\*) ;; # wildcard did not match anything 9481.9Sapb "${pkg}-${t}") ;; # exact match 9491.13Sapb *) echo >&2 "${ERRWARNNOTE}another version of ${pkg} is already registered" 9501.13Sapb ${verbose} && echo >&2 " in ${SYSPKG_DB_TOPDIR}" 9511.13Sapb ${verbose} && echo >&2 " (while registering ${pkg}-${t})" 9521.13Sapb ${force} || ${update} || bomb 9531.13Sapb delete_old_pkg 9541.9Sapb ;; 9551.9Sapb esac 9561.9Sapb 9571.9Sapb # Check whether the desired version of ${pkg} is already registered, 9581.9Sapb # and create it if appropriate. 9591.9Sapb if [ -d "${SYSPKG_DB_SUBDIR}" ]; then 9601.9Sapb echo >&2 "${ERRWARNNOTE}${pkg}-${t} is already registered" 9611.9Sapb ${verbose} && echo >&2 " in ${SYSPKG_DB_TOPDIR}" 9621.9Sapb if ${force}; then 9631.13Sapb delete_old_pkg 9641.13Sapb register_syspkg 9651.9Sapb elif ${update}; then 9661.9Sapb # 9671.9Sapb # If all files in SYSPKG_DB_SUBDIR are newer 9681.9Sapb # than all files in the pkg, then do nothing. 9691.9Sapb # Else delete and re-register the pkg. 9701.9Sapb # 9711.9Sapb [ -n "${newestfile}" ] || init_newestfile 9721.9Sapb if [ -n "${newestfile}" ]; then 9731.14Sapb case "$(${FIND} "${SYSPKG_DB_SUBDIR}" -type f \ 9741.14Sapb ! -newer "${newestfile}" -print)" \ 9751.9Sapb in 9761.9Sapb "") ;; 9771.13Sapb *) 9781.13Sapb echo >&2 "${NOTE}some files are newer but pkg version is unchanged" 9791.13Sapb delete_old_pkg 9801.13Sapb register_syspkg 9811.13Sapb ;; 9821.9Sapb esac 9831.9Sapb 9841.9Sapb else 9851.9Sapb # No files in the pkg? (This could happen 9861.9Sapb # if a pkg contains only directories.) 9871.13Sapb # Do nothing (keep the already-registered pkg). 9881.19Sapb : 9891.9Sapb fi 9901.9Sapb else 9911.9Sapb bomb 9921.9Sapb fi 9931.9Sapb else 9941.9Sapb register_syspkg 9951.9Sapb fi 9961.9Sapb} 9971.9Sapb 9981.9Sapb# 9991.20Smbalmer# do_create_syspkg_tgz() creates the binary pkg (*.tgz) if 10001.9Sapb# appropriate. 10011.9Sapb# 10021.9Sapb# If binpkgfile already exists, that might be an error, depending on 10031.9Sapb# ${force} and ${update} flags. 10041.9Sapb# 10051.14Sapbdo_create_syspkg_tgz() 10061.9Sapb{ 10071.9Sapb [ -n "${binpkgfile}" ] || bomb 10081.9Sapb 10091.14Sapb delete_and_recreate() 10101.9Sapb { 10111.9Sapb echo >&2 "${ERRWARNNOTE}deleting and re-creating ${pkg}-${t}.tgz" 10121.9Sapb rm -f "${binpkgfile}" 10131.9Sapb create_syspkg_tgz 10141.9Sapb } 10151.9Sapb 10161.9Sapb # Check whether another version of ${pkg} already exists. 10171.9Sapb pattern="${pkg}-[0-9]*" 10181.14Sapb matches="$(cd "${binpkgdir}" && echo ${pattern} || bomb)" 10191.9Sapb case "${matches}" in 10201.9Sapb *\*) ;; # wildcard did not match anything 10211.9Sapb "${pkg}-${t}.tgz") ;; # exact match 10221.13Sapb *) echo >&2 "${ERRWARNNOTE}another version of ${pkg} binary pkg already exists" 10231.13Sapb ${verbose} && echo >&2 " in ${binpkgdir}" 10241.13Sapb ${verbose} && echo >&2 " (while creating ${pkg}-${t}.tgz)" 10251.13Sapb # If neither force nor update, this is a fatal error. 10261.13Sapb # If force but not update, then leave old .tgz in place. 10271.13Sapb # If update, then delete the old .tgz. 10281.13Sapb ${force} || ${update} || bomb 10291.13Sapb if ${update}; then 10301.13Sapb echo >&2 "${NOTE}deleting old binary pkg (${matches})" 10311.13Sapb ( cd "${binpkgdir}" && rm -f ${matches} || bomb ) 10321.13Sapb fi 10331.9Sapb ;; 10341.9Sapb esac 10351.9Sapb 10361.9Sapb # Check whether the desired version of ${pkg} already exists, 10371.9Sapb # and create it if appropriate. 10381.9Sapb if [ -e "${binpkgfile}" ]; then 10391.9Sapb echo >&2 "${ERRWARNNOTE}${pkg}-${t}.tgz already exists" 10401.9Sapb ${verbose} && echo >&2 " in ${binpkgdir}" 10411.9Sapb if ${force}; then 10421.9Sapb delete_and_recreate 10431.9Sapb elif ${update}; then 10441.9Sapb # 10451.9Sapb # If all files in SYSPKG_DB_SUBDIR are older 10461.9Sapb # than ${binpkgfile}, then do nothing. 10471.9Sapb # Else delete and re-create the tgz. 10481.9Sapb # 10491.14Sapb case "$(${FIND} "${SYSPKG_DB_SUBDIR}" -type f \ 10501.14Sapb -newer "${binpkgfile}" -print)" \ 10511.9Sapb in 10521.9Sapb "") ;; 10531.9Sapb *) delete_and_recreate ;; 10541.9Sapb esac 10551.9Sapb else 10561.9Sapb bomb 10571.9Sapb fi 10581.9Sapb else 10591.9Sapb create_syspkg_tgz 10601.9Sapb fi 10611.9Sapb} 10621.9Sapb 10631.9Sapb#################### 10641.9Sapb# begin main program 10651.9Sapb 10661.9Sapbparse_args ${1+"$@"} 10671.9Sapbmake_PLIST 10681.9Sapbchoose_version_number 10691.9SapbSYSPKG_DB_SUBDIR="${SYSPKG_DB_TOPDIR}/${pkg}-${t}" 10701.9Sapbdo_register_syspkg 10711.9Sapbif [ -n "${binpkgdir}" ]; then 10721.9Sapb binpkgfile="${binpkgdir}/${pkg}-${t}.tgz" 10731.9Sapb do_create_syspkg_tgz 10741.5Sdyoungfi 10751.1Sagc 10761.9Sapbexit 0 1077