commit:     1d79338fa7391f8bc41bb74411c9a955e24d81cd
Author:     Thomas Deutschmann <whissi <AT> gentoo <DOT> org>
AuthorDate: Tue Aug  6 18:04:20 2019 +0000
Commit:     Thomas Deutschmann <whissi <AT> gentoo <DOT> org>
CommitDate: Wed Aug  7 15:03:44 2019 +0000
URL:        https://gitweb.gentoo.org/proj/genkernel.git/commit/?id=1d79338f

initrd.scripts: prompt_user(): Read answer from $GK_PROMPT_FILE on timeout

This commit will bring back read timeout which was removed in
Commit a280829. Read timeout is still disabled by default but
can now be controlled via gk.prompt.timeout kernel command-line
argument.

When gk.prompt.timeout is != 0, the current prompt will be written
to $GK_PROMPT_FILE. This will allow remote user to notice that
there's a prompt.

In addition, on timeout, $GK_PROMPT_FILE will be read allowing
remote user to answer prompt and hopefully to fix the problem
and resume booting.

To make this work, gk.prompt.timeout will be set to 30 seconds
by default when SSH usage is enabled.

Signed-off-by: Thomas Deutschmann <whissi <AT> gentoo.org>

 defaults/initrd.defaults |  2 ++
 defaults/initrd.scripts  | 36 ++++++++++++++++++++++++++++++------
 defaults/linuxrc         | 10 ++++++++++
 doc/genkernel.8.txt      |  9 +++++++++
 4 files changed, 51 insertions(+), 6 deletions(-)

diff --git a/defaults/initrd.defaults b/defaults/initrd.defaults
index 553600d..06057d7 100644
--- a/defaults/initrd.defaults
+++ b/defaults/initrd.defaults
@@ -85,6 +85,8 @@ GK_NET_TIMEOUT_DAD=10
 GK_NET_TIMEOUT_DECONFIGURATION=10
 GK_NET_TIMEOUT_DHCP=10
 GK_NET_TIMEOUT_INTERFACE=10
+GK_PROMPT_FILE='/tmp/current_prompt'
+GK_PROMPT_TIMEOUT=0
 GK_SHELL_LOCKFILE='/tmp/rescueshell.lock'
 GK_SSHD_LOCKFILE='/tmp/remote-rescueshell.lock'
 GK_SSHD_PIDFILE='/var/run/dropbear.pid'

diff --git a/defaults/initrd.scripts b/defaults/initrd.scripts
index 68adfb9..88046b4 100644
--- a/defaults/initrd.scripts
+++ b/defaults/initrd.scripts
@@ -1108,12 +1108,30 @@ prompt_user() {
        bad_msg '- type "shell" for a shell'
        bad_msg '- type "q" to skip ...'
        printf "%s" "${2}(${oldvalue}) :: "
-       read ${1}
-       #if [ $? -gt 0 ]
-       #then
-       #       # prompt timed out
-       #       printf "\n"
-       #fi
+
+       if [ "${GK_PROMPT_TIMEOUT}" = '0' ]
+       then
+               read ${1}
+       else
+               local read_timeout_timestamp
+               let read_timeout_timestamp=$(date +%s)+${GK_PROMPT_TIMEOUT}
+
+               echo "# Could not find the ${2} in ${oldvalue}${explnt}" > 
"${GK_PROMPT_FILE}"
+               echo "# Please specify another value (file will be processed at 
$(date -d @${read_timeout_timestamp}):" >> "${GK_PROMPT_FILE}"
+               echo "${1}=${oldvalue}" >> "${GK_PROMPT_FILE}"
+               read -t ${GK_PROMPT_TIMEOUT} ${1}
+               if [ $? -gt 0 ]
+               then
+                       # prompt timed out
+                       printf "\n"
+
+                       if [ -f "${GK_PROMPT_FILE}" ]
+                       then
+                               warn_msg "Timeout! Trying to read answer from 
'${GK_PROMPT_FILE}' ..."
+                               . "${GK_PROMPT_FILE}" && run rm 
"${GK_PROMPT_FILE}"
+                       fi
+               fi
+       fi
 
        case $(eval echo '$'${1}) in
                'q')
@@ -2145,6 +2163,12 @@ start_sshd() {
                return
        fi
 
+       if [ "${GK_PROMPT_TIMEOUT}" = '0' ]
+       then
+               warn_msg "Changing gk.prompt.timeout=0 to 30 ..."
+               GK_PROMPT_TIMEOUT=30
+       fi
+
        if [ ! -x "/usr/sbin/dropbear" ]
        then
                bad_msg "/usr/sbin/dropbear not found! Did you call genkernel 
with --ssh parameter?"

diff --git a/defaults/linuxrc b/defaults/linuxrc
index b2ac54e..a57de1c 100644
--- a/defaults/linuxrc
+++ b/defaults/linuxrc
@@ -336,6 +336,16 @@ do
                        fi
                        unset tmp_wait
                ;;
+               gk.prompt.timeout=*)
+                       tmp_timeout=${x#*=}
+                       if is_int "${tmp_timeout}"
+                       then
+                               GK_PROMPT_TIMEOUT=${tmp_timeout}
+                       else
+                               warn_msg "'${x}' does not look like a valid 
time (second) value -- ignored!"
+                       fi
+                       unset tmp_timeout
+               ;;
                real_rootflags=*)
                        REAL_ROOTFLAGS=${x#*=}
                ;;

diff --git a/doc/genkernel.8.txt b/doc/genkernel.8.txt
index 3ab28ce..3ebd320 100644
--- a/doc/genkernel.8.txt
+++ b/doc/genkernel.8.txt
@@ -687,6 +687,15 @@ recognized by the kernel itself.
 *gk.net.timeout.interface*=<...>::
     By default we will wait up to 10 seconds for interface to show up.
 
+*gk.prompt.timeout*=<...>::
+By default a prompt within genkernel initramfs like shown when set
+*root* could not be found will never timeout. Use this option to set
+a timeout.
+
+NOTE: When *dosshd* is used, *gk.prompt.timeout* will be set to 30 seconds
+when not set. This will allow remote user to provide answer through
+*GK_PROMPT_FILE* which is set to '/tmp/current_prompt' by default.
+
 *dosshd*::
     Will bring up an interface and start a SSH daemon within initramfs
     allowing to remotely unlock encrypted devices or just for debugging

Reply via email to