various fixes, upgrade nfsroot to buster
[automated-distro-installer] / fai-redep
1 #!/bin/bash
2 # Copyright (C) 2019 Ian Kelling
3 # SPDX-License-Identifier: AGPL-3.0-or-later
4 set -eE -o pipefail
5 trap 'echo "$0:$LINENO:error: \"$BASH_COMMAND\" returned $?" >&2' ERR
6
7 readonly this_file="$(readlink -f -- "${BASH_SOURCE[0]}")"; cd "${this_file%/*}"
8
9 usage() {
10 cat <<EOF
11 usage: ${0##*/} [OPTIONS] [HOST]
12 Deploy fai config (the one in nfs) to HOST or default faiserver
13
14
15 -d DISTRO DISTRO for setting up fai class DESKTOP packages, for preinstalling stuff.
16 -t TARGET_HOST Copy only secrets for TARGET_HOST into the config space. Useful for virtual server
17 on hardware we don't control.
18 -h|--help Print help and exit
19
20 Note: uses paths specific to authors machine.
21 EOF
22 exit $1
23 }
24
25 ##### begin command line parsing ########
26
27 # ensure we can handle args with spaces or empty.
28 ret=0; getopt -T || ret=$?
29 [[ $ret == 4 ]] || { echo "Install util-linux for enhanced getopt" >&2; exit 1; }
30
31 temp=$(getopt -l help hd:t: "$@") || usage 1
32 eval set -- "$temp"
33 while true; do
34 case $1 in
35 -d) distro=$2; shift ;;
36 -t) target=$2; shift ;;
37 -h|--help) usage ;;
38 --) shift; break ;;
39 *) echo "$0: unexpected args: $*" >&2 ; usage 1 ;;
40 esac
41 shift
42 done
43 host=${1:-faiserver}
44
45 readonly host distro target
46
47 ##### end command line parsing ########
48
49 # i use faiserver as a dns alias, but ssh key is associated with
50 # a canonical hostname and we will have ssh warning spam unless we
51 # use it, so look it up just to avoid the warning spam.
52 faiserver_host=$(chost $host) || faiserver_host=$host
53
54 rsync -rlpt --delete --relative --exclude /fai/config/basefiles/ fai/config root@$faiserver_host:/srv
55
56 sudo rsync -a /root/.ssh/home.pub \
57 root@$faiserver_host:/srv/fai/config/files/root/.ssh/authorized_keys/STANDARD
58 # todo: automatically disable faiserver after a period so
59 # these files are not available.
60
61 if [[ $target ]]; then
62 if sudo test -e /q/root/shadow/$target; then
63 shadowfile=shadow/$target # empty otherwise
64 fi
65 sudo rsync -lpt --files-from=- /q/root root@$faiserver_host:/srv/fai/config/distro-install-common <<EOF
66 luks/$target
67 luks/host-$target
68 $shadowfile
69 EOF
70 else
71 sudo rsync -rlpt /q/root/shadow /q/root/luks root@$faiserver_host:/srv/fai/config/distro-install-common
72 fi
73
74 dirs=(/p/c/machine_specific/${target:-*}/filesystem/etc/ssh)
75 if [[ -e ${dirs[0]} ]]; then
76 rsync -rlpt --delete --relative ${dirs[@]} root@$faiserver_host:/srv/fai/config/distro-install-common
77 fi
78
79 . /a/bin/distro-setup/pkgs
80 pall+=($(/a/bin/buildscripts/emacs -p; /a/bin/distro-setup/distro-pkgs $distro))
81
82 printf "%s\n%s\n" "PACKAGES install" ${pall[*]} | \
83 ssh root@$faiserver_host dd of=/srv/fai/config/package_config/DESKTOP 2>/dev/null ||: # broken pipe
84
85
86 rsync -rplt --include '/*.gz' --exclude '/**' --delete-excluded $BASEFILE_DIR/ root@$faiserver_host:/srv/fai/config/basefiles/
87 ssh root@$faiserver_host bash <<'EOF'
88 set -eE -o pipefail
89 # make it the root because pxe-kexec only looks there.
90 # It wouldn't be too hard to change if we needed.
91 # We could also just dump things in /srv/tftp, but fai
92 # has some defaults, which I don't even use, which expect
93 # the other directory, so it's kind of a tossup, whatever.
94 sed -ri 's,^ *(TFTP_DIRECTORY=).*,\1"/srv/tftp/fai",' /etc/default/tftpd-hpa
95 systemctl restart tftpd-hpa
96
97 changed=false
98 f=/srv/fai/nfsroot/root/.ssh/known_hosts
99 install -d -m 700 /srv/fai/nfsroot/root/.ssh
100 # the known hosts entries that fai already sets up are like
101 # IP,HOSTNAME key_info...
102 # we are skipping the ip, because it doesn't block ssh
103 # with a prompt as long as you have the user supplied hostname,
104 # and i don't want to deal with getting it, it's not adding
105 # any important security in this case.
106 if ! grep -xFq "$line" $f &>/dev/null; then
107 changed=true
108 printf "%s\n" "$line" >>$f
109 fi
110
111 if ! modprobe nfsd &>/dev/null; then
112 # no apt-cache on maru debian, because we are low on space already
113 sed -i '/^ *APTPROXY=/d' /srv/fai/config/class/DEBIAN.var
114 # maru debian doesn't have loopback devs created
115 if ! losetup -f; then
116 shopt -s nullglob
117 x=(/dev/loop*)
118 minor=0
119 if (( ${#x[@]} )); then
120 minor=$(( ${x[-1]#/dev/loop} + 1 ))
121 fi
122 mknod -m660 /dev/loop$minor b 7 $minor
123 losetup -f
124 fi
125 # -B boo only iso, no nfsroot, no paritial miorr, no config space.
126 # -f = force, for overwriting
127 # -S = make squash image for http booting
128 # -d config space url, instead of putting it in the squash.img,
129 # this just makes it so that we don't have to regenerate the img
130 # when the config changes.
131 cd /srv/fai/config
132 tar czf /var/www/faiserver/html/config.tar.gz .
133 if $changed || [[ ! -e /var/www/faiserver/html/squash.img ]]; then
134 # note, on maru, selinux needs to be disabled in android before
135 # this will work.
136 mount
137 export debug=true
138 fai-cd -d http://faiserver:8080/config.tar.gz -f -M -S /var/www/faiserver/html/squash.img
139 mount
140 fi
141 fi
142 EOF