Skip to content

Commit

Permalink
split build into stages
Browse files Browse the repository at this point in the history
  • Loading branch information
nkraetzschmar committed Oct 9, 2023
1 parent ab0470f commit 84d0d0d
Show file tree
Hide file tree
Showing 7 changed files with 213 additions and 140 deletions.
9 changes: 2 additions & 7 deletions .github/workflows/build.yml
Original file line number Diff line number Diff line change
Expand Up @@ -9,13 +9,8 @@ jobs:
target: [ amd64, arm64v8 ]
steps:
- uses: actions/checkout@v3
- name: setup
run: |
ls -lah /proc/sys/fs/binfmt_misc
wget -q http://deb.debian.org/debian/pool/main/q/qemu/qemu-user-static_8.0.4+dfsg-3+b1_amd64.deb
sudo dpkg -i qemu-user-static_8.0.4+dfsg-3+b1_amd64.deb
sudo dd bs=1M if=/usr/lib/binfmt.d/qemu-aarch64.conf of=/proc/sys/fs/binfmt_misc/register
ls -lah /proc/sys/fs/binfmt_misc
- name: setup binfmt
run: sudo podman run --privileged -v /proc/sys/fs/binfmt_misc:/proc/sys/fs/binfmt_misc "ghcr.io/gardenlinux/binfmt_container"
- name: build
run: |
set -x
Expand Down
138 changes: 5 additions & 133 deletions build
Original file line number Diff line number Diff line change
Expand Up @@ -2,138 +2,10 @@

set -exuo pipefail

main() (
debian_source=
while [ $# -gt 0 ]; do
case "$1" in
--debian-source)
debian_source="$2"
shift 2
;;
*)
break
;;
esac
done
exec 3>&1
exec 1>&2

source="$1"
shift
pkg="$(build_source "$@")"

patches=()

while [ $# -gt 0 ]; do
patches+=("$1")
shift
done

if [[ "$source" = "git+"* ]]; then
git_source "${source#git+}"
else
apt_source "$source"
fi

if [ -n "$debian_source" ]; then
mkdir debian_src
cd debian_src
if [[ "$debian_source" = "git+"* ]]; then
git_source "${debian_source#git+}"
else
apt_source "$debian_source"
fi
rm -rf ../src/debian
mv src/debian ../src/
cd ..
rm -rf debian_src
fi

cd src

for patch in "${patches[@]}"; do
apply_patches "$patch"
done

name="$(dpkg-parsechangelog --show-field Source)"
version="$(dpkg-parsechangelog --show-field Version)"
version_orig="${version%-*}"
gzip < ../orig.tar > "../${name}_${version_orig}.orig.tar.gz"
rm ../orig.tar

sudo apt-get build-dep --no-install-recommends -y .
DEB_BUILD_OPTIONS="terse ${DEB_BUILD_OPTIONS-}" dpkg-buildpackage --no-sign

cd ..
rm -rf src
ls -lah
)

apt_source() (
apt-get source --only-source --download-only "$1"
orig=(*.orig.tar.*)
debian=(*.debian.tar.*)
dsc=(*.dsc)
auto_decompress "$orig" > orig.tar
mkdir src
tar -C src -x --strip-components 1 < orig.tar
auto_decompress "$debian" | tar -C src -xv
rm "$orig" "$debian" "$dsc"
)

git_source() (
IFS='#' read -r url ref <<< "$1"
git clone --bare --branch "$ref" --depth 1 "$url" src.git
GIT_DIR=src.git git archive --prefix src/ "$ref" > orig.tar
rm -rf src.git
tar -x < orig.tar
)

auto_decompress() (
case "${1##*.}" in
gz)
gzip -d < "$1"
;;
xz)
xz -d < "$1"
;;
*)
exit 1
;;
esac
)

apply_patches() (
git_dir="$(realpath $(mktemp -u ../patches.tmp.XXXX))"
if [[ "$1" = "git+"* ]]; then
IFS='#' read -r url ref <<< "${1#git+}"
git clone --branch "$ref" --depth 1 "$url" "$git_dir"
dir="$git_dir"
else
dir="$(cd .. && realpath "$1")"
fi

if [ -x "$dir/exec.pre" ]; then
SOURCE="$source" "$dir/exec.pre"
fi

if [ -f "$dir/patches/series" ]; then
while read -r patch; do
patch -p1 < "$dir/patches/$patch"
done < "$dir/patches/series"
fi

version="$(yq -r .version < "$dir/changelog_config.yaml")"
[ "$version" != null ] || version="$(dpkg-parsechangelog --show-field Version)"
email="$(yq -r .email < "$dir/changelog_config.yaml")"
name="$(yq -r .name < "$dir/changelog_config.yaml")"
distribution="$(yq -r .distribution < "$dir/changelog_config.yaml")"
version_suffix="$(yq -r .version_suffix < "$dir/changelog_config.yaml")"
message="$(yq -r .message < "$dir/changelog_config.yaml")"
DEBEMAIL="$email" DEBFULLNAME="$name" dch --newversion "$version$version_suffix" --distribution "$distribution" --force-distribution -- "$message"

if [ -x "$dir/exec.post" ]; then
SOURCE="$source" "$dir/exec.post"
fi

[ ! -e "$git_dir" ] || rm -rf "$git_dir"
)

main "$@"
build_indep "$pkg.dsc"
build_archdep "$pkg.dsc"
3 changes: 3 additions & 0 deletions build.containerfile
100644 → 100755
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@ COPY pkgs ./
RUN apt-get update && DEBIAN_FRONTEND=noninteractive apt-get install --no-install-recommends -y build-essential ca-certificates debhelper devscripts git sudo yq $(awk '{ print $1 }' pkgs)
RUN apt-mark hold $(awk '{ print $1 }' pkgs)
RUN gcc --print-search-dir && echo 'int main() { return 0; }' > main.c && gcc -o main main.c && ./main
COPY build_source /usr/local/bin/
COPY build_indep /usr/local/bin/
COPY build_archdep /usr/local/bin/
COPY build /usr/local/bin/
RUN find /tmp -mindepth 1 -delete
COPY --from=mini_sudo /usr/local/bin/sudo /usr/local/bin/sudo
Expand Down
29 changes: 29 additions & 0 deletions build_archdep
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
#!/usr/bin/env bash

set -exuo pipefail

exec 3>&1
exec 1>&2

main() (
dsc="$(realpath "$1")"
dpkg_arch="$(dpkg --print-architecture)"
dsc_arch="$(grep -oP '(?<=^Architecture: ).*' < "$dsc" | tr ' ' '\n')"

grep -P '^(linux-)?(any|'"$dpkg_arch"')$' <<< "$dsc_arch" || exit 0

sudo apt-get build-dep --no-install-recommends -y "$dsc"

dpkg-source --extract "$dsc" src
cd src
name="$(dpkg-parsechangelog --show-field Source)"
version="$(dpkg-parsechangelog --show-field Version)"
DEB_BUILD_OPTIONS="terse ${DEB_BUILD_OPTIONS-}" dpkg-buildpackage --no-sign --build=any
cd ..
rm -rf src
ls -lah

echo "${name}_${version}_${dpkg_arch}" >&3
)

main "$@"
28 changes: 28 additions & 0 deletions build_indep
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
#!/usr/bin/env bash

set -exuo pipefail

exec 3>&1
exec 1>&2

main() (
dsc="$(realpath "$1")"
dsc_arch="$(grep -oP '(?<=^Architecture: ).*' < "$dsc" | tr ' ' '\n')"

grep -P '^(linux-)?all$' <<< "$dsc_arch" || exit 0

sudo apt-get build-dep --no-install-recommends -y "$dsc"

dpkg-source --extract "$dsc" src
cd src
name="$(dpkg-parsechangelog --show-field Source)"
version="$(dpkg-parsechangelog --show-field Version)"
DEB_BUILD_OPTIONS="terse ${DEB_BUILD_OPTIONS-}" dpkg-buildpackage --no-sign --build=all
cd ..
rm -rf src
ls -lah

echo "${name}_${version}_all" >&3
)

main "$@"
143 changes: 143 additions & 0 deletions build_source
Original file line number Diff line number Diff line change
@@ -0,0 +1,143 @@
#!/usr/bin/env bash

set -exuo pipefail

exec 3>&1
exec 1>&2

main() (
debian_source=
while [ $# -gt 0 ]; do
case "$1" in
--debian-source)
debian_source="$2"
shift 2
;;
*)
break
;;
esac
done

source="$1"
shift

patches=()

while [ $# -gt 0 ]; do
patches+=("$1")
shift
done

if [[ "$source" = "git+"* ]]; then
git_source "${source#git+}"
else
apt_source "$source"
fi

if [ -n "$debian_source" ]; then
mkdir debian_src
cd debian_src
if [[ "$debian_source" = "git+"* ]]; then
git_source "${debian_source#git+}"
else
apt_source "$debian_source"
fi
rm -rf ../src/debian
mv src/debian ../src/
cd ..
rm -rf debian_src
fi

cd src

for patch in "${patches[@]}"; do
apply_patches "$patch"
done

name="$(dpkg-parsechangelog --show-field Source)"
version="$(dpkg-parsechangelog --show-field Version)"
version_orig="${version%-*}"
gzip < ../orig.tar > "../${name}_${version_orig}.orig.tar.gz"
rm ../orig.tar

dpkg-source --build .

cd ..
rm -rf src
ls -lah

echo "${name}_${version}" >&3
)

apt_source() (
apt-get source --only-source --download-only "$1"
orig=(*.orig.tar.*)
debian=(*.debian.tar.*)
dsc=(*.dsc)
auto_decompress "$orig" > orig.tar
mkdir src
tar -C src -x --strip-components 1 < orig.tar
auto_decompress "$debian" | tar -C src -xv
rm "$orig" "$debian" "$dsc"
)

git_source() (
IFS='#' read -r url ref <<< "$1"
git clone --bare --branch "$ref" --depth 1 "$url" src.git
GIT_DIR=src.git git archive --prefix src/ "$ref" > orig.tar
rm -rf src.git
tar -x < orig.tar
)

auto_decompress() (
case "${1##*.}" in
gz)
gzip -d < "$1"
;;
xz)
xz -d < "$1"
;;
*)
exit 1
;;
esac
)

apply_patches() (
git_dir="$(realpath $(mktemp -u ../patches.tmp.XXXX))"
if [[ "$1" = "git+"* ]]; then
IFS='#' read -r url ref <<< "${1#git+}"
git clone --branch "$ref" --depth 1 "$url" "$git_dir"
dir="$git_dir"
else
dir="$(cd .. && realpath "$1")"
fi

if [ -x "$dir/exec.pre" ]; then
SOURCE="$source" "$dir/exec.pre"
fi

if [ -f "$dir/patches/series" ]; then
while read -r patch; do
patch -p1 < "$dir/patches/$patch"
done < "$dir/patches/series"
fi

version="$(yq -r .version < "$dir/changelog_config.yaml")"
[ "$version" != null ] || version="$(dpkg-parsechangelog --show-field Version)"
email="$(yq -r .email < "$dir/changelog_config.yaml")"
name="$(yq -r .name < "$dir/changelog_config.yaml")"
distribution="$(yq -r .distribution < "$dir/changelog_config.yaml")"
version_suffix="$(yq -r .version_suffix < "$dir/changelog_config.yaml")"
message="$(yq -r .message < "$dir/changelog_config.yaml")"
DEBEMAIL="$email" DEBFULLNAME="$name" dch --newversion "$version$version_suffix" --distribution "$distribution" --force-distribution -- "$message"

if [ -x "$dir/exec.post" ]; then
SOURCE="$source" "$dir/exec.post"
fi

[ ! -e "$git_dir" ] || rm -rf "$git_dir"
)

main "$@"
3 changes: 3 additions & 0 deletions crossbuild.containerfile
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,9 @@ COPY --from=native /native /native
COPY setup_native ./
RUN [ "/native/bash", "-c", "PATH=/native:$PATH ./setup_native import $(awk '{ print $1 }' pkgs)" ]
RUN gcc --print-search-dir && echo 'int main() { return 0; }' > main.c && gcc -o main main.c && ./main
COPY build_source /usr/local/bin/
COPY build_indep /usr/local/bin/
COPY build_archdep /usr/local/bin/
COPY build /usr/local/bin/
RUN find /tmp -mindepth 1 -delete
COPY --from=mini_sudo /usr/local/bin/sudo /usr/local/bin/sudo
Expand Down

0 comments on commit 84d0d0d

Please sign in to comment.