Introduction
Dans cet article je vais racconter comment j’ai galéré pour faire sortir un esperluette (&) à ma Yubikey.
Je dois depuis quelques temps travaillé sous Windows (arg…) et tapé plusieurs fois par jours une certaine chaine de caractère assez longue et complexe (je n’entrerais pas dans les détails ☺). Pour me « simplifier la vie » j’ai décidé d’utiliser ma Yubikey en mode « static password » pour générer cette séquence de caractères.
Dans l’article gestion du clavier sous GNU/Linux je détailles ce que sont les scancodes et keycodes, ainsi que leurs différents types.
L’interface graphique de configuration de la Yubikey yubikey-personalization-gui
permet de configurer la yubikey en mode « static password » mais avec le layout qwerty.
En fait, on écrit sont text dans un champ dédié et le logiciel traduit ce text en scancode en se basant sur une table de convertion qwerty.
Donc si je configure ma yubikey après avoir écrit « q » dans ce champ, j’obtiendrait un « q » si je suis en qwerty au moment ou j’appui sur le bouton de la yubikey, un « a » si je suis en azerty, un « b » si je suis en bépo…
Une astuce consiste à passer en qwerty et taper son text sur le clavier au layout désiré (disont bépo) sans se soucié de ce qui va être entré dans le champs de text.
Normalement la convertion text → scancode qui sera faite par yubikey-personalization-gui
donnera le bon text dans le layout bépo.
Par exemple, j’utilise abituellement un layout bépo, je veux que ma yubikey génère la séquence « bépo » (pour faire simple).
Je me met temporairement en layout qwerty et après mettre placé dans le champ text, j’appui sur les touche « bépo » sur mon clavier bépo.
Dans le champ, le text « qwer » s’affiche (normal je suis en qwerty).
Je configure la Yubikey avec ce champ text qui sera traduit par le logiciel en « scancode des quatre première touche de lettre clavier », ce qui nous donne « bépo » dans un layout bépo.
Cette technique montre rapidement ses limites, notamment quand on veut généré des chiffre ou des caractères spéciaux.
L’outil ykpersonalize
en ligne de commande est plus compliqué à manier mais beaucoup plus puissant.
Il permet par exemple de configurer la yubikey en lui indiquant directement les scancodes à retourner… enfin pas tout à fait, mais j’y viens.
max@laptop % ykpersonalize -1 -v -oshort-ticket -ofixed=h:141a0815 -a00000000000000000000000000000000
max@laptop % ykpersonalize -2 -v -oshort-ticket -ofixed=h:141a0815 -a00000000000000000000000000000000 -o-static-ticket -o-strong-pw1 -o-strong-pw2 -o-man-update
Les deux commande précédente permettent respectivement de configurer les slot 1 et 2 de la yubikey avec les scancode des quatres première touche de lettre du clavier. Explications :
-1
,-2
permet de selectionner le slot-v
plus verbeux, permet de voir ce qui se passe-oshort-ticket
lorsque cette option est utilisée sans être accompagnée de l’option-ostatic-ticket
cela permet de programmer la yubikey en mode static password en spécifiant directement les scancodes désiré. Attention, ce n’est pas dans le man mais comme indiqué dans la section-ostatic-ticket
du man avec-oshort-ticket
le mot de passe généré par la yubikey est toujours basé sur la clé AES. Pour faire en sorte que les sancodes programé ne soit pas mixé avec la clé AES et ne génère n’importe quoi il faut indiquer une clé AES null-a
permet d’indiqué une clé AES. Si cette option est omise, une clé AES aléatoire est générée. Pour avoir une clé AES null il faut utilisera00000000000000000000000000000000
-ofixed
permet de spécifier l’identifiant publique de la clé (0 à 32 caractères), c’est la chaine de caractère qui ne change jamais au début de chaque OTP. Ici vu qu’on veut généré un mot de passe statique on n’utilise que cette identifiant publique.h:
permet de spécifié les scancode en hexadécimal. Pour configurer la Yubikey il faut utiliser les scancodes USB étant donné que c’est un device USB. 0x14, 0x1a, 0x08 et 0x15 sont respectivement les scancode USB des quatres première touche de lettre du clavier.-o-static-ticket -o-strong-pw1 -o-strong-pw2 -o-man-update
: lorsqu’on selectionne la slot 2 les options append-cr, static-ticket, strong-pw1, strong-pw2 et man-update sont activé par défaut. Je désactive tout, excepté append-cr qui est utile et aussi présent par défaut avec le slot 1. En effet short-ticket ne doit pas être accompagné de static-ticket pour permettre une configuration via scancodes.
Ci dessus j’indique que ykpersonalize
permet de configurer la yubikey en lui indiquant directement les scancodes à retourner, mais pas tout à fait.
En fait lorsqu’on configure la Yubikey on ne spécifie que les scancode d’appui, la clé s’occupe elle même de trouver les scancode de relache… et c’est bien dommage.
En effet parfois on veut envoyer plusieurs scancode d’appui avec d’envoyer des relache, pour faire des combinaisons de touches, Shift+A, Ctrl+C, AltGr+p…
Pour indiqué à la yubikey qu’un scancode doit être précédé et suivit d’un appui et d’une relache de la touche Shift il faut ajouté 0x80 au scancode.
Par exemple le scancode pour « b » en bépo est 0x14, pour obtenir un « B » je doit paramétrer la Yubikey avec le scancode 0x94.
Il n’y a pas d’équivalent pour les autres touches, il est donc impossible de générer des combinaisons de touches avec Alt, AltGr ou quoique ce soit d’autre que Shift.
D’où mon problème avec le esperluette (&) car en bépo celui-ci se génére via la combinaisons de touches AltGr+p.
Pour le contourner j’ai utilisé le scancode de la touche scroll et remappé mon layout pour qu’à l’apparition de ce scancode le caractère « & » soit imprimé. Au début j’ai essayé d’utiliser la touche pause mais celle-ci à un scancode particulier qui est couplé avec numlock… bref je n’ai pas réussi à le remapper correctement sans effet de bord donc j’ai choisi d’utiliser la touche scroll.
remap sous Windows
Pour remapper un touche de clavier sous windows il existe plusieurs solutions :
- SharpKeys : utilise une méthode utilisant la base de registre. Malheureusement ça ne gère pas les combinaisons de touches.
- AutoHotkey : très puissant mais nécessite la présence constante du logiciel en mémoire… bref j’aime pas ça.
- MSKLC : permet de créer sont propre layout.
J’ai choisi d’utiliser MSKLC sachant que c’est la méthode principal détaillé dans la page wiki du pilote bépo Windows. Et qu’il y a même déjà une page expliquant comment modifier ce pilote.
J’ai d’abord téléchager et installé une VM Windows gratuite pour pouvoir faire la compilation et les tests.
Installer bepo.klc.
cygwin % PATH="$PATH":'/cygdrive/c/Program Files/Microsoft Keyboard Layout Creator 1.4/bin/i386'
cygwin % kbdutool.exe -u -s bepo.klc
-u
: spécifie que le fichier bepo.klc est en utf8-s
: ne génère pas directement directement la dll, uniquement les fichiers sources
Modifier les fichier bepo.H et bepo.C :
--- bepo-a/bepo.H 2015-10-19 13:29:49.140863200 -0700
+++ bepo-b/bepo.H 2015-10-19 10:54:03.717515200 -0700
@@ -100,4 +100,5 @@
#define T34 _EQ( 'H' )
#undef T35
#define T35 _EQ( 'F' )
-
+#undef T46
+#define T46 _EQ(NONAME)
--- bepo-a/bepo.C 2015-10-19 13:29:49.172047600 -0700
+++ bepo-b/bepo.C 2015-10-19 10:54:49.545518200 -0700
@@ -286,6 +286,7 @@
{0xff ,0 ,WCH_NONE ,WCH_NONE ,WCH_NONE ,0x02db ,WCH_NONE },
{VK_SPACE ,0 ,' ' ,0x00a0 ,WCH_NONE ,'_' ,0x202f },
{VK_DECIMAL ,0 ,'.' ,'.' ,WCH_NONE ,WCH_NONE ,WCH_NONE },
+ {VK_NONAME ,0 ,'&' ,WCH_NONE ,WCH_NONE ,WCH_NONE ,WCH_NONE },
{0 ,0 ,0 ,0 ,0 ,0 ,0 }
};
Explications : Dans le fichier bepo.H j’indique que le scancode de la touche scroll correspond au keycode de la touche « NONAME ». Dans le fichier bepo.C j’indique que le keycode de la touche « NONAME » (VK_NONAME) correspond au keysym « & ». Les quatres éléments suivant le « ’&‘ » sont les keysym généré lorsque la touche est accompagné respectivement de Shift, Ctrl, Ctrl+Alt, Shift+Ctrl+Alt.
Pour savoir que « T46 » correspond au scancode de la touche scroll, on peut aller voir dans le fichier suivant qui indique le mapping complet correspondant au clavier qwerty.
/cygdrive/c/Program Files/Microsoft Keyboard Layout Creator 1.4/inc/kbd.h
Pourquoi je m’enmerde à mapper le scancode sur le keycode NONAME si je peux assigner directement le keysym & au keycode VK_SCROLL ? D’après ce que j’ai compris, certain keycode déclanche des actions bien spécifique, par exemple VK_SNAPSHOT permet de prendre une capture d’écran, VK_NUMLOCK toggle le status numlock de windows… Si on assigne un keysym à ces keycode cela ne supprimera pas leurs actions pour autant. Par exemple si j’assigne « a » à VK_SNAPSHOT, appuyer sur la touche de snapshot écrira « a » à l’écran et prendra une capture d’écran. VK_SCROLL toggle le status scroll de windows, et le comportement d’Excel change en fonction de ce status. En plus chez moi, ça allume une led sur le clavier… et j’aime pas ça.
Donc ma solution a été d’assigner au scan code de la touche scroll un key code qui ne déclanche aucune action et qui n’est utilisé par aucun logiciel. D’après le listing des keycodes disponible sous Windows, VK_NONAME n’est pas utilisé on peut donc en faire ce qu’on veut pour l’instant… parfait !
Une fois les fichiers modifiés on empèche leurs modification et on lance la compilation :
cygwin % attrib.exe +R bepo.H
cygwin % attrib.exe +R bepo.C
cygwin % kbdutool.exe -u -x bepo.klc
-x
permet de compiler en pour du x86-m
permet de compiler en pour du amd64-i
permet de compiler en pour du ia64
Pour savoir si vous devez utiliser x, m ou i faite simplement un file
sur l’une des dll de System32 de votre système cible.
Par exemple, ici je vais utilisé la dll généré par l’option -x
:
cygwin % file /cygdrive/c/Windows/System32/kernel32.dll
/cygdrive/c/Windows/System32/kernel32.dll: PE32 executable (DLL) (console) Intel 80386, for MS Windows
cygwin % file bepo.dll.*
bepo.dll.i: PE32+ executable (DLL) (native) Intel Itanium, for MS Windows
bepo.dll.m: PE32+ executable (DLL) (native) x86-64, for MS Windows
bepo.dll.x: PE32 executable (DLL) (native) Intel 80386, for MS Windows
Attention si vous vous planté vous allez faire planté tous vos système de gestion de clavier. Ça veut dire plus de clavier du tous, quelque soit le layout… même pas de clavier virtuel… et bien on se sent bien con quant on a plus aucun clavier. Pour réparé il suffit d’utiliser un livecd et de supprimer la dll merdique.
Une fois qu’on a généré la dll du layout on peut la copier dans System32 à la place du layout bépo standard, et rebooter.
cygwin % cygstart --action=runas mv cygdrive/c/Windows/System32/bepo.dll{,.save}
cygwin % cygstart --action=runas cp bepo.dll cygdrive/c/Windows/System32/
Mais ce n’est pas fini ☺ Ça fonctionne très bien dans l’invite de commande windows (cmd) ou notepad… mais pas dans mintty, l’émulateur de terminal de cygwin. En fait il y a un bug dans mintty, celui-ci ne test le layout que pour certains keycode. J’ai fourni un patch au développeurs et espère qu’il sera intégré dans les prochaines versions (up : le patch est maintenant intégré et le bug n’éxiste plus).
diff --git a/src/wininput.c b/src/wininput.c
index 22c5db5..ebd975f 100644
--- a/src/wininput.c
+++ b/src/wininput.c
@@ -772,10 +772,9 @@ win_key_down(WPARAM wp, LPARAM lp)
else if (key <= '9') app_pad_code(key);
else if (VK_OEM_PLUS <= key && key <= VK_OEM_PERIOD)
app_pad_code(key - VK_OEM_PLUS + '+');
- when VK_PACKET:
- layout();
otherwise:
- return 0;
+ if (!layout())
+ return false;
}
Vous pouvez compiler facilement mintty sous cygwin en installant les paquets gcc-g++ et make.
Lancer simplement make
dans le répertoire des sources.