Skip to content

Commit

Permalink
Add functionality that exists in initramfs to dracut.
Browse files Browse the repository at this point in the history
* Support 'zfs:<rootfs>' import and mounting.
  This was for some reason removed in eda3d4e.
* Support booting from snapshots.
* Support mounting recursive filesystems.
* Support mounting of additional filesystems.
* Support mounting nativly encrypted filesystems.

* Move code snippet that fetches and mounts recursive filesystems into recursive_mount_filesystems().
* zfs_set_ifs() needs to be a global func. We need it in a number of places!
  * Use this wherever we use CMD="somecmd someopt someopt" ; OUT="$($CMD someopt)"
* Dracut have the func emergency_shell() which does a little more.
  For those that don't have it, just run '/bin/sh -i -l'.
  • Loading branch information
FransUrbo committed Jul 28, 2015
1 parent 0111acb commit 6172672
Show file tree
Hide file tree
Showing 5 changed files with 226 additions and 89 deletions.
45 changes: 37 additions & 8 deletions contrib/dracut/90zfs/mount-zfs.sh.in
Original file line number Diff line number Diff line change
Expand Up @@ -15,29 +15,58 @@ esac
udev_trigger

if [ "${root}" = "zfs:AUTO" ] ; then
ZFS_BOOTFS=""
POOLS=$(get_pools)
IFS=";"

for pool in $POOLS
do
[ -z "$pool" ] && continue
ZFS_BOOTFS=""

# No 'else' or return below - if there's more pools, we try
# them. If not, we'll drop through and go to the end
# where we need a reboot because we couldn't find a root fs.
if import_pool "$pool"; then
if find_rootfs "$pool"; then
if mount_fs "${ZFS_BOOTFS}"; then
info "ZFS: Using ${ZFS_BOOTFS} as root."

rootok=1
if zfs_action "Importing pool ${pool}" import_pool "${pool}"
then
if find_rootfs "${pool}"; then
if recursive_mount_filesystems \
"Using '${ZFS_BOOTFS}' as root." \
"${ZFS_BOOTFS}"
then
IFS="$OLD_IFS"

rootok=1
return 0
fi
fi
fi
done
else
# Because of the case at the top, it's either 'zfs:AUTO' or
# 'zfs:<rootfs>'. Import the pool from rootfs and mount it.
root="${root#zfs:}" # Remove leading 'zfs:'
pool="${root%%/*}" # Remove everything after first slash.
ZFS_BOOTFS="${root}" # For zfs-functions.
if zfs_action "Importing pool ${pool}" import_pool "${pool}"; then
info "ZFS: Using ${pool} as root pool."

# Will be overwritten in clone_snap() if we're booting from
# a snapshot.
ZFS_BOOTFS_ORIG="$ZFS_BOOTFS"

# Booting from a snapshot? Updates ZFS_BOOTFS_ORIG and ZFS_BOOTFS...
echo "${root}" | grep -q '@' && setup_snapshot_booting
root="$ZFS_BOOTFS"

if recursive_mount_filesystems "Using '${root}' as root." \
"${root}"
then
rootok=1
return 0
fi
else
warn "ZFS: Can't import '${pool}'."
# Fallthrough
fi
fi

rootok=0
Expand Down
25 changes: 25 additions & 0 deletions contrib/dracut/README.dracut.markdown
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,31 @@ parameters passed in from the boot loader:
* `root=...`: If not set, importable pools are searched for a bootfs
attribute. If an explicitly set root is desired, you may use
`root=ZFS:pool/dataset`
* It is also possible to boot from a snapshot (technically, a clone of
the snapshot) using `root=ZFS:pool/dataset@snapshot`.
* If the actual snapshot isn't specified, only the at (@) character,
the user will be asked for a snapshot to boot from.
* With the extra parameter `rollback=(on,yes,1)`, instead of doing a
clone and boot from that, the code will rollback the filesystem up
to the snapshot specified.
* Even though there is no freely availible native encryption for any
opensource ZFS implementation, the hope is that one day have one.
This code supports the native encryption that Solaris have, using
the `zfs key` option.
* Supports both 'native' and 'legacy' filesystems.
* Supports 'recursive filesystems'. That is, if the root file system
is something like `rpool/ROOT/fedora17`, it is possible to have
`rpool/ROOT/fedora17/var`, `rpool/ROOT/fedora17/usr` etc.
It is not important that the 'mountpoint' property is set or correct,
the 'base filesystem' will be removed from the full path of the filesystem.
This means, that with the root fs as `rpool/ROOT/fedora17` and the sub-
filesystem as `rpool/ROOT/fedora17/var`, the result would be `/var`,
where it will be mounted.
* In addition to 'recursive filesystems', it is possible to have other
filesystems mounted by setting the ZFS_INITRD_ADDITIONAL_DATASETS variable
in /etc/sysconfig/zfs. Here, it is imparative that the 'mountpoint'
property is correct for each of these filesystems, since each filesystem
will use this to correctly mount it.

* `zfs_force=0`: If set to 1, the initramfs will run `zpool import -f` when
attempting to import pools if the required pool isn't automatically imported
Expand Down
9 changes: 2 additions & 7 deletions contrib/initramfs/scripts/zfs
Original file line number Diff line number Diff line change
Expand Up @@ -335,13 +335,8 @@ mountroot()
# NOTE: Mounted in the order specified in the
# ZFS_INITRD_ADDITIONAL_DATASETS variable so take care!

# Go through the complete list (recursivly) of all filesystems below
# the real root dataset
filesystems=$("${ZFS}" list -oname -tfilesystem -H -r "${ZFS_BOOTFS}")
for fs in $filesystems $ZFS_INITRD_ADDITIONAL_DATASETS
do
mount_fs "$fs"
done
recursive_mount_filesystems "Using ${ZFS_BOOTFS} as root." \
"${ZFS_BOOTFS}"

# ------------
# Debugging information
Expand Down
Loading

0 comments on commit 6172672

Please sign in to comment.