diff options
-rw-r--r-- | dracut.cmdline.7.asc | 15 | ||||
-rwxr-xr-x | modules.d/95cifs/cifs-lib.sh | 36 | ||||
-rwxr-xr-x | modules.d/95cifs/cifsroot.sh | 26 | ||||
-rwxr-xr-x | modules.d/95cifs/module-setup.sh | 46 | ||||
-rwxr-xr-x | modules.d/95cifs/parse-cifsroot.sh | 52 |
5 files changed, 175 insertions, 0 deletions
diff --git a/dracut.cmdline.7.asc b/dracut.cmdline.7.asc index 8f642f35..0b1b8a22 100644 --- a/dracut.cmdline.7.asc +++ b/dracut.cmdline.7.asc @@ -398,6 +398,21 @@ NFS **rd.nfs.domain=**_<NFSv4 domain name>_:: Set the NFSv4 domain name. Will overwrite the settings in _/etc/idmap.conf_. +CIFS +~~~ +**root=**cifs://[_<username>_[:_<password>_]@]_<server-ip>_:_<root-dir>_:: + mount cifs share from <server-ip>:/<root-dir>, if no server-ip is given, use + dhcp next_server. if server-ip is an IPv6 address it has to be put in + brackets, e.g. [2001:DB8::1]. If a username or password are not specified +as part of the root, then they must be passed on the command line through +cifsuser/cifspass. + +**cifsuser=_<username>_:: + Set the cifs username, if not specified as part of the root. + +**cifspass=_<password>_:: + Set the cifs password, if not specified as part of the root. + iSCSI ~~~~~ **root=**iscsi:[_<username>_:_<password>_[:_<reverse>_:_<password>_]@][_<servername>_]:[_<protocol>_]:[_<port>_][:[_<iscsi_iface_name>_]:[_<netdev_name>_]]:[_<LUN>_]:_<targetname>_:: diff --git a/modules.d/95cifs/cifs-lib.sh b/modules.d/95cifs/cifs-lib.sh new file mode 100755 index 00000000..3cbe6dc4 --- /dev/null +++ b/modules.d/95cifs/cifs-lib.sh @@ -0,0 +1,36 @@ +#!/bin/sh +# -*- mode: shell-script; indent-tabs-mode: nil; sh-basic-offset: 4; -*- +# ex: ts=8 sw=4 sts=4 et filetype=sh + +# cifs_to_var CIFSROOT +# use CIFSROOT to set $server, $path, and $options. +# CIFSROOT is something like: cifs://[<username>[:<password>]]@<host>/<path> +# NETIF is used to get information from DHCP options, if needed. + +type getarg >/dev/null 2>&1 || . /lib/dracut-lib.sh + +cifs_to_var() { + local cifsuser; local cifspass + # Check required arguments + server=${1##cifs://} + cifsuser=${server%@*} + cifspass=${cifsuser#*:} + if [ "$cifspass" != "$cifsuser" ]; then + cifsuser=${cifsuser%:*} + else + cifspass=$(getarg cifspass) + fi + if [ "$cifsuser" != "$server" ]; then + server="${server#*@}" + else + cifsuser=$(getarg cifsuser) + fi + + path=${server#*/} + server=${server%/*} + + if [ ! "$cifsuser" -o ! "$cifspass" ]; then + die "For CIFS support you need to specify a cifsuser and cifspass either in the cifsuser and cifspass commandline parameters or in the root= CIFS URL." + fi + options="user=$cifsuser,pass=$cifspass" +} diff --git a/modules.d/95cifs/cifsroot.sh b/modules.d/95cifs/cifsroot.sh new file mode 100755 index 00000000..7956d6f6 --- /dev/null +++ b/modules.d/95cifs/cifsroot.sh @@ -0,0 +1,26 @@ +#!/bin/sh +# -*- mode: shell-script; indent-tabs-mode: nil; sh-basic-offset: 4; -*- +# ex: ts=8 sw=4 sts=4 et filetype=sh + +type getarg >/dev/null 2>&1 || . /lib/dracut-lib.sh +. /lib/cifs-lib.sh + +[ "$#" = 3 ] || exit 1 + +# root is in the form root=cifs://user:pass@[server]/[folder] either from +# cmdline or dhcp root-path +netif="$1" +root="$2" +NEWROOT="$3" + +cifs_to_var $root +echo server: $server +echo path: $path +echo options: $options + +mount.cifs //$server/$path $NEWROOT -o $options && { [ -e /dev/root ] || >/dev/root ; } + +# inject new exit_if_exists +echo 'settle_exit_if_exists="--exit-if-exists=/dev/root"; rm "$job"' > $hookdir/initqueue/cifs.sh +# force udevsettle to break +> $hookdir/initqueue/work diff --git a/modules.d/95cifs/module-setup.sh b/modules.d/95cifs/module-setup.sh new file mode 100755 index 00000000..2f2e78da --- /dev/null +++ b/modules.d/95cifs/module-setup.sh @@ -0,0 +1,46 @@ +#!/bin/bash +# -*- mode: shell-script; indent-tabs-mode: nil; sh-basic-offset: 4; -*- +# ex: ts=8 sw=4 sts=4 et filetype=sh + +check() { + # If our prerequisites are not met, fail anyways. + type -P mount.cifs >/dev/null || return 1 + + [[ $hostonly ]] || [[ $mount_needs ]] && { + for fs in ${host_fs_types[@]}; do + strstr "$fs" "\|cifs" && return 0 + done + return 255 + } + + return 0 +} + +depends() { + # We depend on network modules being loaded + echo network +} + +installkernel() { + instmods cifs ipv6 +} + +install() { + local _i + local _nsslibs + dracut_install -o mount.cifs + dracut_install /etc/services /etc/nsswitch.conf /etc/protocols + + inst_libdir_file 'libcap-ng.so*' + + _nsslibs=$(sed -e '/^#/d' -e 's/^.*://' -e 's/\[NOTFOUND=return\]//' /etc/nsswitch.conf \ + | tr -s '[:space:]' '\n' | sort -u | tr -s '[:space:]' '|') + _nsslibs=${_nsslibs#|} + _nsslibs=${_nsslibs%|} + + inst_libdir_file -n "$_nsslibs" 'libnss*.so*' + + inst_hook cmdline 90 "$moddir/parse-cifsroot.sh" + inst "$moddir/cifsroot.sh" "/sbin/cifsroot" + inst "$moddir/cifs-lib.sh" "/lib/cifs-lib.sh" +} diff --git a/modules.d/95cifs/parse-cifsroot.sh b/modules.d/95cifs/parse-cifsroot.sh new file mode 100755 index 00000000..d5adb98e --- /dev/null +++ b/modules.d/95cifs/parse-cifsroot.sh @@ -0,0 +1,52 @@ +#!/bin/sh +# -*- mode: shell-script; indent-tabs-mode: nil; sh-basic-offset: 4; -*- +# ex: ts=8 sw=4 sts=4 et filetype=sh +# +# root=cifs://[user:pass@]<server>/<folder> +# +# This syntax can come from DHCP root-path as well. +# +# If a username or password are not specified as part of the root, then they +# will be pulled from cifsuser and cifspass on the kernel command line, +# respectively. +# + +type getarg >/dev/null 2>&1 || . /lib/dracut-lib.sh +. /lib/cifs-lib.sh + +#Don't continue if root is ok +[ -n "$rootok" ] && return + +# This script is sourced, so root should be set. But let's be paranoid +[ -z "$root" ] && root=$(getarg root=) +[ -z "$netroot" ] && netroot=$(getarg netroot=) + +# netroot= cmdline argument must be ignored, but must be used if +# we're inside netroot to parse dhcp root-path +if [ -n "$netroot" ] ; then + if [ "$netroot" = "$(getarg netroot=)" ] ; then + warn "Ignoring netroot argument for CIFS" + netroot=$root + fi +else + netroot=$root; +fi + +# Continue if cifs +case "${netroot%%:*}" in + cifs);; + *) unset netroot; return;; +esac + +# Check required arguments +cifs_to_var $netroot + +# If we don't have a server, we need dhcp +if [ -z "$server" ] ; then + DHCPORSERVER="1" +fi; + +# Done, all good! +rootok=1 + +echo '[ -e $NEWROOT/proc ]' > $hookdir/initqueue/finished/cifsroot.sh |