143 lines
3.9 KiB
Bash
Executable File
143 lines
3.9 KiB
Bash
Executable File
#!/bin/sh
|
|
# Report unavailable capabilities as SKIP. In strict mode, each SKIP is an error.
|
|
set -u
|
|
|
|
binary=${1:-}
|
|
strict=0
|
|
if [ "${1:-}" = "--strict" ]; then
|
|
strict=1
|
|
shift
|
|
binary=${1:-}
|
|
fi
|
|
|
|
failures=0
|
|
skips=0
|
|
passes=0
|
|
|
|
pass() {
|
|
passes=$((passes + 1))
|
|
printf 'PASS: %s\n' "$*"
|
|
}
|
|
|
|
skip() {
|
|
skips=$((skips + 1))
|
|
printf 'SKIP: %s\n' "$*"
|
|
}
|
|
|
|
fail() {
|
|
failures=$((failures + 1))
|
|
printf 'FAIL: %s\n' "$*" >&2
|
|
}
|
|
|
|
need_command() {
|
|
command -v "$1" >/dev/null 2>&1
|
|
}
|
|
|
|
if [ -n "$binary" ]; then
|
|
if [ ! -x "$binary" ]; then
|
|
fail "latchd binary is not executable: $binary"
|
|
else
|
|
pass "latchd binary is available"
|
|
fi
|
|
else
|
|
skip "latchd binary not supplied; capability-only probe"
|
|
fi
|
|
|
|
# This checks the PAM runtime only. Authentication requires a test account and policy.
|
|
if need_command ldconfig && ldconfig -p 2>/dev/null | grep -q 'libpam\.so'; then
|
|
pass "PAM runtime library is available"
|
|
else
|
|
skip "PAM runtime library is unavailable"
|
|
fi
|
|
if [ -n "$binary" ] && need_command nm && nm -D "$binary" 2>/dev/null | grep -q 'pam_chauthtok'; then
|
|
pass "PAM password-change entry point is linked"
|
|
else
|
|
skip "PAM password-change entry point could not be inspected"
|
|
fi
|
|
if [ -r /etc/pam.d/latchd ]; then
|
|
pass "latchd PAM policy is installed"
|
|
else
|
|
skip "latchd PAM policy is not installed (authentication E2E requires a provisioned VM)"
|
|
fi
|
|
if need_command faillock; then
|
|
pass "faillock helper is available"
|
|
else
|
|
skip "faillock helper is unavailable"
|
|
fi
|
|
|
|
# A pseudo-terminal does not test VT allocation by the host or VM.
|
|
if [ -c /dev/tty0 ] && [ -d /sys/class/tty/tty0 ]; then
|
|
pass "Linux virtual terminal device is available"
|
|
else
|
|
skip "Linux virtual terminal is unavailable (container or non-console host)"
|
|
fi
|
|
|
|
# Xvfb tests X11 without access to the host display.
|
|
if need_command Xvfb; then
|
|
display_number=$((100 + ($$ % 500)))
|
|
display=":$display_number"
|
|
xlog=${TMPDIR:-/tmp}/latchd-xvfb.$$.log
|
|
Xvfb "$display" -screen 0 640x480x24 -nolisten tcp >"$xlog" 2>&1 &
|
|
xvfb_pid=$!
|
|
cleanup_xvfb() {
|
|
kill "$xvfb_pid" >/dev/null 2>&1 || true
|
|
wait "$xvfb_pid" >/dev/null 2>&1 || true
|
|
rm -f "$xlog"
|
|
}
|
|
trap cleanup_xvfb EXIT HUP INT TERM
|
|
ready=0
|
|
i=0
|
|
while [ "$i" -lt 20 ]; do
|
|
if [ -S "/tmp/.X11-unix/X$display_number" ] && kill -0 "$xvfb_pid" 2>/dev/null; then
|
|
ready=1
|
|
break
|
|
fi
|
|
i=$((i + 1))
|
|
sleep 0.1
|
|
done
|
|
if [ "$ready" -eq 1 ]; then
|
|
pass "X11 server starts in an isolated display ($display)"
|
|
else
|
|
fail "Xvfb did not start; see $xlog"
|
|
fi
|
|
cleanup_xvfb
|
|
trap - EXIT HUP INT TERM
|
|
else
|
|
skip "Xvfb is unavailable"
|
|
fi
|
|
|
|
# A compositor must own the Wayland socket. Installed client libraries are not sufficient.
|
|
wayland_socket=
|
|
if [ -n "${WAYLAND_DISPLAY:-}" ] && [ -n "${XDG_RUNTIME_DIR:-}" ]; then
|
|
case "$WAYLAND_DISPLAY" in
|
|
/*) wayland_socket=$WAYLAND_DISPLAY ;;
|
|
*) wayland_socket=$XDG_RUNTIME_DIR/$WAYLAND_DISPLAY ;;
|
|
esac
|
|
fi
|
|
if [ -n "$wayland_socket" ] && [ -S "$wayland_socket" ]; then
|
|
pass "Wayland compositor socket is available ($wayland_socket)"
|
|
else
|
|
skip "Wayland compositor socket is unavailable (requires a compositor-backed VM/session)"
|
|
fi
|
|
|
|
# Check loginctl only when systemd-logind is available.
|
|
if need_command loginctl && [ -d /run/systemd/system ]; then
|
|
if loginctl --no-pager show-seat seat0 >/dev/null 2>&1; then
|
|
pass "systemd-logind seat0 is reachable"
|
|
else
|
|
fail "systemd-logind is present but seat0 is not reachable"
|
|
fi
|
|
else
|
|
skip "systemd-logind seat0 is unavailable"
|
|
fi
|
|
|
|
printf 'E2E summary: pass=%s skip=%s fail=%s\n' "$passes" "$skips" "$failures"
|
|
if [ "$failures" -ne 0 ]; then
|
|
exit 1
|
|
fi
|
|
if [ "$strict" -eq 1 ] && [ "$skips" -ne 0 ]; then
|
|
echo "E2E strict mode: unavailable capabilities are errors" >&2
|
|
exit 2
|
|
fi
|
|
exit 0
|