Add Boot RAID hint
[linux_from_scratch_hints.git] / Root_FS_on_RAID+encryption+LVM.txt
blobaa6f1cbf000fda05aaafb8f4358e4eab39ffc9f0
1 AUTHOR: Bryan Kadzban <bryan at linuxfromscratch dot org>
3 DATE: 2009-09-25
5 LICENSE:
6 Creative Commons Attribution-Share Alike 3.0 United States
7 (http://creativecommons.org/licenses/by-sa/3.0/us/)
9 SYNOPSIS: LFS on RAID, dm-crypt, and/or LVM2
11 DESCRIPTION:
12 This hint explains how to build an LFS system capable of booting most RAID, most
13 dm-crypt, and most LVM2 setups.  It allows you to use dmraid (most "RAID" add-on
14 boards), and/or Linux kernel "md" RAID.  It also allows you to encrypt the RAID
15 array, and use LVM2 on top of the encryption.  The rootfs can then be a logical
16 volume.
18 Any of these transformations can be omitted, but the transformations must be
19 layered in this order.  It is worth noting explicitly that this hint does not
20 cover encrypting a single logical volume (encryption after LVM); it only covers
21 encrypting the entire PV.
23 PREREQUISITES:
24 On the host:
26 - LVM2 userspace tools, if required.
27 - dmraid, if required.
28 - mdadm, if required.
29 - LUKS-capable cryptsetup, if required.
30 - Also all dependencies of the above packages.
32 For the LFS system:
34 Required:
36 - Sources for LVM2 userspace tools (with device-mapper): at least version
37   2.02.53.  Note that all the other packages require device-mapper, so you will
38   need the LVM2 package even if you don't plan on using LVM.
40   http://sourceware.org/lvm2/
41   ftp://sources.redhat.com/pub/lvm2/LVM2.2.02.53.tgz
43 - Patch for LVM2 udev rules, to make them work better with udev in LFS.
45   http://www.linuxfromscratch.org/patches/downloads/lvm2/LVM2-2.02.53-fix_udev_rules-1.patch
47 - Sources for lfs-initramfs, newest stable version.
49   http://www.linuxfromscratch.org/~bryan/lfs-initramfs-1.0.tar.bz2
51 Optional (depends on configuration):
53 - dmraid sources: newest stable version.
55   http://people.redhat.com/heinzm/sw/dmraid/src/
56   http://people.redhat.com/heinzm/sw/dmraid/src/dmraid-1.0.0.rc15.tar.bz2
58 - mdadm sources: newest stable version.
60   http://neil.brown.name/blog/mdadm
61   http://www.kernel.org/pub/linux/utils/raid/mdadm/mdadm-3.0.tar.bz2
63 - LUKS-capable cryptsetup sources: newest stable version.
65   http://code.google.com/p/cryptsetup/
66   http://cryptsetup.googlecode.com/files/cryptsetup-1.0.7.tar.bz2
68   - You will need popt for cryptsetup: latest stable version.
69     http://www.linuxfromscratch.org/blfs/view/svn/general/popt.html
71 HINT:
73 0. Preface
75 Throughout this hint, individual steps are annotated according to which sets of
76 transformations require them.  [dmr] denotes dmraid; [mdr] denotes md-raid;
77 [enc] denotes encryption, and [lvm] denotes LVM2.  Multiple transformations per
78 note are comma-separated.
80 Steps are grouped according to what portion of the book they apply to.  A note
81 precedes each group of steps, offset by lots of = characters.
83 Also note that the only dmraid setup supported is RAID1.  Although dmraid
84 probably supports RAID0/RAID5 if your particular RAID BIOS does, grub does not.
85 If grub cannot read the /boot partition, you will not be able to boot.  If you
86 have another single disk, you can put /boot on that disk, of course.  Most of
87 this hint should still work in that case, but that setup is untested.
89 1. [dmr,mdr,enc,lvm] Decide on a disk layout
91 dmraid arrays are most often composed of full disks.  md RAID can be composed of
92 either disks, or partitions (but see above: due to grub support, only partitions
93 are supported here).  dm-crypt can handle any source block device, as can LVM.
95 ===============================================================================
96   The following steps apply at section 2.2 of the LFS book: "Creating a New
97   Partition".  Follow them *instead of* the instructions in that section of the
98   book, until the next ==-delimited note.
99 ===============================================================================
101 2. [dmr] Build the array
103 Build your array according to whatever process your BIOS uses.  This will write
104 out the RAID signature sector to all involved drives, so that the dmraid program
105 will be able to find it in the next step.  (This usually must be done inside the
106 BIOS or option ROM setup, so you'll have to reboot to do it.)  Boot your host
107 system.
109 3. [dmr] Bring up the dmraid array
111 You will need the "dm-mod" kernel module loaded, if it is not already.  To scan
112 your hard drives and bring up the array, run (as root):
114   dmraid -ay
116 Explanation of argument:
118   -ay: Activates all scanned dmraid arrays ("activate yes").
120 This will create a new device node or symlink (depending on your version of
121 device-mapper and its configuration) in /dev/mapper named after the ID of your
122 array.  This name is supposed to be unique.
124 4. [dmr] Partition the dmraid array
126 Run your favorite partitioning tool on /dev/mapper/<dmraid array>, as root.  You
127 will need at least one partition for the following steps, but if you also plan
128 to use dm-crypt or LVM, you will need two: one for /boot and one for the rest of
129 the data.
131 5. [mdr] Bring up md-raid on the host
133 First set aside a partition for /boot.  You may be able to get away without this
134 if you use RAID1 and the correct metadata format (to avoid overwriting the first
135 few sectors of the disk), but this may not work.  The size of this partition can
136 be as small as a few hundred megabytes; it only has to hold any kernel images
137 you wish to boot to, the initramfs image for those kernels, and the config files
138 for grub.  This is usually on the order of 10 megabytes per kernel.
140 mdadm should load the correct kernel modules for this step.  Ensure the source
141 partitions you decided on (step 1 above) are correct and present, and as root:
143   mdadm --create --metadata=1.2 --homehost="<id string>" --level=<X> \
144         --auto=<md|mdp> /dev/sdAB /dev/sdCD /dev/sdXY
146 Explanation of arguments:
148   --create: Create a new array
150   --metadata=1.2: Use the newest level metadata.  This is not necessarily
151                   required.  All supported options:
152     --metadata=1.0: Put the superblock at the end of each device.
153     --metadata=1.2: Put the superblock 4K into each device.
155     There is also a --metadata=1.1 option, but it definitely doesn't work with
156         grub, since it puts the metadata right at the start of each device.  There
157         is also a 0.9 metadata level, but that has serious limitations and is not
158         supported by this hint at all.
160   --homehost="<id string>": Set the "home host" string for this array.  This is
161                             used for auto-assembly inside the initramfs: any
162                             device with a matching home host string will be put
163                             into the RAID array.  Remember the string you use.
165   --level=<X>: Select the RAID level to use.  Valid options are 0 (not
166                recommended), 1, 5, 6, 10, and any others listed in your local
167                mdadm(8) man page.
169   --auto=<md|mdp>: Choose either "md" or "mdp".  "mdp" allows partitions to be
170                    created on the result of the RAID array; this is normally not
171                    needed with LVM, but may be useful otherwise.  Remember the
172                    value you choose.
174   /dev/sd*: Device files to use as RAID sources.  These are usually partitions,
175             but if you're brave, you can try to get a RAID1 to work with grub
176             across a pair of disks.
178 Note that mdadm will find the smallest source device, and act as if the rest of
179 the devices were also that size.  Note also that standard RAID array device
180 counts apply here: a RAID5 array needs at least three members, a RAID1 array
181 needs exactly two members, etc.
183 Note also that you could use partitions created on the dmraid array, but that
184 type of setup is at the edge of what this hint supports.  It may work, but mdadm
185 might have issues reassembling the array inside initramfs, for example.  (You
186 may be able to hack on mdadm.conf to get this to work, though.)
188 Finally, note that you could name the array if you want.  See the mdadm(8) man
189 page for even more options.
191 6. [enc] Create encrypted volume
193 If you didn't do mdraid above (step 5), then set aside a partition for /boot
194 now.  The same comments as above apply: a few hundred megs is large enough.
196 You will need the "dm-crypt" kernel module loaded, if it is not already.  As
197 root, first fill the partition with random data, to foil some types of attack
198 which I am not familiar with but which most of the dm-crypt guides seem to know
199 about:
201   dd if=/dev/urandom of=<device> bs=1048576
203 Here, <device> is the disk or partition or dmraid array or mdadm array that you
204 wish to encrypt.  This operation will take a *long* time; approximately five
205 minutes per gigabyte depending on disk and processor speeds.  If that is too
206 long, you can use a worse-quality random number generator that will run faster:
208   badblocks -c 10240 -s -w -t random -v <device>
210 You could also skip this step entirely if you really want to.
212 Now put the encryption header on the volume, and choose a key:
214   cryptsetup --cipher=aes-cbc-essiv:sha256 --key-size=256 luksFormat <device>
216 The cipher given here is not required (use any cipher your kernel supports),
217 although using -cbc-essiv is recommended to defend against watermark attacks.
218 Note that the size of the hash chosen must match the --key-size argument.
220 Now open the encrypted volume:
222   cryptsetup luksOpen <device> pv
224 The last argument ("pv") is arbitrary, although "pv" makes sense if you're going
225 to put LVM on this encrypted volume.  The string given will be used verbatim for
226 the decrypted device name in /dev/mapper, so remember it if you use something
227 else.
229 7. [lvm] Set up LVM
231 If you did not do encryption above (step 6) or mdraid (step 5), then set aside a
232 partition for /boot now.  The same comments apply: a few hundred megabytes will
233 be more than enough.
235 LVM groups a set of physical volumes (PVs) into a volume group (VG), which is
236 then split into logical volumes (LVs).  LVs can also be resized at runtime,
237 either larger (if room is available on any of the VG's PVs) or smaller.
239 To start, format the sources as an LVM PV:
241   pvcreate --zero y /dev/<device>
243 Use whichever <device> is current at this point: either /dev/mapper/pv, or
244 /dev/mdXpX, or /dev/mdX, or /dev/mapper/<dmraid-name>, or /dev/sdXY.
246 You can also remove the "--zero y" arguments if you don't wish to zero out the
247 contents of the volume before you start.
249 (Writing zeros may or may not increase security if the underlying volume is
250 encrypted.  On the one hand, if an attacker knows that a certain sector is
251 all-zeros in plaintext, this may -- depending on the encryption algorithm --
252 help them attack the encryption key.  On the other hand, it does write out lots
253 of seemingly-random data to the raw disk device, and this may disguise the fact
254 that it contains an encrypted volume if you didn't already write random data out
255 to it in step 6.  Writing zeros also takes a while.)
257 Repeat this step for any other device you wish to add to the volume group (VGs
258 can do a sorta-kinda-almost-RAID setup, where a set of logical volumes spans any
259 number of physical volumes in the VG.  It's easiest with a single PV though.)
261 Now create a VG containing this PV:
263   vgcreate lfs /dev/<device>
265 Use the same /dev/<device> that you just formatted as a PV.  If you have more
266 than one PV, you can specify more than one /dev/<device>.
268 The volume group is named "lfs" here.  You can use any name you wish.  Once
269 logical volumes are created below, they will be accessible as symlinks at
270 /dev/<vg-name>/<lv-name>, so use any volume group name that will make them easy
271 to keep separate from all the other stuff in /dev.
273 Now create the logical volume(s):
275   lvcreate -L 10G -n root lfs
276   lvcreate -L 1G -n swap lfs
277   ...
279 The argument to -L is the size of the logical volume.  Any size that will fit in
280 the current volume group is acceptable, though I recommend leaving some space
281 free for future LV growth, or for snapshot LVs.  (These can be used to check
282 your filesystems in the background, for instance, instead of having a 180-day
283 timeout after which fsck does a full check at boot time.)
285 The argument to -n is the logical volume's name: here, root and swap.  The final
286 argument is the volume group that the new LVs are part of: here, lfs.
288 At this point, you should have a /dev/lfs/root and /dev/lfs/swap (or whatever
289 names you chose); use these for the LFS and swap partitions in the book.
291 ===============================================================================
292   Notes on section 2.4: Mounting the New Partition
293 ===============================================================================
295 8. [mdr,enc,lvm] Mounting /boot
297 Be sure to mount your boot partition at $LFS/boot in this step.
299 Also be sure to use the correct (final) root and swap devices (for example,
300 /dev/lfs/root and /dev/lfs/swap if you are doing LVM, you used "lfs" for your
301 VG name, and you used "root" / "swap" for your LV names).
303 ===============================================================================
304   Notes on sections 3.2: All Packages, and 3.3: Needed Patches
305 ===============================================================================
307 9. [dmr,mdr,enc,lvm] New packages
309 You need LVM2 and lfs-initramfs, and maybe dmraid, mdadm, and cryptsetup+popt.
310 You also need the patch from above for LVM2.  See above for links.
312 ==============================================================================
313   Modifications to Chapter 6
314 ===============================================================================
316 10. [dmr,mdr,enc,lvm] Modifications to Udev-XXX (any recent version)
318 Do *not* install rules/packages/64-device-mapper.rules, even though the book
319 says to.  Instead, install rules/suse/64-device-mapper.rules -- this is a much
320 better base for device-mapper support.  (Installing 64-md-raid.rules is fine,
321 and is required if you plan to do md RAID.)
323 install -m644 -v rules/packages/64-md-raid /lib/udev/rules.d/
324 install -m644 -v rules/suse/64-device-mapper.rules /lib/udev/rules.d/
326 Before installing udev-config, stop it from ignoring device-mapper devices (so
327 that the device-mapper udev rules will work), by commenting out the rule:
329 sed -i -e 's/^KERNEL=="dm-\*",.*ignore_device"$/#&/' 55-lfs.rules
331 ===============================================================================
332   New packages at the end of chapter 6
333 ===============================================================================
335 11. [dmr,mdr,enc,lvm] Installing LVM2
337 Once you're finished with chapter 6, you need to install a few more packages to
338 support your chosen root FS type.  All of these packages require device-mapper
339 (which is now part of LVM2).  Whether you want to use LVM or not:
341 patch -Np1 -i ../LVM2-2.02.53-fix_udev_rules-1.patch
342 ./configure --prefix=/usr --bindir=/bin --sbindir=/sbin --libdir=/lib \
343     --enable-readline --with-udev-prefix= --with-udevdir=/etc/udev/rules.d \
344     --enable-udev_rules
346 If you do *not* want to use LVM, build and install just device-mapper:
348 make device-mapper
349 make install_device-mapper
351 If you *do* want to use LVM, build and install everything:
353 make
354 make check
355 make install
356 install -m644 doc/example.conf /etc/lvm/lvm.conf
358 (Note that the every test in the testsuite will fail, unless you run it as root.
359 It requires the ability to mknod(2) so it can create a path to the device-mapper
360 kernel driver.  Also note that the tests require support for pretty much
361 everything in the kernel -- all device-mapper targets.  Therefore, if you have
362 configured your kernel to disable any of these, or you build as a non-root user,
363 then either consider the tests optional, or do not be surprised if they fail.)
365 12. [dmr] Installing dmraid
367 ./configure --prefix=/usr --bindir=/bin --sbindir=/sbin --libdir=/lib
368 make
369 make install
371 13. [mdr] Installing mdadm
373 First, prevent mdadm from installing udev rules that rely on vol_id (which is
374 now gone), and which are also duplicated by the 64-md-raid.rules file that you
375 already have:
377 sed -i -e '/^install :/s/ install-udev//' Makefile
379 Then build and install it:
381 make INSTALL=install
382 make INSTALL=install install
384 (Note that mdadm also has a testsuite, which you can run -- but again, only as
385 root -- with "sh ./test" after building.)
387 14. [enc] Installing cryptsetup
389 First install popt and move its library to /lib (but keep the compile-time
390 symlink in /usr/lib):
392 ./configure --prefix=/usr
393 make
394 make check
395 make install
396 mv -v /usr/lib/libpopt.so.* /lib
397 ln -sfv ../../lib/libpopt.so.0 /usr/lib/libpopt.so
399 Then install cryptsetup:
401 ./configure --prefix=/usr --libdir=/lib --sbindir=/sbin --sysconfdir=/etc
402 make
403 make install
405 15. [dmr,mdr,enc,lvm] Installing lfs-initramfs
407 ./configure --prefix=/usr --sysconfdir=/etc
408 make
409 make install
411 Now edit /etc/mkinitramfs.conf; see the inline comments for guidance on what
412 variables to set to what values.
414 Once the config file looks sane, continue in the LFS book.
416 ===============================================================================
417   Modifications to Chapter 8
418 ===============================================================================
420 16. [dmr,mdr,lvm,enc] Kernel Configuration
422 Be sure to enable the kernel options required for your chosen layers of device
423 mapping.
425 17. [enc] Creating /etc/crypttab
427 The initramfs uses /etc/crypttab to find out which source devices to decrypt
428 into which target names.  Find the source device for your encryption.  Then
429 create the crypttab file:
431 cat <<'EOF' >/etc/crypttab
432 # Begin /etc/crypttab
434 # Syntax is:
435 # dest src password options
436 #   "options" and "password" are optional (and "password" may not be supported
437 #   in the initramfs).  "none" means no password or options.
439 pv /dev/xxxxxxxxxxx none none
441 # End /etc/crypttab
444 18. [dmr,mdr,lvm,enc] Creating the initramfs image
446 Now that everything is set up, you can actually create the initramfs.  The
447 mkinitramfs script has several options; we will explicitly force it to pull the
448 files for the LFS book's current kernel version.  (Add "-f" if you have already
449 run the script once, and it has created the initramfs-<version>.cpio.gz file in
450 /boot.)  As root:
452 mkinitramfs -k <kernel-version>
454 19. [dmr,mdr,lvm,enc] Grub configuration
456 A note: since we're using a separate partition for /boot, none of the grub path
457 names will begin with /boot (since grub's root is the other partition, its
458 pathnames will be either (e.g.) /grub/menu.lst, or /lfskernel-<version>).
460 Another note: you don't actually need a "root=X" kernel command line parameter
461 with this setup.  The initramfs will (try to) find it from /etc/fstab.  This
462 *does* mean that whenever you change /etc/fstab (or /etc/crypttab), you will
463 want to rerun mkinitramfs so it picks up the changes, but you don't need to keep
464 changing menu.lst if you want to change how the root FS is found.  You will also
465 be able to choose more mount-time options (e.g., "barrier=1" now works, assuming
466 your device-mapper stack supports it all the way down; "data=journal" does as
467 well), since they all come from fstab.
469 On to the actual changes.  In addition to the kernel line in menu.lst, you will
470 need an "initrd" line that refers to the initramfs-<kernel-version>.cpio.gz
471 file.  (Don't worry, it's not really an initrd.  The interface from grub to the
472 kernel is the same as it would be for an initrd, so keeping the same name in
473 grub's configuration makes sense.)
475 Be *SURE* to keep an entry in menu.lst for your host distro.  If the initramfs
476 breaks, your system will likely be unusable; you will have to mount everything
477 back up from the host and figure out how to fix the initramfs.  (Having a
478 reasonable LiveCD available also helps with this.)
480 ===============================================================================
481   End: Use the initramfs to boot
482 ===============================================================================
484 Reboot.  Choose the LFS entry from the GRUB menu.  Enter the dm-crypt password
485 if you configured that, when requested.  (Note that you may have to add a
486 rootdelay=X kernel command line parameter, depending on your disk hardware and
487 discovery speeds.)  If you are dropped to "an extremely minimal shell", that
488 means that something went wrong: you can either reboot and play with kernel
489 command line options to try to get it to work, or manually run the commands in
490 the script named /init to see where the breakage is.
492 Unfortunately there are hardly any debugging tools on the initramfs; there may
493 never be very many.
496 ACKNOWLEDGEMENTS:
498 - Alexander Patrakov <patrakov AT gmail.com>
499   For filing the bug that started this.  Also for providing feedback on early
500   versions of lfs-initramfs, and the list of features he thought it needed.
502 - Simon Geard <delgarde AT ihug.co.nz>
503   For testing many early versions of lfs-initramfs.
506 CHANGELOG:
508 [2009-09-25]
509     Initial Release