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

Daemon mode causes stuttering when two monitors are connected #19

Closed
thiagokokada opened this issue Nov 7, 2017 · 6 comments
Closed

Comments

@thiagokokada
Copy link

thiagokokada commented Nov 7, 2017

Firstly, great project. mons is exactly what I needed to manage multiple monitors using i3wm.

To the issue I am having: running mons in daemon mode with two monitors cause a small stuttering each dozen of seconds, that is quite noticiable when watching a video. The issue seems to be xrandr itself, that causes this stuttering when two monitors are enabled, however if only one monitor is connected there is no problem. To easily reproduce the problem, you can run in a terminal;

while true; do xrandr; done

With two monitor connected, open a video in YouTube for example. The frame rate is completely choppy. Of course, mons runs xrandr in a much slower rate (each 3 seconds it seems by looking at the code), however it is still distracting.

I don't know a good solution. Maybe this could be fixable in xrandr itself, maybe not. Or there could be another way to query the connected monitors instead of using xrandr. Any ideas?

@Ventto
Copy link
Owner

Ventto commented Nov 12, 2017

Hi @m45t3r, thanks for the feedback.

Indeed, I came across the problem as well. Few weeks ago, I tried the deamon mode on two different computers, but I couldn't reproduce that stuttering.

After an investigation:

  • EDID is a data structure provided by a digital display to describe its capabilities to a video source
  • After plugging-in a monitor, a file called edid is created in /sys/class/drm/*/.

Inconvenience:

  • If your driver doesn't use/support DRM, you won't get it
  • Some amplificators are considered as monitors, causing edid file creation as well

The juice is worth the squeeze and I can't keep using xrandr after getting such a stuttering.
So a first workaround would be:

prev=0; i=0
while true; do
    for edid in /sys/class/drm/*/edid; do
        [ -n "$(cat "$edid")" ] && i=$((i+1))
    done
    [ "$i" -eq 1 ] && [ "$i" != "$prev" ] && "${XRANDR}" --auto 
    prev="$i"; i=0
    sleep 2
done

Ventto pushed a commit that referenced this issue Nov 12, 2017
Signed-off-by: Thomas Venriès <thomas.venries@gmail.com>
@thiagokokada
Copy link
Author

Looks good, however I am getting the following warning though:

./mons: line 244: warning: command substitution: ignored null byte in input

And btw, there is another interesting file in this directory:

$ cat /sys/class/drm/card0-eDP-1/enabled 
enabled

$ cat /sys/class/drm/card0-HDMI-A-1/enabled 
disabled

In fact, this seems to be a good choice for detecting connect/disconnect monitors, since my eDP entry is enabled and HDMI were disabled in the above case.

@Ventto
Copy link
Owner

Ventto commented Nov 13, 2017

Warning message, but does it work ?
What is your /bin/sh ?

Try to replace this:

[ -n "$(cat "$edid")" ] && i=$((i+1))

With this:

[ -n "$(<"$edid")" ] && i=$((i+1))

It avoids both forking a subshell and executing the /bin/cat non-builtin command.

@thiagokokada
Copy link
Author

thiagokokada commented Nov 13, 2017

In Arch Linux, {/usr}/bin/sh points to bash:

$ pacman -Qo /usr/bin/sh
/usr/bin/sh is owned by bash 4.4.012-2

Btw, even changing the line I as suggested:

[ -n "$(<"$edid")" ] && i=$((i+1))

I get the same error. However, this seems to work though:

# Daemon mode
if $aFlag ; then
    prev=0; i=0
    while true; do
        for status in /sys/class/drm/*/status; do
            [ "$(<"$status")" = "connected" ] && i=$((i+1))
        done
        if [ "$i" -eq 1 ] && [ "$i" != "$prev" ]; then
            "${XRANDR}" --auto --dpi "${dpi}"
        fi
        prev="$i"; i=0
        sleep 2
    done
fi

BTW, /sys/class/drm/*/status seems to return connected or disconected, exactly what we want (and without relaying in EDID support).

@Ventto
Copy link
Owner

Ventto commented Nov 13, 2017

Sold !
I had chosen edid to avoid extending the door for non-monitor devices.
Hoping that the check on status file (which is more generic) does the job for everyone.

Ventto pushed a commit that referenced this issue Nov 13, 2017
Signed-off-by: Thomas Venriès <thomas.venries@gmail.com>
@thiagokokada
Copy link
Author

Thanks @Ventto.

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

No branches or pull requests

2 participants