diff --git a/scripts/bee-mxqsub b/scripts/bee-mxqsub index a1c28212e..d9df882db 100755 --- a/scripts/bee-mxqsub +++ b/scripts/bee-mxqsub @@ -59,6 +59,9 @@ buildroot= # like 0, so beerc picks bee's default for root, /src/mariux/beeroot, which is # where the artifacts belong. Pass --repository to build into a private tree. repository= +# beesh --fakeroot runs only the install and packaging under fakeroot, and +# configures and builds with the real UID; see the job phase. Without it, the +# whole of beesh runs under fakeroot. use_fakeroot=1 keep_buildroot=0 # The staging directory has to be readable from the cluster nodes, so it must @@ -112,7 +115,9 @@ Options: pull a bee-file away from the running job (default: /scratch/tmp/bee-mxqsub-\$USER) --no-stage build from the bee-files in the repository - --fakeroot call beesh under fakeroot (default) + --fakeroot install and package under fakeroot, configure and + build without it if beesh has --fakeroot, else + call all of beesh under fakeroot (default) --no-fakeroot call beesh without fakeroot --overlay install each package into an overlay, so that the following bee-files find it, and build in a sandbox @@ -410,11 +415,6 @@ if (( run_job )); then echo "=== buildroot: ${buildroot}" echo "=== repository: ${repository:-}" echo "=== makeflags: ${makeflags}" - if (( use_fakeroot )); then - echo "=== fakeroot: yes" - else - echo "=== fakeroot: no" - fi if (( overlay )); then echo "=== overlay: ${overlay_root} over ${overlay_dirs[*]}" else @@ -437,6 +437,24 @@ if (( run_job )); then export "${assignment?}" done + # Under fakeroot, the stat, chmod and chown calls of every build process + # go through the one faked daemon, which made the Firefox build take 17:37 + # instead of 11:34. Only installing and packaging need the fake root, and + # beesh --fakeroot confines it to them. Older beesh versions lack the + # option and get the whole of beesh run under fakeroot as before. Ask + # only now, as --env may have set PATH to another bee. + beesh_fakeroot=0 + if (( use_fakeroot )); then + if beesh --help 2>/dev/null | grep -q -e '--fakeroot'; then + beesh_fakeroot=1 + echo "=== fakeroot: install and packaging only (beesh --fakeroot)" + else + echo "=== fakeroot: all of beesh (beesh lacks --fakeroot)" + fi + else + echo "=== fakeroot: no" + fi + # mxqd hands a job the usual soft limit of 1024 open files while the hard # limit is higher, and raising the soft limit to the hard one needs no # privileges. Every process of every build inherits it, fuse-overlayfs @@ -500,6 +518,17 @@ if (( run_job )); then else config=$(bee --print-config) fi + # beesh --fakeroot reads the configuration with the real UID, for which + # beerc picks the private repository below ~/.local and the user's + # package database and cache instead of root's. Hand it the paths of + # root's configuration, as a beesh running under fakeroot would use. + if (( beesh_fakeroot )) && ! (( overlay )); then + for var in BEE_REPOSITORY_PREFIX BEE_METADIR BEE_CACHEDIR; do + value=$(sed -n "s/^${var}=//p" <<< "${config}") + [ -n "${value}" ] || die "cannot read ${var} from bee --print-config" + export "${var}=${value}" + done + fi pkgdir=$(sed -n 's/^BEE_PKGDIR=//p' <<< "${config}") [ -n "${pkgdir}" ] || die "cannot read BEE_PKGDIR from bee --print-config" mkdir -p "${pkgdir}" 2>/dev/null @@ -539,7 +568,9 @@ if (( run_job )); then # A .be0/.bee is a beesh script: its mee_* hooks are called by # beesh, so running it with plain bash only defines the functions # and builds nothing. - if (( use_fakeroot )); then + if (( beesh_fakeroot )); then + ${sandbox[@]+"${sandbox[@]}"} beesh --fakeroot "${beesh_args[@]}" "${beefile}" + elif (( use_fakeroot )); then ${sandbox[@]+"${sandbox[@]}"} fakeroot beesh "${beesh_args[@]}" "${beefile}" else ${sandbox[@]+"${sandbox[@]}"} beesh "${beesh_args[@]}" "${beefile}"