/
usr
/
share
/
initramfs-tools
/
scripts
/
local-top
/
/usr/share/initramfs-tools/scripts/local-top
mkdir
upload
Name
Size
Mode
Actions
cryptopensc
757
0755
edit
dl
rm
cryptroot
8615
0755
edit
dl
rm
iscsi
10297
0755
edit
dl
rm
lvm2
970
0755
edit
dl
rm
Edit:
/usr/share/initramfs-tools/scripts/local-top/cryptroot
(8615B)
#!/bin/sh PREREQ="cryptroot-prepare" # # Standard initramfs preamble # prereqs() { # Make sure that cryptroot is run last in local-top local req for req in "${0%/*}"/*; do script="${req##*/}" if [ "$script" != "${0##*/}" ]; then printf '%s\n' "$script" fi done } case $1 in prereqs) prereqs exit 0 ;; esac . /scripts/functions [ -f /lib/cryptsetup/functions ] || return 0 . /lib/cryptsetup/functions # wait_for_source() # Wait for encrypted $CRYPTTAB_SOURCE . Set $CRYPTTAB_SOURCE # to its normalized device name when it shows up; # return 1 if timeout. wait_for_source() { wait_for_udev 10 if crypttab_resolve_source; then # the device is here already, no need to loop return 0 fi # If the source device hasn't shown up yet, give it a little while # to allow for asynchronous device discovery (e.g. USB). # # We also need to take into account RAID or other devices that may # only be available on local-block stage. So, wait 5 seconds upfront, # in local-top; if that fails, end execution relying on local-block # invocations. Allow $ROOTDELAY/4 invocations with 1s sleep times (with # a minimum of 20 invocations), and if after that we still fail, then it's # really time to give-up. Variable $initrd_cnt tracks the re-invocations. # # Part of the lines below has been taken from initramfs-tools # scripts/local's local_device_setup(), as suggested per # https://launchpad.net/bugs/164044 . local slumber=5 if [ "${CRYPTROOT_STAGE-}" = "local-block" ]; then slumber=1 fi cryptsetup_message "Waiting for encrypted source device $CRYPTTAB_SOURCE..." while [ $slumber -gt 0 ]; do sleep 1 if [ -x /scripts/local-block/lvm2 ]; then # activate any VG that might hold $CRYPTTAB_SOURCE /scripts/local-block/lvm2 "$CRYPTTAB_SOURCE" fi if crypttab_resolve_source; then wait_for_udev 10 return 0 fi slumber=$(( $slumber - 1 )) done return 1 } # setup_mapping() # Set up a crypttab(5) mapping defined by $CRYPTTAB_NAME, # $CRYPTTAB_SOURCE, $CRYPTTAB_KEY, $CRYPTTAB_OPTIONS. setup_mapping() { local dev initrd_cnt # We control here the number of re-invocations of this script from # local-block - the heuristic is $ROOTDELAY/4, with a minimum of 20. if [ -f "$CRYPTROOT_COUNT_FILE" ]; then initrd_cnt="$(cat <"$CRYPTROOT_COUNT_FILE")" else initrd_cnt="${ROOTDELAY:-180}" initrd_cnt=$(( initrd_cnt/4 )) if [ $initrd_cnt -lt 20 ]; then initrd_cnt=20 fi echo "$initrd_cnt" >"$CRYPTROOT_COUNT_FILE" fi # The same target can be specified multiple times # e.g. root and resume lvs-on-lvm-on-crypto if dm_blkdevname "$CRYPTTAB_NAME" >/dev/null; then return 0 fi crypttab_parse_options --export --missing-path=fail || return 1 if ! wait_for_source; then if [ $initrd_cnt -eq 0 ]; then # we've given up if [ -n "$panic" ]; then panic "ALERT! encrypted source device $CRYPTTAB_SOURCE does not exist, can't unlock $CRYPTTAB_NAME." else # let the user fix matters if they can echo " ALERT! encrypted source device $CRYPTTAB_SOURCE does not exist, can't unlock $CRYPTTAB_NAME." echo " Check cryptopts=source= bootarg: cat /proc/cmdline" echo " or missing modules, devices: cat /proc/modules; ls /dev" panic "Dropping to a shell." fi return 1 # can't continue because environment is lost else initrd_cnt=$(( initrd_cnt - 1 )) echo "$initrd_cnt" >"$CRYPTROOT_COUNT_FILE" return 0 # allow some attempts on local-block stage fi fi # our `cryptroot-unlock` script searches for cryptsetup processes # with a given CRYPTTAB_NAME it their environment export CRYPTTAB_NAME if [ -z "${CRYPTTAB_OPTION_keyscript+x}" ]; then # no keyscript: interactive unlocking, or key file if [ "${CRYPTTAB_KEY#/FIXME-initramfs-rootmnt/}" != "$CRYPTTAB_KEY" ]; then # skip the mapping for now if the root FS is not mounted yet sed -rn 's/^\s*[^#[:blank:]]\S*\s+(\S+)\s.*/\1/p' /proc/mounts | grep -Fxq -- "$rootmnt" || return 1 # substitute the "/FIXME-initramfs-rootmnt/" prefix by the real root FS mountpoint otherwise CRYPTTAB_KEY="$rootmnt/${CRYPTTAB_KEY#/FIXME-initramfs-rootmnt/}" fi if [ "$CRYPTTAB_KEY" != "none" ]; then if [ ! -e "$CRYPTTAB_KEY" ]; then cryptsetup_message "ERROR: Skipping target $CRYPTTAB_NAME: non-existing key file $CRYPTTAB_KEY" return 1 fi # try only once if we have a key file CRYPTTAB_OPTION_tries=1 fi fi local count=0 maxtries="${CRYPTTAB_OPTION_tries:-3}" fstype vg rv while [ $maxtries -le 0 ] || [ $count -lt $maxtries ]; do if [ -z "${CRYPTTAB_OPTION_keyscript+x}" ] && [ "$CRYPTTAB_KEY" != "none" ]; then # unlock via keyfile unlock_mapping "$CRYPTTAB_KEY" else # unlock interactively or via keyscript run_keyscript "$count" | unlock_mapping fi rv=$? count=$(( $count + 1 )) if [ $rv -ne 0 ]; then cryptsetup_message "ERROR: $CRYPTTAB_NAME: cryptsetup failed, bad password or options?" sleep 1 continue elif ! dev="$(dm_blkdevname "$CRYPTTAB_NAME")"; then cryptsetup_message "ERROR: $CRYPTTAB_NAME: unknown error setting up device mapping" return 1 fi if ! fstype="$(get_fstype "$dev")" || [ "$fstype" = "unknown" ]; then if [ "$CRYPTTAB_TYPE" != "luks" ]; then # bad password for plain dm-crypt device? or mkfs not run yet? cryptsetup_message "ERROR: $CRYPTTAB_NAME: unknown fstype, bad password or options?" wait_for_udev 10 /sbin/cryptsetup remove -- "$CRYPTTAB_NAME" sleep 1 continue fi elif [ "$fstype" = lvm2 ]; then if [ ! -x /sbin/lvm ]; then cryptsetup_message "WARNING: $CRYPTTAB_NAME: lvm is not available" return 1 elif vg="$(lvm pvs --noheadings -o vg_name --config 'log{prefix=""}' -- "$dev")"; then # activate the VG held by the PV we just unlocked lvm lvchange -a ay --sysinit -- "$vg" fi fi cryptsetup_message "$CRYPTTAB_NAME: set up successfully" wait_for_udev 10 return 0 done cryptsetup_message "ERROR: $CRYPTTAB_NAME: maximum number of tries exceeded" exit 1 } ####################################################################### # Begin real processing mkdir -p /cryptroot # might not exist yet if the main system has no crypttab(5) # Do we have any kernel boot arguments? if ! grep -qE '^(.*\s)?cryptopts=' /proc/cmdline; then # ensure $TABFILE exists and has a mtime greater than the boot time # (existing $TABFILE is preserved) touch -- "$TABFILE" else # let the read builtin unescape the '\' as GRUB substitutes '\' by '\\' in the cmdline tr ' ' '\n' </proc/cmdline | sed -n 's/^cryptopts=//p' | while IFS= read cryptopts; do # skip empty values (which can be used to disable the initramfs # scripts for a particular boot, cf. #873840) [ -n "$cryptopts" ] || continue unset -v target source key options IFS="," for x in $cryptopts; do case "$x" in target=*) target="${x#target=}";; source=*) source="${x#source=}";; key=*) key="${x#key=}";; *) options="${options+$options,}$x";; esac done if [ -z "${source:+x}" ]; then cryptsetup_message "ERROR: Missing source= value in kernel parameter cryptopts=$cryptopts" else # preserve mangling printf '%s %s %s %s\n' "${target:-cryptroot}" "$source" "${key:-none}" "${options-}" fi done >"$TABFILE" fi # Do we have any settings from the $TABFILE? if [ -s "$TABFILE" ]; then # Create locking directory before invoking cryptsetup(8) to avoid warnings mkdir -pm0700 /run/cryptsetup modprobe -q dm_crypt crypttab_foreach_entry setup_mapping fi exit 0
Save
cmd:
run