summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLars Wirzenius <liw@liw.fi>2018-08-29 16:02:55 +0300
committerLars Wirzenius <liw@liw.fi>2018-08-29 19:44:52 +0300
commit1dfe146d026ec59c25e6f3daf52ba680e0ffb529 (patch)
tree2ab14896fec59c819943d9865016273676119feb
parent62d0a8b089bf58c88811b2a668543f2bf88983d1 (diff)
downloadvmdb2-1dfe146d026ec59c25e6f3daf52ba680e0ffb529.tar.gz
Add: lvm2, luks plugins
-rw-r--r--NEWS2
-rw-r--r--lvm2.lukskey1
-rw-r--r--lvm2.vmdb69
-rw-r--r--vmdb/plugins/grub_plugin.py6
-rw-r--r--vmdb/plugins/luks_plugin.py87
-rw-r--r--vmdb/plugins/lvm2_plugin.py80
-rw-r--r--without-tests1
7 files changed, 246 insertions, 0 deletions
diff --git a/NEWS b/NEWS
index 935cee3..eeb8f5c 100644
--- a/NEWS
+++ b/NEWS
@@ -28,6 +28,8 @@ Version 0.13.2+git, not yet released
chroot, overwriting what the tarball has. This allows vmdb2 to work
with a tarball generated in a different network location.
+* Add plugins for doing full-disk encryption via cryptsetup, and LVM2.
+
Version 0.13.2, released 2018-05-06
------------------------------------
diff --git a/lvm2.lukskey b/lvm2.lukskey
new file mode 100644
index 0000000..9f592eb
--- /dev/null
+++ b/lvm2.lukskey
@@ -0,0 +1 @@
+hunter2
diff --git a/lvm2.vmdb b/lvm2.vmdb
new file mode 100644
index 0000000..284117b
--- /dev/null
+++ b/lvm2.vmdb
@@ -0,0 +1,69 @@
+# This is a sample VMDB2 input file to specify a simple
+# system that boots on a PC with BIOS. Uses LVM2.
+
+steps:
+ - mkimg: "{{ image }}"
+ size: 4G
+
+ - mklabel: msdos
+ device: "{{ image }}"
+
+ - mkpart: primary
+ device: "{{ image }}"
+ start: 1M
+ end: 100M
+ tag: /boot
+
+ - mkpart: primary
+ device: "{{ image }}"
+ start: 100M
+ end: 2G
+ tag: /rootpv
+
+ - cryptsetup: /rootpv
+ tag: rootpv_crypt
+ key-cmd: echo lvm2.lukskey
+
+ - vgcreate: rootvg
+ physical:
+ - rootpv_crypt
+
+ - lvcreate: rootvg
+ name: rootfs
+ size: 1G
+
+ - mkfs: ext2
+ partition: /boot
+
+ - mkfs: ext4
+ partition: rootfs
+
+ - mount: /boot
+
+ - mount: rootfs
+
+ - unpack-rootfs: rootfs
+
+ - debootstrap: stretch
+ mirror: http://deb.debian.org/debian
+ target: rootfs
+ unless: rootfs_unpacked
+
+ - apt: install
+ packages:
+ - linux-image-amd64
+ tag: rootfs
+ unless: rootfs_unpacked
+
+ - cache-rootfs: rootfs
+ unless: rootfs_unpacked
+
+ - chroot: rootfs
+ shell: |
+ sed -i '/^root:[^:]*:/s//root::/' /etc/passwd
+ echo pc-vmdb2 > /etc/hostname
+
+ - grub: bios
+ tag: rootfs
+ image-dev: "{{ image }}"
+ console: serial
diff --git a/vmdb/plugins/grub_plugin.py b/vmdb/plugins/grub_plugin.py
index d5ffd3c..0025011 100644
--- a/vmdb/plugins/grub_plugin.py
+++ b/vmdb/plugins/grub_plugin.py
@@ -161,6 +161,7 @@ class GrubStepRunner(vmdb.StepRunnerInterface):
])
self.set_grub_cmdline_config(chroot, kernel_params)
+ self.add_grub_crypto_disk(chroot)
if console == 'serial':
self.add_grub_serial_console(chroot)
@@ -255,3 +256,8 @@ class GrubStepRunner(vmdb.StepRunnerInterface):
f.write('GRUB_TERMINAL=serial\n')
f.write('GRUB_SERIAL_COMMAND="serial --speed=115200 --unit=0 '
'--word=8 --parity=no --stop=1"\n')
+
+ def add_grub_crypto_disk(self, chroot):
+ filename = self.chroot_path(chroot, '/etc/default/grub')
+ with open(filename, 'a') as f:
+ f.write('GRUB_ENABLE_CRYPTODISK=y\n')
diff --git a/vmdb/plugins/luks_plugin.py b/vmdb/plugins/luks_plugin.py
new file mode 100644
index 0000000..7d8ed3f
--- /dev/null
+++ b/vmdb/plugins/luks_plugin.py
@@ -0,0 +1,87 @@
+# Copyright 2018 Lars Wirzenius
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
+#
+# =*= License: GPL-3+ =*=
+
+
+
+import logging
+import os
+import tempfile
+
+import cliapp
+
+import vmdb
+
+
+class LuksPlugin(cliapp.Plugin):
+
+ def enable(self):
+ self.app.step_runners.add(CryptsetupStepRunner())
+
+
+class CryptsetupStepRunner(vmdb.StepRunnerInterface):
+
+ def get_required_keys(self):
+ return ['cryptsetup']
+
+ def run(self, step, settings, state):
+ underlying = step['cryptsetup']
+ crypt_name = step['tag']
+
+ state.tmp_key_file = None
+ key_file = step.get('key-file')
+ key_cmd = step.get('key-cmd')
+ if key_file is None and key_cmd is None:
+ raise Exception(
+ 'cryptsetup step MUST define one of key-file or key-cmd')
+
+ if key_file is None:
+ output = vmdb.runcmd(['sh', '-c', key_cmd])
+ output = output.decode('UTF-8')
+ key = output.splitlines()[0]
+ fd, key_file = tempfile.mkstemp()
+ state.tmp_key_file = key_file
+ os.close(fd)
+ open(key_file, 'w').write(key)
+
+ dev = state.tags.get_dev(underlying)
+ if dev is None:
+ for t in state.tags.get_tags():
+ logging.debug(
+ 'tag %r dev %r mp %r', t, state.tags.get_dev(t),
+ state.tags.get_mount_point(t))
+ assert 0
+
+ vmdb.runcmd(['cryptsetup', 'luksFormat', dev, key_file])
+ vmdb.runcmd(
+ ['cryptsetup', 'open', '--type', 'luks', '--key-file', key_file, dev,
+ crypt_name])
+
+ crypt_dev = '/dev/mapper/{}'.format(crypt_name)
+ assert os.path.exists(crypt_dev)
+ state.tags.append(crypt_name)
+ state.tags.set_dev(crypt_name, crypt_dev)
+
+ def teardown(self, step, settings, state):
+ x = state.tmp_key_file
+ if x is not None and os.path.exists(x):
+ os.remove(x)
+
+ underlying = step['cryptsetup']
+ crypt_name = step['tag']
+
+ crypt_dev = '/dev/mapper/{}'.format(crypt_name)
+ vmdb.runcmd(['cryptsetup', 'close', crypt_dev])
diff --git a/vmdb/plugins/lvm2_plugin.py b/vmdb/plugins/lvm2_plugin.py
new file mode 100644
index 0000000..405398c
--- /dev/null
+++ b/vmdb/plugins/lvm2_plugin.py
@@ -0,0 +1,80 @@
+# Copyright 2018 Lars Wirzenius
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
+#
+# =*= License: GPL-3+ =*=
+
+
+
+import os
+
+import cliapp
+
+import vmdb
+
+
+class Lvm2Plugin(cliapp.Plugin):
+
+ def enable(self):
+ self.app.step_runners.add(VgcreateStepRunner())
+ self.app.step_runners.add(LvcreateStepRunner())
+
+
+class VgcreateStepRunner(vmdb.StepRunnerInterface):
+
+ def get_required_keys(self):
+ return ['vgcreate', 'physical']
+
+ def run(self, step, settings, state):
+ vgname = self.get_vg(step)
+ physical = self.get_pv(step, state)
+
+ for phys in physical:
+ vmdb.runcmd(['pvcreate', phys])
+ vmdb.runcmd(['vgcreate', vgname] + physical)
+
+ def teardown(self, step, settings, state):
+ vgname = self.get_vg(step)
+ physical = self.get_pv(step, state)
+
+ vmdb.runcmd(['vgremove', '--force', vgname])
+ for phys in physical:
+ vmdb.runcmd(['pvremove', phys])
+
+ def get_vg(self, step):
+ return step['vgcreate']
+
+ def get_pv(self, step, state):
+ return [
+ state.tags.get_dev(tag)
+ for tag in step['physical']
+ ]
+
+
+class LvcreateStepRunner(vmdb.StepRunnerInterface):
+
+ def get_required_keys(self):
+ return ['lvcreate']
+
+ def run(self, step, settings, state):
+ vgname = step['lvcreate']
+ lvname = step['name']
+ size = step['size']
+
+ vmdb.runcmd(['lvcreate', '--name', lvname, '--size', size, vgname])
+
+ lvdev = '/dev/{}/{}'.format(vgname, lvname)
+ assert os.path.exists(lvdev)
+ state.tags.append(lvname)
+ state.tags.set_dev(lvname, lvdev)
diff --git a/without-tests b/without-tests
index 49d0e5d..ce34a61 100644
--- a/without-tests
+++ b/without-tests
@@ -13,6 +13,7 @@ vmdb/plugins/echo_plugin.py
vmdb/plugins/error_plugin.py
vmdb/plugins/grub_plugin.py
vmdb/plugins/kernel_plugin.py
+vmdb/plugins/lvm2_plugin.py
vmdb/plugins/mkfs_plugin.py
vmdb/plugins/mkimg_plugin.py
vmdb/plugins/mount_plugin.py