Newer
Older
if [ "$arch" != "noarch" ] && ! options_has "!tracedeps"; then
for file in "$pkgbasedir"/.control.*/.PKGINFO; do
dir="${file%/.PKGINFO}"
name="$(pkginfo_val pkgname $file)"
datadir="$pkgbasedir"/$name
subpkgname=$name
scan_shared_objects "$name" "$dir" "$datadir"
done
fi
for file in "$pkgbasedir"/.control.*/.PKGINFO; do
dir="${file%/.PKGINFO}"
name=$(pkginfo_val pkgname $file)
ver=$(pkginfo_val pkgver $file)
apk=$name-$ver.apk
datadir="$pkgbasedir"/$name
subpkgname=$name
trace_apk_deps "$name" "$dir" || return 1
msg "Compressing data..."
Natanael Copa
committed
(
cd "$datadir"
# data.tar.gz
set -- *
if [ "$1" = '*' ]; then
touch .dummy
set -- .dummy
fi
tar -c "$@" | abuild-tar --hash | gzip -9 >"$dir"/data.tar.gz
msg "Create checksum..."
# append the hash for data.tar.gz
local sha256=$(sha256sum "$dir"/data.tar.gz | cut -f1 -d' ')
echo "datahash = $sha256" >> "$dir"/.PKGINFO
# control.tar.gz
tar -c $(cat "$dir"/.metafiles) | abuild-tar --cut \
| gzip -9 > control.tar.gz
abuild-sign -q control.tar.gz || exit 1
msg "Create $apk"
# create the final apk
cat control.tar.gz data.tar.gz > "$PKGDEST"/$apk
subpkgname=
cd "$abuildrepo" || return 1
# remove compat symlink
for d in "$abuildrepo/$CARCH"; do
[ -L "$d" ] && rm "$d"
done
# remove broken links from abuildrepo
for apk in *.apk */*.apk; do
if [ -L "$apk" ] && [ ! -f "$apk" ]; then
rm -f "$apk"
fi
done
local apk
mkdir -p "$abuildrepo"/$CARCH
# create links for this package
[ -f "$PKGDEST"/$apk ] || continue
ln -sf "$PKGDEST"/$apk "$abuildrepo"/$CARCH/$apk
}
update_abuildrepo() {
local d apk
if ! apk_up2date || [ -n "$force" ]; then
sanitycheck && builddeps && clean && fetch && unpack \
&& prepare && mkusers && rootpkg || return 1
fi
clean_abuildrepo
mklinks_abuildrepo
cd "$abuildrepo"
local index=$CARCH/APKINDEX.tar.gz
msg "Updating the cached abuild repository index..."
local sign=".SIGN.RSA.${SIGN_PUBLIC_KEY##*/}"
local oldindex=
if [ -f "$index" ]; then
oldindex="--index $index"
$APK index --quiet $oldindex --output "$index".unsigned \
--description "$repo $(cd $startdir && git describe)" \
--rewrite-arch $CARCH \
$CARCH/*.apk || exit 1
abuild-sign -q "$index".unsigned || exit 1
mv "$index".unsigned "$index"
chmod 644 "$index"
default_doc() {
depends="$depends_doc"
pkgdesc="$pkgdesc (documentation)"
arch=${arch_doc:-"noarch"}
for i in doc man info html sgml licenses gtk-doc; do
if [ -d "$pkgdir/usr/share/$i" ]; then
mkdir -p "$subpkgdir/usr/share"
mv "$pkgdir/usr/share/$i" "$subpkgdir/usr/share/"
rm -f "$subpkgdir/usr/share/info/dir"
# remove if empty, ignore error (not empty)
rmdir "$pkgdir/usr/share" "$pkgdir/usr" 2>/dev/null
doc() {
default_doc
}
default_mod() {
depends="$kernel $depends_mod"
if [ -d "$pkgdir/lib/$i" ]; then
rm -rf "$subpkgdir/lib"
mkdir -p "$subpkgdir/lib"
mv "$pkgdir/lib/$i" "$subpkgdir/lib"
mod() {
default_mod
}
default_dev() {
depends="$pkgname $depends_dev"
pkgdesc="$pkgdesc (development files)"
for i in $origsubpackages; do
[ "${i%:*}" = "$subpkgname" ] || depends="$depends ${i%:*}"
done
for i in usr/include usr/lib/pkgconfig usr/share/aclocal\
usr/share/gettext usr/bin/*-config \
usr/share/vala/vapi usr/share/gir-[0-9]*\
$(find -name include -type d) \
$(find usr/ -name '*.[acho]' 2>/dev/null); do
if [ -e "$pkgdir/$i" ] || [ -L "$pkgdir/$i" ]; then
d="$subpkgdir/${i%/*}" # dirname $i
rmdir "$pkgdir/${i%/*}" 2>/dev/null
# move *.so links needed when linking the apps to -dev packages
for i in lib/*.so usr/lib/*.so; do
if [ -L "$i" ]; then
mkdir -p "$subpkgdir"/"${i%/*}"
mv "$i" "$subpkgdir/$i" || return 1
fi
done
dev() {
default_dev
}
is_function() {
type "$1" 2>&1 | head -n 1 | egrep -q "is a (shell )?function"
}
do_fakeroot() {
if [ -n "$FAKEROOT" ]; then
$FAKEROOT -- "$@"
else
"$@"
fi
}
local do_build=build
cd "$startdir"
if is_function package; then
build || return 1
[ -n "$FAKEROOT" ] && msg "Entering fakeroot..."
do_fakeroot "$abuild_path" $color_opt $do_build \
getpkgver || return 1
local p="$pkgname-$pkgver-$pkgrel"
local i files="$prefix/APKBUILD"
for i in $source; do
files="$files $prefix/${i##*/}"
done
mkdir -p "$PKGDEST"
msg "Creating source package $p.src.tar.gz..."
(cd .. && tar -zcf "$PKGDEST/$p.src.tar.gz" $files)
# return true if arch is supported or noarch
check_arch() {
list_has $CARCH $arch || [ "$arch" = "noarch" ] || [ "$arch" = "all" ]
# check if package is up to date
getpkgver || return 1
local pkg="$PKGDEST/$pkgname-$pkgver-r$pkgrel.apk"
for i in $pkgname $subpackages; do
[ -f "$PKGDEST/$pkgname-$pkgver-r$pkgrel.apk" ] || return 1
done
[ -n "$keep" ] && return 0
for i in $source APKBUILD; do
local s
if is_remote "$i"; then
s="$SRCDEST/${i##*/}" # $(basename $i)
else
s="$startdir/${i##*/}"
fi
if [ "$s" -nt "$pkg" ]; then
return 1
fi
done
return 0
}
getpkgver || return 1
local dir="$abuildrepo"/$CARCH
local apk="${pkgname%:*}-$pkgver-r$pkgrel.apk"
local idx="$dir"/APKINDEX.tar.gz
local file="$dir"/$apk
# check if index is missing
[ -f "$idx" ] || return 1
# if link or file is missing, then we need update abuildrepo index
[ -f "$file" ] || return 1
# if file exists and is newer than index, then we need update index
[ "$file" -nt "$idx" ] && return 1
return 0
}
up2date() {
apk_up2date && abuildindex_up2date
}
# rebuild package and abuildrepo index if needed
abuildindex() {
up2date && return 0
update_abuildrepo
# source all APKBUILDs and output:
# 1) origin of package
# 2) all dependencies
# the output is i in a format easy parseable for awk
depparse_aports() {
# lets run this in a subshell since we source all APKBUILD here
(
aportsdir=$(realpath ${APKBUILD%/APKBUILD}/..)
for i in $aportsdir/*/APKBUILD; do
pkgname=
subpackages=
depends=
makedepends=
# filter out conflicts from deps and version info
for j in $depends $makedepends; do
case "$j" in
!*) continue;;
esac
for j in $pkgname $subpackages; do
echo -n "d ${j%%:*} $1"
shift
while [ $# -gt 0 ]; do
echo -n ",$1"
shift
done
echo
local deps= i=
# strip versions from deps
for i in "$@"; do
done
[ -z "$deps" ] && return 0
( depparse_aports
if [ -z "$upgrade" ]; then
# list installed pkgs and prefix with 'i '
$APK info -q | sort | sed 's/^/i /'
) | awk -v pkgs="$deps" '
1340
1341
1342
1343
1344
1345
1346
1347
1348
1349
1350
1351
1352
1353
1354
1355
1356
1357
1358
1359
1360
1361
1362
1363
1364
function depgraph(pkg, a, i) {
if (visited[pkg])
return 0;
visited[pkg] = 1;
split(deps[pkg], a, ",");
for (i in a)
depgraph(a[i]);
print pkg ":" origin[pkg];
}
$1 == "i" { visited[$2] = 1 }
$1 == "o" { origin[$2] = $3 }
$1 == "d" { deps[$2] = $3 }
END {
split(pkgs, pkgarray);
for (i in pkgarray)
depgraph(pkgarray[i]);
}
'
}
# build and install dependencies
builddeps() {
local deps= alldeps= pkg= i= dir= ver= missing= installed_deps=
local filtered_deps= conflicts=
[ -n "$nodeps" ] && return 0
Natanael Copa
committed
msg "Analyzing dependencies..."
# add depends unless it is a subpackage or package itself
for i in $BUILD_BASE $depends $makedepends; do
[ "$pkgname" = "${i%%[<>=]*}" ] && continue
subpackages_has ${i%%[<>=]*} || deps="$deps $i"
done
installed_deps=$($APK info -e $deps)
# find which deps are missing
for i in $deps; do
if [ "${i#\!}" != "$i" ]; then
$APK info -q -e "${i#\!}" \
&& conflicts="$conflicts ${i#\!}"
elif ! deplist_has $i $installed_deps || [ -n "$upgrade" ]; then
missing="$missing $i"
fi
done
if [ -n "$conflicts" ]; then
error "Conflicting package(s) installed:$conflicts"
return 1
fi
if [ -z "$install_deps" ] && [ -z "$recursive" ]; then
# if we dont have any missing deps we are done now
[ -z "$missing" ] && return 0
error "Missing dependencies: $missing Use -r to autoinstall or -R to build"
return 1
fi
uninstall_after=".makedepends-$pkgname $uninstall_after"
if [ -n "$install_deps" ] && [ -z "$recursive" ] && [ -n "$deps" ]; then
# make a --simluate run first to detect missing deps
# apk-tools --virtual is no goot at reporting those.
$SUDO_APK add --repository "$abuildrepo" \
--simulate --quiet $deps || return 1
$SUDO_APK add --repository "$abuildrepo" \
--virtual .makedepends-$pkgname $deps \
&& return 0
[ -z "$recursive" ] && return 1
# find dependencies that are installed but missing in repo.
for i in $deps; do
local m=$($APK search --repository "$abuildrepo" ${i%%[<>=]*})
missing="$missing $i"
fi
done
for i in $(deptrace $missing); do
# i = pkg:dir
local dir=${i#*:}
local pkg=${i%:*}
# ignore if dependency is in other repo
[ -d "$dir" ] || continue
# break cricular deps
list_has $pkg $ABUILD_VISITED && continue
export ABUILD_VISITED="$ABUILD_VISITED $pkg"
msg "Entering $dir"
cd "$dir" && $0 $forceroot $keep $quiet $install_deps \
$recursive $upgrade $color_opt abuildindex || return 1
$SUDO_APK add -u --repository "$abuildrepo" \
--virtual .makedepends-$pkgname $deps
# replace the md5sums in the APKBUILD
[ -z "$source" ] && return 0
msg "Updating the md5sums in APKBUILD..."
for s in $source; do
files="$files ${s##*/}"
done
md5sums="$(cd "$srcdir" && md5sum $files)" || die "md5sum failed"
sed -i -e '/^md5sums="/,/"\$/d; /^md5sums=''/,/''\$/d' "$APKBUILD"
echo "md5sums=\"$md5sums\"" >>"$APKBUILD"
if options_has "!strip" || [ "$arch" = "noarch" ]; then
return 0
fi
cd "${subpkgdir:-$pkgdir}" || return 1
msg "Stripping binaries"
scanelf --recursive --nobanner --etype "ET_DYN,ET_EXEC" . \
| sed -e 's:^ET_DYN ::' -e 's:^ET_EXEC ::' \
| xargs -r strip
# simply list target apks
listpkg() {
getpkgver || return 1
for name in $(listpkgnames) ; do
echo "$name-$pkgver-r$pkgrel.apk"
source_has() {
local i
for i in $source; do
[ "$1" = "${i##*/}" ] && return 0
done
return 1
}
subpackages_has() {
local i
for i in $subpackages; do
[ "$1" = "${i%:*}" ] && return 0
done
return 1
}
list_has() {
local needle="$1"
local i
shift
for i in $@; do
[ "$needle" = "$i" ] && return 0
[ "$needle" = "!$i" ] && return 1
done
return 1
}
# same as list_has but we filter version info
deplist_has() {
local needle="$1"
local i
shift
for i in $@; do
[ "$needle" = "$i" ] && return 0
[ "$needle" = "!$i" ] && return 1
done
return 1
}
options_has() {
list_has "$1" $options
}
depends_has() {
deplist_has "$1" $depends
}
deplist_has "$1" $makedepends
md5sums_has() {
list_has "$1" $md5sums
}
install_has() {
list_has "$1" $install
}
getpkgver || return 1
local pkgf="$PKGDEST/$1-$pkgver-r$pkgrel.apk"
local deps i
if ! subpackages_has $1 && [ "$1" != "$pkgname" ]; then
die "$1 is not built by this APKBUILD"
fi
# recursively install dependencies that are provided by this APKBUILD
deps=$($APK index "$pkgf" 2>/dev/null | awk -F: '$1=="D" { print $2 }')
for i in $deps; do
if subpackages_has $i || [ "$i" = "$pkgname" ]; then
post_add $i || return 1
fi
done
$SUDO_APK add $apk_opt_wait -u "$pkgf" || die "Failed to install $1"
installdeps() {
local deps i
$SUDO_APK add $apk_opt_wait --repository "$abuildrepo" \
--virtual .makedepends-$pkgname \
$makedepends
}
uninstalldeps (){
$SUDO_APK del $apk_opt_wait .makedepends-$pkgname
}
if ! [ -n "$force" ]; then
check_arch || return 0
fi
if up2date && [ -z "$force" ]; then
msg "Package is up to date"
else
echo "$program $abuild_ver"
echo "usage: $program [options] [-i PKG] [-P REPODEST] [-p PKGDEST]"
echo " [-s SRCDEST] [cmd] ..."
echo " $program [-c] -n PKGNAME[-PKGVER]"
echo " -c Enable colored output"
echo " -d Disable dependency checking"
echo " -f Force specified cmd, even if they are already done"
echo " -k Keep built packages, even if APKBUILD or sources are newer"
echo " -m Disable colors (monochrome)"
echo " -p Set package destination directory"
echo " -P Set PKGDEST to REPODEST/<repo>/\$CARCH, where repo is the parents dir name"
echo " -r Install missing dependencies from system repository (using sudo)"
echo " -R Recursively build and install missing dependencies (using sudo)"
echo " -s Set source package destination directory"
echo " -u Recursively build and upgrade all dependencies (using sudo)"
echo " checksum Generate checksum to be included in APKBUILD"
echo " fetch Fetch sources to \$SRCDEST and verify checksums"
echo " sanitycheck Basic sanity check of APKBUILD"
echo " md5check Check md5sums"
echo " unpack Unpack sources to \$srcdir"
echo " build Compile and install package into \$pkgdir"
echo " listpkg List target packages"
echo " package Create package in \$PKGDEST"
echo " rootpkg Run '$0 build package' as fakeroot"
echo " clean Remove temp build and install dirs"
echo " cleanoldpkg Remove binary packages except current version"
echo " cleanpkg Remove already built binary and source package"
echo " cleancache Remove downloaded files from \$SRCDEST"
echo " srcpkg Make a source package"
echo " sourcecheck Check if remote source package exists upstream"
echo " up2date Compare target and sources dates"
echo " installdeps Install packages listed in makedepends and depends"
echo " uninstalldeps Uninstall packages listed in makedepends and depends"
echo ""
exit 0
}
APKBUILD="${APKBUILD:-./APKBUILD}"
while getopts "cdfFhi:kimnp:P:qrRs:u" opt; do
'c') default_colors
color_opt="-c";;
'f') force="-f";;
'F') forceroot="-F";;
'h') usage;;
'i') install_after="$install_after $OPTARG";;
'k') keep="-k";;
'm') monochrome
color_opt="-m";;
'n') die "Use newapkbuild to create new aports";;
'p') PKGDEST=$OPTARG;;
'P') REPODEST=$OPTARG;;
'q') quiet="-q";;
'r') install_deps="-r";;
'R') recursive="-R";;
's') SRCDEST=$OPTARG;;
'u') upgrade="-u"
recursive="-R";;
# check so we are not root
if [ "$(whoami)" = "root" ] && [ -z "$FAKEROOTKEY" ]; then
[ -z "$forceroot" ] && die "Do not run abuild as root"
FAKEROOT=
fi
# find startdir
[ -f "$APKBUILD" ] || die "Could not find $APKBUILD (PWD=$PWD)"
APKBUILD=$(readlink -f "$APKBUILD")
startdir="${APKBUILD%/*}"
srcdir=${srcdir:-"$startdir/src"}
pkgbasedir=${pkgbasedir:-"$startdir/pkg"}
pkgrel=0
repo=${startdir%/*}
repo=${repo##*/}
abuildrepo="$abuildrepo_base"/$repo
SRCDEST=${SRCDEST:-$startdir}
PKGDEST=${PKGDEST:-$startdir}
cd "$startdir" || die
. "$APKBUILD"
# If REPODEST is set then it will override the PKGDEST
if [ -n "$REPODEST" ]; then
PKGDEST="$REPODEST/$repo/$CARCH"
# for recursive action
export REPODEST
# if we want build debug package
if [ -n "$DEBUG" ]; then
CFLAGS="$CFLAGS -g"
options="$options !strip"
fi
# If we are handling a sub package then reset subpackages and install
origsubpackages="$subpackages"
controldir="$pkgbasedir"/.control.${subpkgname:-$pkgname}
fi
while [ $# -gt 0 ]; do
runpart $1
shift
done