]> git.pld-linux.org Git - projects/cleanbuild.git/blob - cleanbuild-docker.sh
6a9ac30f73aa992efb74d72c56b5d448df6f3a38
[projects/cleanbuild.git] / cleanbuild-docker.sh
1 #!/bin/sh
2 set -eu
3
4 PROGRAM=${0##*/}
5
6 # defaults
7 : ${PACKAGE_NAME=''}
8 : ${NETWORKING=false}
9 : ${TRACING=false}
10 : ${TMPFS="4G"}
11
12 dir=$(pwd)
13 image=registry.gitlab.com/pld-linux/cleanbuild
14 topdir=$dir/rpm
15 home=/home/builder
16
17 die() {
18         echo >&2 "$0: $*"
19         exit 1
20 }
21
22 is_no() {
23         # Test syntax
24         if [ $# = 0 ]; then
25                 return 2
26         fi
27
28         case "$1" in
29         no|No|NO|false|False|FALSE|off|Off|OFF|N|n|0)
30                 # true returns zero
31                 return 0
32                 ;;
33         *)
34                 # false returns one
35                 return 1
36                 ;;
37         esac
38 }
39
40 tmpfs() {
41         if is_no "${TMPFS:-true}" || [ "$TMPFS" -le 0 ]; then
42                 return
43         fi
44
45         echo "--tmpfs $home/rpm/BUILD:rw,exec,nosuid,size=$TMPFS"
46 }
47
48 create_container() {
49         # cleanup first
50         docker kill $name >/dev/null 2>&1 || :
51         docker rm $name >/dev/null 2>&1 || :
52
53         install -d $topdir/logs
54
55         # start the container
56         docker run --name=$name -d \
57                 -w $home \
58                 -v $topdir:$home/rpm \
59                 -v $dir:$home/cleanbuild \
60                 -v $dir/cache/poldek:/var/cache/poldek \
61                 -v $dir/cache/ccache/$PACKAGE_NAME:$home/.ccache \
62                 $(tmpfs) \
63                 $image
64
65         # set the homedir
66         docker exec --user=root -w / $name usermod -d $home builder
67
68         # these paths need to be accessible for builder
69         docker exec --user=root -w / $name sh -c "cd $home && chown builder:builder rpm rpm/logs rpm/BUILD .ccache"
70
71         if [ ! -d $topdir/rpm-build-tools ]; then
72                 docker exec $name builder --init-rpm-dir
73         fi
74 }
75
76 package_prepare() {
77         # fetch sources and install deps
78         if [ -d $topdir/packages/$PACKAGE_NAME ]; then
79                 # chown, as it might be different owner (root) modified outside container
80                 docker exec --user=root -w / $name chown -R builder:builder $home/rpm/packages/$PACKAGE_NAME
81         fi
82         docker exec $name builder -g $PACKAGE_NAME
83
84         # prevent network access like pld builders do
85         $NETWORKING || docker exec --user=root -w / $name setfacl -m u:builder:--- /etc/resolv.conf
86
87         git_tag=$(GIT_DIR=$topdir/packages/$PACKAGE_NAME/.git git describe --tags --always)
88         buildlog=rpm/logs/${git_tag#auto/*/}.log
89 }
90
91 package_build() {
92         while true; do
93                 # install deps
94                 docker exec $name builder -g -nn -R $PACKAGE_NAME
95                 # remove .la dependencies
96                 docker exec --user=root -w / $name $home/cleanbuild/cleanup-la
97                 # reset findunusedbr state after deps install
98                 docker exec --user=root -w / $name $home/cleanbuild/findunusedbr -c / $home/rpm/packages/$PACKAGE_NAME/$PACKAGE_NAME.spec
99
100                 # actual build
101                 docker exec $name cleanbuild/teeboth $buildlog builder -nn -bb $PACKAGE_NAME --define '__spec_clean_body %{nil}' && rc=$? || rc=$?
102
103                 findbr=$PACKAGE_NAME.findbr.log
104                 builddir=$(docker exec $name sh -c 'test ! -d rpm/BUILD/* || echo rpm/BUILD/*')
105                 if [ -z "$builddir" ]; then
106                         echo >&2 "No build dir. Build failed?"
107                         exit 6
108                 fi
109                 # need root to run poldek
110                 docker exec --user=root -w / $name sh -c "cd $home && cleanbuild/findbr $builddir $buildlog" > $findbr
111
112                 installed_something=false
113                 while read pkg msg; do
114                         ./addbr rpm/packages/$PACKAGE_NAME/$PACKAGE_NAME.spec "$pkg" "$msg" || continue
115                         installed_something=true
116                 done < $findbr
117                 rm -f $findbr
118
119                 # go for another try
120                 $installed_something && continue
121
122                 docker exec --user=root -w / $name $home/cleanbuild/findunusedbr -c / $home/rpm/packages/$PACKAGE_NAME/$PACKAGE_NAME.spec
123
124                 if [ $rc -eq 0 ]; then
125                         # finished ok, cleanup
126                         docker kill $name >/dev/null && docker rm $name >/dev/null || :
127                 fi
128
129                 # propagate error
130                 exit $rc
131         done
132 }
133
134 parse_options() {
135         local t
136         t=$(getopt -o 'x' --long 'network,no-tmpfs,notmpfs,tmpfs:' -n "$PROGRAM" -- "$@")
137         [ $? != 0 ] && exit $?
138         eval set -- "$t"
139
140         while :; do
141                 case "$1" in
142                 -x)
143                         TRACING=true
144                         ;;
145                 --network)
146                         NETWORKING=true
147                         ;;
148                 --no-tmpfs|--notmpfs)
149                         TMPFS=false
150                         ;;
151                 --tmpfs)
152                         shift
153                         TMPFS="$1"
154                         ;;
155                 --)
156                         shift
157                         break
158                         ;;
159                 *)
160                         die "Internal error: [$1] not recognized!"
161                         ;;
162                 esac
163                 shift
164         done
165
166         test "$#" -eq 1 || die "package not specified or excess arguments"
167         PACKAGE_NAME="${1%.spec}"
168 }
169
170 main() {
171         parse_options "$@"
172
173         $TRACING && set -x
174         local name="cleanbuild-$PACKAGE_NAME"
175         create_container
176         package_prepare
177         package_build
178 }
179
180 main "$@"
This page took 0.086393 seconds and 2 git commands to generate.