Project

General

Profile

FSFVM ยป create-vm-ceph-luks.sh

Denis 'GNUtoo' Carikli, 02/24/2020 08:15 PM

 
1
#!/bin/bash
2
# Script managed by Ansible, do not edit
3
#
4
#    Copyright (C) 2017  Free Software Foundation
5
#    Copyright (C) 2017  Ruben Rodriguez <ruben@fsf.org>
6
#
7
#    This program is free software; you can redistribute it and/or modify
8
#    it under the terms of the GNU General Public License as published by
9
#    the Free Software Foundation; either version 3 of the License, or
10
#    (at your option) any later version.
11
#
12
#    This program is distributed in the hope that it will be useful,
13
#    but WITHOUT ANY WARRANTY; without even the implied warranty of
14
#    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15
#    GNU General Public License for more details.
16
#
17
#    You should have received a copy of the GNU General Public License
18
#    along with this program; if not, write to the Free Software
19
#    Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301 USA
20
#
21
# https://dsa.debian.org/howto/install-kvm/
22
# dependencies
23
# apt install --no-install-recommends libvirt-dev kvm virtinst xfsprogs pwgen
24

    
25
set -e
26
export LANG=C
27
export LC_ALL=C
28

    
29
if [ $# -lt 4 ]; then
30
  echo "Usage: $0 hostname.foo.bar disksize(MB) ramsize(MB) cpucount [distro_release_codename]"
31
  echo "Example: $0 www.gnu.org 5000 512 2 flidas"
32
  echo "supported codenames are flidas, belenos and stretch"
33
  exit 1
34
fi
35

    
36
HOST=$1
37
HOSTSHORT=$(echo $HOST | sed 's/\..*//')
38
POOL=rbd
39

    
40
if ! getent hosts $HOST > /dev/null; then
41
  echo "Could not resolve the hostname to an IP. Add it to the DNS first!"
42
  exit 1
43
fi
44

    
45
IP=$(getent ahosts $HOST |grep ^209.*RAW| sed 's/ .*//')
46
IP6=$(getent ahosts $HOST |grep ^2001.*RAW| sed 's/ .*//')
47
NIC=eth0
48
GATEWAY=209.51.188.1
49
GATEWAY6=2001:470:142::1
50

    
51
SIZE=$2
52
RAM=$3
53
CPUS=$4
54

    
55
RELEASE=flidas
56
[ 1${5}1 != 11 ] && RELEASE=$5
57
case $RELEASE in
58
  flidas|belenos)
59
    archive=http://us.archive.trisquel.info/trisquel
60
    linux_pkg=linux-image-virtual
61
    ;;
62
  stretch)
63
    archive=http://deb.debian.org/debian/
64
    linux_pkg=linux-image-amd64
65
    ;;
66
  *)
67
    echo "$0: error: unknown release"
68
    exit 1
69
    ;;
70
esac
71

    
72
rbd create $HOST --size $SIZE -p $POOL --image-format=2 --image-feature exclusive-lock,object-map,fast-diff,layering
73
DEVICE=$(rbd-nbd map $HOST)
74

    
75
TARGET=$(mktemp -d)
76
KEYFILE=/dev/shm/keyfile
77
pwgen 128 -s -1 | xargs echo -n > $KEYFILE
78
echo YES | cryptsetup luksFormat -y --cipher aes-xts-plain64 --hash sha256 --use-urandom --key-size 256  $DEVICE --key-file=$KEYFILE
79
cryptsetup luksOpen $DEVICE $HOST-crypt0 --key-file=$KEYFILE
80
mkfs.xfs -i size=2048 -s size=4096 -d agcount=4 /dev/mapper/$HOST-crypt0
81
mount /dev/mapper/$HOST-crypt0 $TARGET -o discard,noatime,nodiratime
82

    
83
if ! [ -d /srv/debootstrap-cache/${RELEASE} ] ; then
84
  mkdir -p /srv/debootstrap-cache/${RELEASE}
85
  eatmydata debootstrap --exclude=resolvconf ${RELEASE} /srv/debootstrap-cache/${RELEASE} $archive
86
fi
87
eatmydata cp -a /srv/debootstrap-cache/${RELEASE}/* $TARGET
88

    
89
mknod $TARGET/dev/sda b 8 0
90
mkdir $TARGET/dev/mapper
91
cp -av $(readlink -f /dev/mapper/${HOST}-crypt0) $TARGET/dev/mapper/${HOST}-crypt0
92
cat << EOF > $TARGET/boot/keyscript.sh
93
#!/bin/sh
94
echo -n $(cat $KEYFILE)
95
EOF
96
chmod 700 $TARGET/boot/keyscript.sh $TARGET/boot/
97

    
98
cat << EOF > /dev/shm/grub.cfg
99
cryptomount -k /keyfile hd0
100
linux (crypto0)/vmlinuz root=/dev/mapper/${HOST}-crypt0 ro elevator=noop console=tty0 console=ttyS0,115200 biosdevname=0 net.ifnames=0
101
initrd (crypto0)/initrd.img
102
boot
103
EOF
104
dd if=/dev/zero of=/dev/shm/memdisk bs=1M count=1
105
mkfs.ext2 /dev/shm/memdisk
106
mkdir /dev/shm/memdiskmount || true
107
mount /dev/shm/memdisk /dev/shm/memdiskmount
108
cp $KEYFILE /dev/shm/memdiskmount/
109
umount /dev/shm/memdiskmount
110
grub-mkimage -v -C xz -c /dev/shm/grub.cfg  -O i386-pc  -o /var/lib/libvirt/images/grub-$HOST.bin  biosdisk ext2 linux xfs normal luks help crypto cryptodisk zfscrypt gcry_sha512 gcry_sha256 echo cat memdisk -m /dev/shm/memdisk
111

    
112
cat << EOF > $TARGET/etc/fstab
113
# <file system> <mount point>   <type>  <options>       <dump>  <pass>
114
proc            /proc           proc    defaults        0       0
115
/dev/mapper/${HOST}-crypt0 / xfs noatime,nodiratime,sunit=8192,swidth=8192 0 1
116
EOF
117

    
118
echo "${HOST}-crypt0 /dev/sda none luks,discard,keyscript=/boot/keyscript.sh" > $TARGET/etc/crypttab
119

    
120
mount -t proc none $TARGET/proc
121
mount -o bind /dev $TARGET/dev
122

    
123
case $RELEASE in
124
  flidas|belenos)
125
    cat << EOF > $TARGET/etc/apt/sources.list
126
deb http://us.archive.trisquel.info/trisquel/ ${RELEASE} main
127
deb http://us.archive.trisquel.info/trisquel/ ${RELEASE}-updates main
128
deb http://archive.trisquel.info/trisquel ${RELEASE}-security main
129
EOF
130
    ;;
131
  stretch)
132
    cat << EOF > $TARGET/etc/apt/sources.list
133
deb http://http.us.debian.org/debian ${RELEASE} main
134
deb http://security.debian.org/ ${RELEASE}/updates main
135
deb http://http.us.debian.org/debian ${RELEASE}-updates main
136
EOF
137
    ;;
138
esac
139

    
140
echo "nameserver 209.51.188.16" > $TARGET/etc/resolv.conf
141

    
142
# For disabling upstart during initial setup
143
cat << EOF > $TARGET/usr/sbin/policy-rc.d
144
#!/bin/sh
145
exit 101
146
EOF
147
chmod 755 $TARGET/usr/sbin/policy-rc.d
148

    
149
cp /usr/lib/x86_64-linux-gnu/libeatmydata.so $TARGET/usr/lib/x86_64-linux-gnu/libeatmydata.so
150
DEBIAN_FRONTEND=noninteractive eatmydata chroot $TARGET apt-get update
151
# busybox-static needed for debian stretch
152
DEBIAN_FRONTEND=noninteractive eatmydata chroot $TARGET apt-get dist-upgrade --force-yes -y -o Dpkg::Options::="--force-confnew"
153
DEBIAN_FRONTEND=noninteractive eatmydata chroot $TARGET apt-get install --force-yes -y --no-install-recommends $linux_pkg ssh acpid busybox-static xfsprogs cryptsetup python3-apt python
154

    
155
rm $TARGET/usr/sbin/policy-rc.d
156

    
157
# Set root password
158
ROOTPW=$(pwgen 12 -s -1)
159
echo root:$ROOTPW | chroot $TARGET chpasswd
160

    
161
cat << EOF > $TARGET/etc/init/ttykvm.conf
162
# ttykvm - getty
163
#
164
# This service maintains a getty on tty1 from the point the system is
165
# started until it is shut down again.
166

    
167
start on stopped rc RUNLEVEL=[2345]
168

    
169
stop on runlevel [!2345]
170

    
171
respawn
172
exec /sbin/getty -8 115200 ttyS0 xterm
173
EOF
174

    
175
cat << EOF > $TARGET/etc/network/interfaces
176
# The loopback network interface
177
auto lo
178
iface lo inet loopback
179

    
180
# The primary network interface
181
auto $NIC
182
iface $NIC inet static
183
  address $IP
184
  gateway $GATEWAY
185
  netmask 255.255.255.0
186
  hostname $HOST
187

    
188
iface eth0 inet6 static
189
  pre-up echo 0 > /proc/sys/net/ipv6/conf/eth0/accept_dad
190
  address $IP6
191
  netmask 48
192
  gateway $GATEWAY6
193
  hostname $HOST
194
EOF
195

    
196
cat << EOF  > $TARGET/etc/resolv.conf
197
domain fsf.org
198
search fsf.org
199
nameserver 209.51.188.16
200
EOF
201

    
202
echo $HOST > $TARGET/etc/hostname
203

    
204
cat << EOF  > $TARGET/etc/hosts
205
127.0.0.1       localhost
206
$IP    $HOST $HOSTSHORT
207

    
208
::1     localhost ip6-localhost ip6-loopback
209
fe00::0 ip6-localnet
210
ff00::0 ip6-mcastprefix
211
ff02::1 ip6-allnodes
212
ff02::2 ip6-allrouters
213
ff02::3 ip6-allhosts
214
EOF
215

    
216
mkdir $TARGET/root/.ssh
217
echo 'from="74.94.156.210" ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIImP7xYaUTag4/cNyy8W//T4SZyD3bFtjSac3U7t41bh Ansible' > $TARGET/root/.ssh/authorized_keys
218

    
219
rm $TARGET/usr/lib/x86_64-linux-gnu/libeatmydata.so
220
umount $TARGET/proc
221
umount $TARGET/dev
222
umount $TARGET
223
cryptsetup luksClose /dev/mapper/${HOST}-crypt0
224
rbd-nbd unmap $DEVICE
225

    
226
cat << EOF > /tmp/disk.xml
227
    <disk type='network' device='disk'>
228
      <driver name='qemu' cache='writeback' discard='unmap' type='raw'  />
229
      <auth username='libvirt'>
230
        <secret type='ceph' uuid='dc8e8240-15b4-47ae-896b-6632aec8103e'/>
231
      </auth>
232
      <source protocol='rbd' name='$POOL/$HOST'>
233
        <host name='cephmon1' port='6789'/>
234
        <host name='cephmon2' port='6789'/>
235
        <host name='cephmon3' port='6789'/>
236
      </source>
237
      <target dev='sda' bus='scsi'/>
238
    </disk>
239
EOF
240

    
241
virt-install --name $HOST  --graphics vnc --boot kernel=/var/lib/libvirt/images/grub-$HOST.bin  --network type=direct,source=macvtap-bond0,source_mode=bridge,model=virtio --disk none --noautoconsole --controller scsi,model=virtio-scsi --cpu host --vcpus=${CPUS} --memory=$RAM,hugepages=true --cpuset=auto
242
virsh attach-device $HOST /tmp/disk.xml --persistent
243
virsh dumpxml $HOST > /tmp/tmp.xml
244
#sed "1s#># xmlns:qemu=\'http://libvirt.org/schemas/domain/qemu/1.0'>#; s#</domain>#<qemu:commandline><qemu:arg value='-set'/><qemu:arg value='device.scsi0-0-0-0.min_io_size=4194304'/><qemu:arg value='-set'/><qemu:arg value='device.scsi0-0-0-0.opt_io_size=4194304'/></qemu:commandline></domain>#" /tmp/tmp.xml -i
245
sed "/virtio-scsi/a <driver queues='$CPUS'/>" /tmp/tmp.xml -i
246
virsh destroy $HOST
247
# This allows ipv6 to do neighbour discovery https://superuser.com/questions/944678/how-to-configure-macvtap-to-let-it-pass-multicast-packet-correctly
248
#sed "s_<interface type='direct.*_<interface type='direct' trustGuestRxFilters='yes'>_" -i /tmp/tmp.xml
249
virsh create /tmp/tmp.xml
250

    
251
echo "
252

    
253
Created new virtual machine $HOST
254

    
255
ROOT PASSWORD	: $ROOTPW
256
LUKS KEY	: `cat $KEYFILE`
257
IP		: $IP
258
RBD IMAGE	: $POOL/$HOST
259
SIZE		: $SIZE
260
RAM SIZE	: $RAM
261
"
262

    
263
rm /tmp/tmp.xml
264
rm -f $KEYFILE
265
rm -rf /dev/shm/memdisk* /dev/shm/grub.cfg
266

    
267
exit 0
    (1-1/1)