#!/bin/bash
# Guide: https://rr-developer.github.io/LUKS-on-Raspberry-Pi/ plus others
#
# This script can be run two different ways:
# * Automatically by sdm on the booted system as invoked by the cryptroot plugin via the sdm-auto-encrypt service
# * Manually on the booted system
#

function errexit() {
    echo -e "$1"
    exit 1
}

function wait_startup_complete {
    # $1 is the message to write
    local lc=0 msg=$1
    while [[ "$(systemctl show -p ActiveState graphical.target --value)" != "active" ]] && [[ "$(systemctl show -p ActiveState multi-user.target --value)" != "active" ]]
    do
        if [ $lc -eq 0 ]
        then
            logger "$msg"
	    echo "$msg" > /dev/console
            lc=1
        fi
        sleep 1
    done
}

function getgbstr() {
    #
    # $1: # of bytes in partition
    #
    # Returns the string "(nn.nnGB, mm.mmGiB)"

    local nbytes=$1
    local gb=1000000000 gib=1073741824 gb2=500000000 gi2=536870912
    local ngbytes ngibytes 
     ngbytes=$(printf %.1f "$(( ((10 * nbytes)+gb2) / gb ))e-1")
    ngibytes=$(printf %.1f "$(( ((10 * nbytes)+gi2) / gib))e-1")
    echo "(${ngbytes}GB, ${ngibytes}GiB)"
    return
}

function getfsdf() {
    #
    # $1: fs name
    # $2: df component: pcent, avail, etc
    #
    echo "$(df --output=$2 $1 | tail -1 | (IFS="%" ; read a ; a="${a% }" ; a="${a# }" echo $a))"
}

function ispdevp() {
    local dev="$1"
    [[ "$dev" =~ "mmcblk" ]] || [[ "$dev" =~ "nvme0n1" ]] && return 0 || return 1
}

function getspname() {
    local dev="$1" pn="$2"
    ispdevp $dev && echo "${dev}p${pn}" || echo "${dev}${pn}"
}

function getpartname() {
    local dev="$1" pn="$2"
    ispdevp $dev && echo "p${pn}" || echo "$pn"
}

function logifsdm() {
    local msg="$1"
    [ $xsdm -eq 1 ] && echo "sdm-cryptconfig: $msg" > /dev/console
}

function printhelp() {
    echo $"
sdm-cryptconfig has several command line switches, all of which are optional

* --authorized-keys keyfile -- Provides SSH authorized_keys file for the initramfs. Required with --ssh
* --crypto cryptalgo -- Specify crypto algorithm (aes [D]) or xchacha (use on Pi4 and earlier)
* --dns dnsaddr -- Set IP Address of DNS server
* --gateway gatewayaddr -- Set IP address of gateway
* --hostname hostname -- Set hostname
* --ipaddr ipaddr -- set IP address to use in initramfs
* --keyfile keyfile -- Key file for USB-based key unlock
* --mapper cryptmapname -- Set cryptroot mapper name [Default: cryptroot]
* --mask netmask -- Set network mask for initramfs
* --nopwd -- No password on encrypted rootfs; keyfile (required) is only unlock
* --quiet -- Do not disable quiet boot for RasPiOS with desktop
* --ssh -- Enable SSH in initramfs
* --sshbash -- Leave ssh session bash enabled (Default: use cryptroot-unlock)
* --sshport port -- Specify initramfs SSH port (Default: 22)
* --sshtimeout timeout -- Specify initramfs SSH timeout (Default: 300)
* --reboot -- Reboot the system (into initramfs) when sdm-cryptconfig is complete
* --sdm -- sdm cryptroot plugin sets this
* --unique-ssh -- Use a different SSH host key in initramfs than the host OS SSH key

The network configuration switches (dns, gateway, hostname, ipaddr, and mask) are only needed
and should only be used if you know that the system is unable to get an IP address and network
configuration information from the network (e.g., via DHCP). These settings are ONLY used in the
initramfs if SSH is enabled and are not automatically removed, so each time the system restarts
the initramfs will use these settings.
"
}

function printinfo() {
    local used1k usedby usedstr rootfs sd

    rootfs=$(findmnt --noheadings --output source /)     # rootfs name
    sd=${rootfs%$(getpartname $rootfs 2)}  # dev name w/o partition name

    used1k=$(getfsdf "/" used)
    usedby=$((used1k*1024))
    usedstr=$(getgbstr $usedby)
    echo ""
    echo "> Rootfs '$rootfs' has $usedby bytes $usedstr used"
    echo ""
    echo "> You will need another disk for the encryption process to use as a scratch disk"
    echo "  This disk must be larger than $usedstr and it will be over-written"
    echo $"
Reboot the system when you are ready to continue

The system will start to reboot, but hang trying to read rootfs. It will try 30 times
before giving up and dropping to the initramfs prompt: (initramfs)

** Ignore the 'ALERT! missing /dev/mapper' message. That is expected. **

Once at the (initramfs) prompt, connect the SSD or SD Card that will be used as a scratch drive

When you have the drive name enter the command:
    (initramfs) sdmcryptfs $sd /dev/sdX

Where:

    $sd is the name of your system disk
    /dev/sdX is the name of your scratch disk

sdmcryptfs will:

* Print the size of rootfs $rootfs
* Save the contents of $rootfs to /dev/sdX
* NOTE: There will be no prompts for passphrases if --nopwd specified
* Enable encryption on $rootfs
  * You will be prompted to enter YES (all in upper case) to continue
  * You will then be prompted to provide the passphrase for $rootfs (unless --nopwd)
    ** Be sure that your CapsLock is set correctly (in case you changed it to type YES)!!! **
* After a short pause you'll be prompted for the passphrase again to unlock $rootfs (unless --nopwd)
* The saved rootfs content will be restored from /dev/sdX to the encrypted rootfs
* When the restore finishes sdmcryptfs will exit and drop you to the (initramfs) prompt
* Type 'exit' to continue the boot sequence

* Once the system boots the sdm-cryptfs-cleanup service will run which:
  * Removes some one-time content and rebuilds initramfs
  * Reboots the system one last time
"
    if [ $xnopwd -eq 0 ]
    then
	echo $"* As the system reboots you'll once again be prompted for the rootfs passphrase (Without the 30 tries)
  ** The system will now ask for the rootfs passphrase like this every time the system boots **
"
    else
	echo $"* As the system reboots it will hang until the USB keyfile disk is found in a USB drive
"
    fi
    if [ $xssh -eq 1 ]
    then
	echo $"
NOTE: You have configured SSH
      Please review https://github.com/gitbls/sdm/blob/master/Docs/Disk-Encryption.md
"
    fi
}

function configcleanupsvc() {
#
# Set up service to run after next reboot that will rebuild initramfs (again) and reboot
#
    echo "> Set up run-once service to rebuild initramfs after encrytped rootfs boot"
    cat > /etc/systemd/system/sdm-cryptfs-cleanup.service <<EOF
[Unit]
Description=sdm cryptroot cleanup service
After=multi-user.target

[Service]
Type=simple
ExecStart=/usr/local/bin/sdm-cryptfs-cleanup

[Install]
WantedBy=multi-user.target
EOF

    echo "> Create /usr/local/bin/sdm-cryptfs-cleanup script"
    cat > /usr/local/bin/sdm-cryptfs-cleanup <<EOF
#!/bin/bash

function wait_startup_complete {
    # $1 is the message to write
    local lc=0 msg=\$1
    while [[ "\$(systemctl show -p ActiveState graphical.target --value)" != "active" ]] && [[ "\$(systemctl show -p ActiveState multi-user.target --value)" != "active" ]]
    do
        if [ \$lc -eq 0 ]
        then
            logger "\$msg"
	    echo "\$msg" > /dev/console
            lc=1
        fi
        sleep 1
    done
}

echo  "sdm-cryptfs-cleanup: Starting; System will restart automatically when completed" > /dev/console
source /etc/sdm/sdm-readparams
[ -f /etc/sdm/assets/cryptbbh ] && cat /etc/sdm/assets/cryptbbh >| /etc/sdm/assets/gfxbbh && do_delayed_boot_behavior reboot
echo  "sdm-cryptfs-cleanup: Clean up initramfs content" > /dev/console
logger "sdm-cryptfs-cleanup: Clean up initramfs content"
mv /etc/initramfs-tools/hooks/luks-hooks /etc/initramfs-tools/hooks/.sdm.luks-hooks.old
# Leave bash in initramfs rather than special case remove if no --sshbash
grep -v -E "sdmcryptfs|mappername|sdmcrypto|sdmnopwd|/etc/sdm/assets/cryptroot" /etc/initramfs-tools/hooks/.sdm.luks-hooks.old > /etc/initramfs-tools/hooks/luks-hooks
chmod 755 /etc/initramfs-tools/hooks/luks-hooks
[ $xsshbash -eq 0 ] && [ -f /etc/dropbear/initramfs/dropbear.conf ] && sed -i "s/bash/cryptroot-unlock/" /etc/dropbear/initramfs/dropbear.conf
rm -f /etc/sdm/assets/cryptroot/*.lek /etc/*.lek
echo "sdm-cryptfs-cleanup: Rebuild initramfs" > /dev/console
logger "sdm-cryptfs-cleanup: Rebuild initramfs"
update-initramfs -u
systemctl disable sdm-cryptfs-cleanup
rm -f /etc/systemd/system/sdm-cryptfs-cleanup.service
rm -f /etc/systemd/system/sdm-auto-encrypt.service
[ -f /usr/bin/startlxde-pi ] && systemctl set-default graphical.target
systemctl daemon-reload
wait_startup_complete "sdm-cryptfs-cleanup: Wait for system startup to complete"
secs=10
logger "sdm-cryptfs-cleanup: The system will restart in \$secs seconds"
echo "sdm-cryptfs-cleanup: The system will restart in \$secs seconds" > /dev/console
sleep \$secs
logger "sdm-cryptfs-cleanup: System restarting now"
echo "sdm-cryptfs-cleanup: System restarting now" > /dev/console
rm -f /usr/local/bin/sdm-cryptfs-cleanup
sleep 2
reboot
EOF
    chmod 755 /usr/local/bin/sdm-cryptfs-cleanup
    pgrep systemd >/dev/null 2>&1 && systemctl daemon-reload
    systemctl enable sdm-cryptfs-cleanup > /dev/null 2>&1
}

function parsecmd() {
    local cmd="$1" args="$2"
    local longopts="authorized-keys:,crypto:,dns:,gateway:,help,hostname:,ipaddr:,keyfile:,mapper:,mappername:,mask:,netmask:,nopwd,ssh,sshbash,sshport:,sshtimeout:,reboot,sdm,unique-ssh"

    OARGS=$(getopt -o h --longoptions $longopts -n 'sdm' -- $args)
    [ $? -ne 0 ] && errexit "? $cmd: Unable to parse command"
    eval set -- "$OARGS"
    while true
    do
	case "${1,,}" in
	    # 'shift 2' if switch has argument, else just 'shift'
	    --authorized-keys) xauthkeys=$2 ; shift 2 ;;
	    --crypto)          xcrypto=$2   ; shift 2 ;;
	    --dns)             xdns=$2      ; shift 2 ;;
	    --gateway)         xgateway=$2  ; shift 2 ;;
	    --hostname)        xhostname=$2 ; shift 2 ;;
	    --ipaddr)          xipaddr=$2   ; shift 2 ;;
	    --keyfile)         xkeyfile=$2  ; shift 2 ;;
	    --mapper|--mappername) xmapper=$2 ; shift 2 ;;
	    --mask|--netmask)  xnetmask=$2  ; shift 2 ;;
	    --nopwd)           xnopwd=1     ; shift 1 ;;
	    --quiet)           xquiet=1     ; shift 1 ;;
	    --reboot)          xreboot=1    ; shift 1 ;;
	    --ssh)             xssh=1       ; shift 1 ;;
	    --sshbash)         xsshbash=1   ; shift 1 ;;
	    --sshport)         xsshport=$2  ; shift 2 ;;
	    --sshtimeout)      xsshtimeout=$2 ; shift 2 ;;
	    --sdm)             xsdm=1       ; shift 1 ;;
	    --unique-ssh)      xunique=1    ; shift 1 ;;
	    --)                shift ; break ;;
	    -h|--help)         printhelp ; shift ; exit ;;
	    *) errexit "? $0: Internal error" ;;
	esac
    done

    if [ "$xauthkeys" != "" ]
    then
	! [ -f $xauthkeys ] && errexit "? --authorized-keys file '$xauthkeys' not found"
    else
	[ $xssh -eq 1 ]  && errexit "? --ssh requires --authorized-keys"
    fi
    [[ $xnopwd -eq 1 ]] && [[ "$xkeyfile" == "" ]] && errexit "? --nopwd requires --keyfile"
}

function doconfiginitramfs() {
    local kcmd="" knopwd="" kskip=""

    # For some reason both of these need to be set
    echo "> Update initramfs configuration for 'MODULES=most' and 'update_initramfs=all'"
    sed -i "s/^MODULES=dep/MODULES=most/" /etc/initramfs-tools/initramfs.conf
    sed -i "s/^update_initramfs=yes/update_initramfs=all/" /etc/initramfs-tools/update-initramfs.conf

# Not sure this is needed but keeping for now
#    echo "> Create /etc/kernel/postinst.d/initramfs-rebuild"
#    cat >> /etc/kernel/postinst.d/initramfs-rebuild <<EOF
##!/bin/sh -e
#
## Rebuild initramfs after kernel upgrade to include new kernel's modules.
## https://github.com/Robpol86/robpol86.com/blob/master/docs/_static/initramfs-rebuild.sh
## Save as (chmod +x): /etc/kernel/postinst.d/initramfs-rebuild
#
## Remove splash from cmdline.
#if grep -q '\bsplash\b' /boot/firmware/cmdline.txt; then
#  sed -i 's/ \?splash \?/ /' /boot/firmware/cmdline.txt
#fi
#
## Exit if not building kernel for this Raspberry Pi's hardware version.
#version="\$1"
#current_version="\$(uname -r)"
#case "\${current_version}" in
#  *-v7+)
#    case "\${version}" in
#      *-v7+) ;;
#      *) exit 0
#    esac
#  ;;
#  *+)
#    case "\${version}" in
#      *-v7+) exit 0 ;;
#    esac
#  ;;
#esac
#update-initramfs -u
#EOF
#    chmod 755 /etc/kernel/postinst.d/initramfs-rebuild

    [ $xnopwd -eq 1 ] && kskip="&& /bin/false"
    echo "> Create /usr/bin/sdmluksunlock; runs in initramfs to unlock rootfs"
    cat > /usr/bin/sdmluksunlock <<EOF
#!/bin/sh
#
# called when it's time to read the LUKS unlock key, which is echoed to stdout/read by caller
#
set -e
trydisks()
{
    for usbpartition in /dev/disk/by-id/usb-*-part1; do
        usbdevice=\$(readlink -f \$usbpartition)
        if mount -t vfat \$usbdevice /mnt 2>/dev/null; then
            if [ -e /mnt/\$CRYPTTAB_KEY.lek ]; then
                cat /mnt/\$CRYPTTAB_KEY.lek
                umount \$usbdevice || continue
                exit
            fi
            umount \$usbdevice || continue
        fi
    done
    return 0
}

if [ ! -e /mnt ]; then
    mkdir -p /mnt
fi
if [ "\$CRYPTTAB_TRIED" == "0" ] ; then
    sleep 4 # Wait a bit for disk to appear
fi
set +e
trydisks
kbd=\$(dmesg | grep -i keyboard | grep -v keyboard-setup)
set -e
if [ "\$kbd" != "" ] $kskip ; then
    trydisks
    /lib/cryptsetup/askpass "Insert USB Keyfile Disk (or type passphrase) then press ENTER: "
else
    while :; do
        set +e
        kbd=\$(dmesg | grep -i keyboard | grep -v keyboard-setup)
        set -e
        [ "\$kbd" != "" ] $kskip && break
        trydisks
        echo "Insert USB Keyfile Disk" >/dev/console
        sleep 1
    done
    /lib/cryptsetup/askpass "Insert USB Keyfile Disk (or type passphrase) then press ENTER: "
fi
EOF
    chmod 755 /usr/bin/sdmluksunlock
    echo "> Create /etc/initramfs-tools/hooks/luks-hooks"
    [ "$xkeyfile" != "" ] && kcmd="copy_file text /etc/sdm/assets/cryptroot/$xkeyfile /etc/$xkeyfile"
    [ $xnopwd -eq 1 ] && knopwd="copy_file text /usr/local/bin/sdmnull /etc/sdmnopwd"
    cat > /etc/initramfs-tools/hooks/luks-hooks <<EOF
#!/bin/sh -e
PREREQS=""
case "\$1" in
        prereqs) echo "\${PREREQS}"; exit 0;;
esac

. /usr/share/initramfs-tools/hook-functions

copy_exec /usr/sbin/resize2fs /usr/sbin
copy_exec /usr/sbin/fdisk /usr/sbin
copy_exec /usr/sbin/cryptsetup /usr/sbin
copy_exec /usr/bin/bash /usr/bin
copy_file text /usr/local/bin/sdmcryptfs /usr/bin
# OK if this fails; means it was copied due to keyscript in crypttab and copied in /usr/share/initramfs-tools/hooks/cryptroot
copy_file text /usr/bin/sdmluksunlock || true
copy_file text /etc/mappername
copy_file text /etc/sdmcrypto
copy_file text /etc/sdmkeyfile
$kcmd
$knopwd
exit 0
EOF
    chmod 755 /etc/initramfs-tools/hooks/luks-hooks

    echo "> Update /etc/initramfs-tools/modules to include crypto '$xcrypto' modules"
    case "$xcrypto" in
	xchacha)
	    cat >> /etc/initramfs-tools/modules <<EOF
algif_skcipher
xchacha20
adiantum
aes_arm
sha256
nhpoly1305
dm-crypt
EOF
	    ;;
	aes|aes-*)
	    cat >> /etc/initramfs-tools/modules <<EOF
algif_skcipher
aes_arm64
aes_ce_blk
aes_ce_ccm
aes_ce_cipher
sha256_arm64
cbc
dm-crypt
EOF
	    ;;
    esac

    echo "> Enable KEYMAP=y in /etc/initramfs-tools/initramfs.conf"
    sed -i "s/KEYMAP=n/KEYMAP=y/" /etc/initramfs-tools/initramfs.conf
    #
    # Configure the network in initramfs.conf if requested
    #
    if [[ $xssh -eq 1 ]] && [[ "${xipaddr}${xgateway}${xnetmask}${xhostname}" != "" ]]
    then
	ips="IP="   # Configure DNS, gateway, hostname, ipaddr, netmask
	[ "$xipaddr" != "" ] && ips="${ips}${xipaddr}:" || ips="${ips}:"
	ips="${ips}:"   # For the mystery 'server' value
	[ "$xgateway" != "" ] && ips="${ips}${xgateway}:" || ips="${ips}:"
	[ "$xnetmask" != "" ] && ips="${ips}${xnetmask}:" || ips="${ips}:"
	[ "$xhostname" != "" ] && ips="${ips}${xhostname}:" || ips="${ips}:"
	ips=${ips%:}
	#echo "ipstatement: $ips"
	echo "$ips" >> /etc/initramfs-tools/initramfs.conf
    fi
    #
    # Configure dropbear if requested
    #
    if [ $xssh -eq 1 ]
    then
	echo "> Configure SSH"
	sed -i "s#\#DROPBEAR_OPTIONS=\"\"#DROPBEAR_OPTIONS=\"-I $xsshtimeout -j -k -s -p $xsshport -c bash -r /etc/dropbear/dropbear_ed25519_host_key\"#" /etc/dropbear/initramfs/dropbear.conf
	echo "> Copy authorized keys file from '$xauthkeys'"
	cp $xauthkeys /etc/dropbear/initramfs/authorized_keys
	if [ $xunique -eq 0 ]
	then
	    echo "> Convert openSSH host key for use in dropbear/initramfs"
	    dropbearconvert openssh dropbear /etc/ssh/ssh_host_ed25519_key /etc/dropbear/initramfs/dropbear_ed25519_host_key
	else
	    echo "> Use unique SSH host key in dropbear/initramfs"
	fi
    fi
}

function domkinitramfs() {
    echo "> Update initramfs with the rootfs encryption settings in place"
    logifsdm "Update initramfs with the rootfs encryption settings in place"
    touch /usr/local/bin/sdmnull  # Used for nopwd
    update-initramfs -u
    rm -f /usr/local/bin/sdmnull
}

function doupdateconfig() {
    local rootfs kfu="" kfuuid="none"

    rootfs=$(findmnt --noheadings --output source /)
    echo "> Update root statement in cmdline.txt"
    sed -i "s#root=[0-9a-zA-Z-]*[ =][0-9a-zA-Z-]* #root=/dev/mapper/$xmapper #" /boot/firmware/cmdline.txt
    echo "> Add cryptdevice '$xmapper' to cmdline.txt"
    # 'rw' needed so crypt device is mounted read/write
    sed -i "s#\$# rw cryptdevice=$rootfs:$xmapper#" /boot/firmware/cmdline.txt

    echo "> Updated cmdline:"
    cat /boot/firmware/cmdline.txt

    echo "> Update /etc/fstab for the encrypted rootfs"
    sed -i "s#PARTUUID=[0-9a-zA-Z-]* */ #/dev/mapper/$xmapper / #" /etc/fstab

    echo "> Update /etc/crypttab"
    if [ "$xkeyfile" != "" ]
    then
	kfuuid=$(basename $xkeyfile)
	kfuuid=${kfuuid%.lek}
	kfu=",keyscript=/usr/bin/sdmluksunlock"
    fi
    echo "$xmapper	$rootfs $kfuuid luks,discard${kfu}" >> /etc/crypttab
}

#
# Main code
#
xauthkeys=""
xcrypto=""
xdns=""
xgateway=""
xhostname=""
xipaddr=""
xkeyfile=""
xmapper=""
xnetmask=""
xnopwd=0
xquiet=0
xreboot=0
xsdm=0
xssh=0
xsshbash=0
xsshport="22"
xsshtimeout="300"
xunique=0
src=$(dirname "$(realpath "$0")")
parsecmd $0 "$*"

[ "$xmapper" == "" ] && xmapper="cryptroot"
[ "$xcrypto" == "" ] && xcrypto="aes"
[[ "aes|xchacha" =~ $xcrypto ]] || [[ "$xcrypto" =~ aes- ]] || errexit "? Unrecognized crypto '$xcrypto'; Supported --crypto cryptos are 'aes' and 'xchacha'"
if [ "$xkeyfile" != "" ]
then
    mkdir -p /etc/sdm/assets/cryptroot
    [ ! -f /etc/sdm/assets/cryptroot/$xkeyfile ] && cp $xkeyfile /etc/sdm/assets/cryptroot
    xkeyfile="$(basename $xkeyfile)"
fi

echo "$xmapper" > /etc/mappername
echo "$xcrypto" > /etc/sdmcrypto
echo "$xkeyfile" > /etc/sdmkeyfile

if [ $xsdm -eq 0 ]
then
    if [ ! -f /usr/local/bin/sdmcryptfs ]
    then
	if [ -f $src/sdmcryptfs ]
	then
	    echo "> Copy sdmcryptfs from $src"
	    cp $src/sdmcryptfs /usr/local/bin
	else
	    echo "> Copy sdmcryptfs from GitHub"
	    curl --fail --silent --show-error -L https://github.com/gitbls/sdm/raw/master/sdmcryptfs -o /usr/local/bin/sdmcryptfs
	    chmod 755 /usr/local/bin/sdmcryptfs
	fi
    fi
fi
logifsdm "Starting; System will restart automatically when complete"

for o in doapt config mkinitramfs updateboot
do
    case "$o" in
	doapt)
	    [ $xssh -eq 1 ] && db="dropbear-initramfs dropbear-bin" || db=""
	    apps="cryptsetup cryptsetup-initramfs cryptsetup-bin $db"
	    echo "Install $apps"
	    if [ $xssh -eq 1 ]
	    then
		echo ""
		echo "** Ignore dropbear WARNINGs about authorized_keys file **"
		echo "   initramfs will be rebuilt with the authorized_keys file later"
		echo ""
		sleep 5
	    fi
	    apt install --no-install-recommends --yes $apps
	    ;;
	config)
	    doconfiginitramfs
	    ;;
	mkinitramfs)
	    domkinitramfs
	    ;;
	updateboot)
	    doupdateconfig
	    configcleanupsvc
	    ;;
    esac
done
if [ $xsdm -eq 1 ]
then
    #
    # if started via sdm, clean up
    #
    systemctl disable sdm-auto-encrypt > /dev/null 2>&1
    rm -f /etc/systemd/system/sdm-auto-encrypt.service
else
    if [ -f /usr/bin/startlxde-pi ]
    then
	#
	# Desktop. Enable console boot and modify quietness unless --quiet
	#
	echo "> Enable console boot for next system restart; will be reset to graphical subsequently"
	systemctl set-default multi-user.target
	if [ $xquiet -eq 0 ]
	then
	    echo "> Enable verbose system restart"
	    sed -i "s/ quiet//g" /boot/firmware/cmdline.txt
	    sed -i "s/ splash//g" /boot/firmware/cmdline.txt
            for svc in plymouth-start plymouth-read-write plymouth-quit plymouth-quit-wait plymouth-reboot
            do
                systemctl mask $svc >/dev/null 2>&1
            done
	fi
    fi
    printinfo
fi

if [ $xreboot -eq 1 ]
then
    wait_startup_complete "sdm-cryptoconfig: Wait for system startup to complete"
    secs=10
    logger "sdm-cryptconfig: System will restart in $secs seconds"
    echo "" > /dev/console
    echo "sdm-cryptconfig: System will restart in $secs seconds" > /dev/console
    sleep $secs
    logger "sdm-cryptconfig: System restarting now"
    echo "sdm-cryptconfig: System restarting now" > /dev/console
    sleep 2
    reboot
fi
exit 0
