Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

SIGUSR1 gets queued up when idle inhibitor is active #51

Open
daenney opened this issue Jan 2, 2020 · 6 comments
Open

SIGUSR1 gets queued up when idle inhibitor is active #51

daenney opened this issue Jan 2, 2020 · 6 comments

Comments

@daenney
Copy link

daenney commented Jan 2, 2020

This one's a bit peculiar. When an idle inhibitor is active (I use Waybar's idle_inhibitor module for this, which uses the associated Wayland protocol) sending a SIGUSR1 to swayidle does nothing (this is correct, since the system can't be considered idle). However, the second you turn off the idle inhibitor swayidle believes the system is idle, and thus locks.

I think this is confusing and unexpected, especially since idle inhibition can be active for long periods of time after which your system might surprise lock on you if you forgot you triggered swayidle some way (for example through a lockcmd shortcut in sway).

I would expect that while the idle inhibitor is active, swayidle would discard requests to enter idle state, instead of seemingly delaying processing them.

~ ❯❯❯ /usr/bin/swayidle -w -d \
      timeout 300 'swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png' \
      timeout 600 'swaymsg "output * dpms off"' \
      resume 'swaymsg "output * dpms on"' \
      lock 'swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png' \
      before-sleep 'swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png'
Got timeout
Register idle timeout at 300000 ms
Setup idle
Command: swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png
Got timeout
Register idle timeout at 600000 ms
Setup idle
Command: swaymsg "output * dpms off"
Setup resume
Command: swaymsg "output * dpms on"
Got lock
Command: swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png
Setup lock hook: swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png
Got before-sleep
Command: swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png
Setup sleep lock: swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png
Got sleep lock: 11
Register with timeout: 600000
Register with timeout: 300000

---> Sent SIGUSR1

Got SIGUSR1
Register with timeout: 0
Register with timeout: 0
idle state
Cmd exec swaymsg "output * dpms off"
Spawned process swaymsg "output * dpms off"
idle state
Cmd exec swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png
Spawned process swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png
active state
Register with timeout: 600000
Cmd exec swaymsg "output * dpms on"
Spawned process swaymsg "output * dpms on"
active state
Register with timeout: 300000

---> Activate Idle inhibitor
---> Sent SIGUSR1

Got SIGUSR1
Register with timeout: 0
Register with timeout: 0

---> Deactivate idle inhibitor

idle state
Cmd exec swaymsg "output * dpms off"
Spawned process swaymsg "output * dpms off"
idle state
Cmd exec swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png
Spawned process swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png
active state
Register with timeout: 600000
Cmd exec swaymsg "output * dpms on"
Spawned process swaymsg "output * dpms on"
active state
Register with timeout: 300000

If I send multiple SIGUSR1's while the idle inhibitor is active you get this instead:

Got SIGUSR1
Register with timeout: 0
Register with timeout: 0
Got SIGUSR1
Register with timeout: 0
Register with timeout: 0
Got SIGUSR1
Register with timeout: 0
Register with timeout: 0
Got SIGUSR1
Register with timeout: 0
Register with timeout: 0

---> Deactivate idle inhibitor

idle state
Cmd exec swaymsg "output * dpms off"
Spawned process swaymsg "output * dpms off"
idle state
Cmd exec swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png
Spawned process swaylock -f -c 000000 -i /home/daenney/Pictures/Rainbow_Dash_Wallpaper.png
active state
Register with timeout: 600000
Cmd exec swaymsg "output * dpms on"
Spawned process swaymsg "output * dpms on"
active state
Register with timeout: 300000
@9p4
Copy link

9p4 commented Aug 18, 2021

Offending code seems to be in this function. Perhaps someone with a better understanding of C can help out?

https://github.com/swaywm/swayidle/blob/master/main.c#L852

@retropc
Copy link

retropc commented Feb 27, 2022

the current behaviour seems to make no sense, but I'm curious as to the thinking behind this @daenney :

When an idle inhibitor is active (I use Waybar's idle_inhibitor module for this, which uses the associated Wayland protocol) sending a SIGUSR1 to swayidle does nothing (this is correct, since the system can't be considered idle).

personally: I want SIGUSR1 to lock the screen regardless of any inhibitors (as it's coming from me pressing my "lock screen now" hotkey)

the current behaviour SIGUSR1 seems completely broken (I suspect it predates the idle inhibitors entirely)

@retropc
Copy link

retropc commented Feb 27, 2022

as a note this happens because the trigger of the timeouts is done by the compositor

swayidle asks it to register a timeout 0ms in the future, and when idle is inhibited the compositor doesn't do anything until the inhibition disappears

@daenney
Copy link
Author

daenney commented Mar 12, 2022

personally: I want SIGUSR1 to lock the screen regardless of any inhibitors (as it's coming from me pressing my "lock screen now" hotkey)

Yeah, I agree with that, it would make sense for that to always work.

@mattfbacon
Copy link

It's unclear to me why USR1 shouldn't be handled by just running the timeout commands directly, i.e., why does it go through the compositor and the idle notifications at all?

@mattfbacon
Copy link

OK, I can identify one issue. If we do handle_idled(cmd, NULL) instead of register_timeout(cmd, 0), then the resume commands never run. This is logical because if we use register_timeout we rely on the compositor to tell us when the system "wakes up". On the other hand, if we just run the idle commands directly with handle_idled, the resume commands will be enabled, but never actually run. This is tricky, because from sway's perspective, the system may not actually be "idle", i.e., there may have been inhibitors that sway-idle bypassed. Regardless, this means the system will also never leave idle, so we can't use that event.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

No branches or pull requests

4 participants