110 lines
1.9 KiB
Bash
Executable File
110 lines
1.9 KiB
Bash
Executable File
#!/bin/sh
|
|
|
|
EVENT=${1:-short-press}
|
|
|
|
LONG_PRESS_TIMEOUT=3 # s
|
|
DEBOUNCE=2 # s
|
|
PIDFILE="/tmp/$(basename $0).pid"
|
|
LOCKFILE=/tmp/.power_key
|
|
|
|
log()
|
|
{
|
|
logger -t $(basename $0) "[$$]: $@"
|
|
}
|
|
|
|
parse_wake_time()
|
|
{
|
|
RK_SUSPEND_STATE=/sys/kernel/wakeup_reasons/last_suspend_time
|
|
if ! [ -f "$RK_SUSPEND_STATE" ]; then
|
|
return -1
|
|
fi
|
|
|
|
SLEEP_TIME=$(sed 's/ /+/' "$RK_SUSPEND_STATE" | bc)
|
|
if [ "$SLEEP_TIME" = "0" ]; then
|
|
log "We have not slept before..."
|
|
return -1
|
|
fi
|
|
|
|
LAST_SUSPEND="$(stat -c "%Y" /sys/power/state)"
|
|
LAST_RESUME="$(echo "$LAST_SUSPEND+$SLEEP_TIME" | bc | cut -d'.' -f1)"
|
|
NOW="$(date "+%s")"
|
|
WAKE_TIME="$(( "$NOW" - "$LAST_RESUME" ))"
|
|
|
|
if [ "$WAKE_TIME" -lt 0 ]; then
|
|
log "Something is wrong, time changed?"
|
|
return -1
|
|
fi
|
|
|
|
log "Last resume: $(date -d "@$LAST_RESUME" "+%D %T")..."
|
|
}
|
|
|
|
short_press()
|
|
{
|
|
log "Power key short press..."
|
|
|
|
if which systemctl >/dev/null; then
|
|
SUSPEND_CMD="systemctl suspend"
|
|
elif which pm-suspend >/dev/null; then
|
|
SUSPEND_CMD="pm-suspend"
|
|
else
|
|
SUSPEND_CMD="echo -n mem > /sys/power/state"
|
|
fi
|
|
|
|
# Debounce
|
|
if [ -f $LOCKFILE ]; then
|
|
log "Too close to the latest request..."
|
|
return 0
|
|
fi
|
|
|
|
if parse_wake_time; then
|
|
if [ "$WAKE_TIME" -le $DEBOUNCE ]; then
|
|
log "We are just resumed!"
|
|
return 0
|
|
fi
|
|
fi
|
|
|
|
log "Prepare to suspend..."
|
|
|
|
touch $LOCKFILE
|
|
sh -c "$SUSPEND_CMD"
|
|
{ sleep $DEBOUNCE && rm $LOCKFILE; }&
|
|
}
|
|
|
|
long_press()
|
|
{
|
|
log "Power key long press (${LONG_PRESS_TIMEOUT}s)..."
|
|
|
|
log "Prepare to power off..."
|
|
|
|
poweroff
|
|
}
|
|
|
|
log "Received power key event: $@..."
|
|
|
|
case "$EVENT" in
|
|
press)
|
|
# Lock it
|
|
exec 3<$0
|
|
flock -x 3
|
|
|
|
start-stop-daemon -K -q -p $PIDFILE || true
|
|
start-stop-daemon -S -q -b -m -p $PIDFILE -x /bin/sh -- \
|
|
-c "sleep $LONG_PRESS_TIMEOUT; $0 long-press"
|
|
|
|
# Unlock
|
|
flock -u 3
|
|
;;
|
|
release)
|
|
# Avoid race with press event
|
|
sleep .5
|
|
|
|
start-stop-daemon -K -q -p $PIDFILE && short_press
|
|
;;
|
|
short-press)
|
|
short_press
|
|
;;
|
|
long-press)
|
|
long_press
|
|
;;
|
|
esac
|