Quand j’utilise mon portable sur mon bureau je le connecte souvent à un moniteur externe en HDMI. Par défaut sous ArchLinux la sortie est clonée et pas à la bonne résolution, ce n’est pas vraiment le but recherché et l’idéal est d’avoir un bureau étendu. Pendant un moment j’utilisais un script que je lançais à la main à chaque fois que je branchais cet écran, pas très pratique mais efficace. Depuis peu j’ai trouvé une solution plutôt intéressante en utilisant les évènements UDEV.

L’idée est tout simplement de lancer un script quand on branche la prise HDMI. Pour connaître quel type évènement est déclenché lors du branchement on utilise le moniteur fourni avec UDEV et ensuite brancher l’écran:

sudo udevadm monitor
monitor will print the received events for:
UDEV - the event which udev sends out after rule processing
KERNEL - the kernel uevent

KERNEL[116342.884117] change /devices/pci0000:00/0000:00:02.0/drm/card0 (drm)
UDEV [116342.886074] change /devices/pci0000:00/0000:00:02.0/drm/card0 (drm)

L’évènement est donc change , cela nous permet d’écrire la règle suivante dans /etc/udev/rules.d/70-persistent-monitor.rules

KERNEL=="card0", SUBSYSTEM=="drm", ACTION=="change", RUN+="su yadomi -c /chemin/vers/le/script.sh"

yadomi correspond à votre nom d’utilisateur, le script a besoin des droits. Une fois que ceci est en place, dès qu’un écran sera branché, le script (script.sh définit dans la règles UDEV) sera exécuté. Il est donc facile d’écrire un script utilisant XRandR pour définir les paramètres de l’écran qui vient d’être branché.

Voila à quoi ressemble mon script.sh:

#!/bin/bash
is_connected=`cat /sys/devices/pci0000:00/0000:00:02.0/drm/card0/card0-HDMI-A-1/status` 
if ["$is_connected" = "connected"]; then
	vendor=`parse-edid /sys/devices/pci0000:00/0000:00:02.0/drm/card0/card0-HDMI-A-1/edid 2>/dev/null | awk -F '"' '/VendorName/ {print $2}'`
	model=`parse-edid /sys/devices/pci0000:00/0000:00:02.0/drm/card0/card0-HDMI-A-1/edid 2>/dev/null | awk -F '"' '/ModelName/ {print $2}'`
	if [-n "$model"] && [-n "$vendor"]; then
		if ["$model" = "HP w2228h"] && ["$vendor" = "HWP"]; then
			xrandr --output HDMI1 --primary --mode 1680x1050 --left-of LVDS1 
			#xrandr --output HDMI1 --left-of LVDS1
		fi
	fi
else
	xrandr --output LVDS1 --mode 1366x768 --output HDMI1 --off
fi

parse-edid permet de retourner des informations sur l’écran, cela permet de définir par exemple une résolution spécifique à tel écran et pas un autre. Il fait partit du paquet read-edid

Voila, c’est plutôt simple à mettre en place et cela permet d’avoir un genre de profile pour chaque écrans. On pourrait également utiliser les layouts de ARandR et les appliqués à la volé.