mirror of
https://github.com/dockur/windows.git
synced 2026-08-03 20:47:12 +01:00
feat: Preserve graceful shutdown for interactive console (#1876)
This commit is contained in:
+7
-1
@@ -53,13 +53,19 @@ if ! enabled "$SHUTDOWN"; then
|
|||||||
exec "${cmd[@]}" ${ARGS:+ $ARGS} >"$pipe" 2>&1
|
exec "${cmd[@]}" ${ARGS:+ $ARGS} >"$pipe" 2>&1
|
||||||
fi
|
fi
|
||||||
|
|
||||||
"${cmd[@]}" ${ARGS:+ $ARGS} >"$pipe" 2>&1 &
|
if ! interactive; then
|
||||||
|
"${cmd[@]}" ${ARGS:+ $ARGS} >"$pipe" 2>&1 &
|
||||||
|
else
|
||||||
|
startConsole "$pipe"
|
||||||
|
setsid -w "${cmd[@]}" ${ARGS:+ $ARGS} </dev/null >"$pipe" 2>&1 &
|
||||||
|
fi
|
||||||
|
|
||||||
pid=$!
|
pid=$!
|
||||||
( sleep 30; boot ) &
|
( sleep 30; boot ) &
|
||||||
|
|
||||||
rc=0
|
rc=0
|
||||||
wait "$pid" || rc=$?
|
wait "$pid" || rc=$?
|
||||||
|
interactive && stopConsole
|
||||||
wait "$output" || :
|
wait "$output" || :
|
||||||
|
|
||||||
[ -f "$QEMU_END" ] && exit "$rc"
|
[ -f "$QEMU_END" ] && exit "$rc"
|
||||||
|
|||||||
+75
-7
@@ -6,13 +6,19 @@ set -Eeuo pipefail
|
|||||||
|
|
||||||
# Configure QEMU for graceful shutdown
|
# Configure QEMU for graceful shutdown
|
||||||
|
|
||||||
|
SHUTDOWN_SKIP=0
|
||||||
|
SHUTDOWN_SIGNAL=0
|
||||||
|
|
||||||
QEMU_PTY="$QEMU_DIR/qemu.pty"
|
QEMU_PTY="$QEMU_DIR/qemu.pty"
|
||||||
QEMU_END="$QEMU_DIR/qemu.end"
|
QEMU_END="$QEMU_DIR/qemu.end"
|
||||||
|
CONSOLE_PID="$QEMU_DIR/console.pid"
|
||||||
|
CONSOLE_SOCKET="$QEMU_DIR/console.sock"
|
||||||
|
|
||||||
_trap() {
|
_trap() {
|
||||||
|
|
||||||
local func="$1"; shift
|
local func="$1"; shift
|
||||||
local sig
|
local sig
|
||||||
|
|
||||||
TRAP_PID=$BASHPID
|
TRAP_PID=$BASHPID
|
||||||
|
|
||||||
for sig; do
|
for sig; do
|
||||||
@@ -174,8 +180,8 @@ cleanupHelpers() {
|
|||||||
|
|
||||||
local pids=( "${SMB_PID:-}" "${NMB_PID:-}" "${DDN_PID:-}" \
|
local pids=( "${SMB_PID:-}" "${NMB_PID:-}" "${DDN_PID:-}" \
|
||||||
"${TPM_PID:-}" "${WSD_PID:-}" "${WEB_PID:-}" \
|
"${TPM_PID:-}" "${WSD_PID:-}" "${WEB_PID:-}" \
|
||||||
"${AUX_PID:-}" "${AUDIO_PID:-}" "${PASST_PID:-}" \
|
"${AUX_PID:-}" "${AUDIO_PID:-}" "${CONSOLE_PID:-}" \
|
||||||
"${DNSMASQ_PID:-}" "${BALLOONING_PID:-}" )
|
"${PASST_PID:-}" "${DNSMASQ_PID:-}" "${BALLOONING_PID:-}" )
|
||||||
|
|
||||||
mKill "${pids[@]}"
|
mKill "${pids[@]}"
|
||||||
|
|
||||||
@@ -183,6 +189,55 @@ cleanupHelpers() {
|
|||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
startConsole() {
|
||||||
|
|
||||||
|
local cnt=0
|
||||||
|
local pid=""
|
||||||
|
local output="${1:-/dev/tty}"
|
||||||
|
|
||||||
|
rm -f -- "$CONSOLE_SOCKET" "$CONSOLE_PID"
|
||||||
|
|
||||||
|
if ! stty -icanon -echo isig -ixon min 1 time 0 </dev/tty; then
|
||||||
|
error "Failed to configure serial console terminal!"
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
(
|
||||||
|
trap '' INT QUIT
|
||||||
|
exec nc -lU "$CONSOLE_SOCKET" </dev/tty >"$output"
|
||||||
|
) &
|
||||||
|
|
||||||
|
pid=$!
|
||||||
|
echo "$pid" > "$CONSOLE_PID"
|
||||||
|
|
||||||
|
while [ ! -S "$CONSOLE_SOCKET" ]; do
|
||||||
|
|
||||||
|
if ! isAlive "$pid"; then
|
||||||
|
rm -f -- "$CONSOLE_PID"
|
||||||
|
error "Serial console relay exited unexpectedly!"
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
sleep 0.02
|
||||||
|
cnt=$((cnt + 1))
|
||||||
|
|
||||||
|
if (( cnt > 100 )); then
|
||||||
|
error "Failed to start serial console relay!"
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
done
|
||||||
|
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
|
stopConsole() {
|
||||||
|
|
||||||
|
mKill "$CONSOLE_PID"
|
||||||
|
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
finish() {
|
finish() {
|
||||||
|
|
||||||
local reason=$1
|
local reason=$1
|
||||||
@@ -276,7 +331,7 @@ waitForShutdown() {
|
|||||||
local name="$APP"
|
local name="$APP"
|
||||||
local slp
|
local slp
|
||||||
|
|
||||||
while (( cnt <= wait_until )); do
|
while (( cnt <= wait_until && SHUTDOWN_SKIP == 0 )); do
|
||||||
|
|
||||||
sleep 1 &
|
sleep 1 &
|
||||||
slp=$!
|
slp=$!
|
||||||
@@ -296,7 +351,7 @@ waitForShutdown() {
|
|||||||
|
|
||||||
sendAcpiShutdown
|
sendAcpiShutdown
|
||||||
|
|
||||||
wait "$slp"
|
wait "$slp" || :
|
||||||
(( cnt++ ))
|
(( cnt++ ))
|
||||||
|
|
||||||
done
|
done
|
||||||
@@ -315,20 +370,29 @@ graceful_shutdown() {
|
|||||||
code=$(signalCode "$sig")
|
code=$(signalCode "$sig")
|
||||||
|
|
||||||
if [ -f "$QEMU_END" ]; then
|
if [ -f "$QEMU_END" ]; then
|
||||||
echo && info "Received $1 signal while already shutting down..."
|
|
||||||
|
if (( code == 130 && SHUTDOWN_SIGNAL == code )); then
|
||||||
|
SHUTDOWN_SKIP=1
|
||||||
|
echo && info "Received SIGINT again, forcing shutdown..."
|
||||||
|
return
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo && info "Received $sig signal while already shutting down..."
|
||||||
return
|
return
|
||||||
fi
|
fi
|
||||||
|
|
||||||
set +e
|
set +e
|
||||||
|
SHUTDOWN_SIGNAL=$code
|
||||||
|
|
||||||
touch "$QEMU_END"
|
touch "$QEMU_END"
|
||||||
echo && info "Received $1 signal, sending ACPI shutdown signal..."
|
echo && info "Received $sig signal, sending ACPI shutdown signal..."
|
||||||
|
|
||||||
if ! readQemuPid pid; then
|
if ! readQemuPid pid; then
|
||||||
warn "QEMU PID file ($QEMU_PID) does not exist?"
|
warn "QEMU PID file ($QEMU_PID) does not exist?"
|
||||||
finish "$code"
|
finish "$code"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
if ! isAlive "$pid"; then
|
if [ -z "$pid" ] || ! isAlive "$pid"; then
|
||||||
warn "QEMU process with PID $pid does not exist?"
|
warn "QEMU process with PID $pid does not exist?"
|
||||||
finish "$code"
|
finish "$code"
|
||||||
fi
|
fi
|
||||||
@@ -346,6 +410,10 @@ graceful_shutdown() {
|
|||||||
! enabled "$SHUTDOWN" && return 0
|
! enabled "$SHUTDOWN" && return 0
|
||||||
[ -n "${QEMU_TIMEOUT:-}" ] && TIMEOUT="$QEMU_TIMEOUT"
|
[ -n "${QEMU_TIMEOUT:-}" ] && TIMEOUT="$QEMU_TIMEOUT"
|
||||||
|
|
||||||
|
if interactive; then
|
||||||
|
_trap graceful_shutdown SIGINT
|
||||||
|
fi
|
||||||
|
|
||||||
_trap graceful_shutdown SIGTERM SIGHUP SIGABRT SIGQUIT
|
_trap graceful_shutdown SIGTERM SIGHUP SIGABRT SIGQUIT
|
||||||
|
|
||||||
return 0
|
return 0
|
||||||
|
|||||||
Reference in New Issue
Block a user