ubuntuusers.de

Luks/LVM beim Booten mit virtueller Tastatur entsperren

Status: Gelöst | Ubuntu-Version: Ubuntu GNOME 17.10 (Artful Aardvark)
Antworten |

TNTMaster

Anmeldungsdatum:
30. Juli 2009

Beiträge: 875

Hallo

Bei meinem Notebook läßt sich der Touch Screen vom Keyboard trennen. Lightdm und Gnome habe ich soweit eingerichtet, daß ich das Teil als Tablet nur über den Touch Screen (halbwegs) bedienen kann, beim Klick in ein Textfeld erscheint automatisch die virtuelle Tastatur, um Eingaben zu machen.

Was mir noch fehlt ist eine virtuelle Tastatur, um das Dateisystems(Vollverschlüsselung) mit dem Passwort beim Booten zu entsperren, da ich das Gerät gerne komplett ohne angesteckter Tastatur betreiben will.

Hat jemand eine Idee, wie ich das umsetzen könnte?

Gruß TNT

encbladexp Team-Icon

Ehemaliger
Avatar von encbladexp

Anmeldungsdatum:
16. Februar 2007

Beiträge: 17518

Dein Problem ist das, bei einer Systemverschlüsselung, an dieser Stelle noch kein X-Server oder Wayland läuft der sowas möglich machen würde. Der müsste dann in der Initrd drin sein, was wohl platzmäßig ein Problem wäre.

mfg Stefan

frostschutz

Avatar von frostschutz

Anmeldungsdatum:
18. November 2010

Beiträge: 7744

Ein Notebook mit Touchscreen habe ich leider nicht. Auf einem Ebook-Reader mit Touchscreen habe ich auch schonmal einfach mit cat/dd auf Touch-Events reagiert.

while cat /dev/input/touchscreen | dd bs=1 count=1
do
    # jemand hat mich angetatscht, mach was
done

Nur kannst du so nicht die Position oder sonst eine Information auswerten bzw. das läuft dann auf Eingabe per Morse-Code hinaus. 😉

Für mehr müsstest du dann in diese Richtung gehen: https://stackoverflow.com/a/28845362/2876682

Und das ganze als Hook ins Initramfs integrieren. So oder so wird da eine handgestrickte Lösung draus.

Ein ganz anderer Ansatz wäre, das System unverschlüsselt zu lassen und dann eben ein verschlüsseltes Laufwerk aus dem bereits laufenden Gnome heraus aufzusperren. Also keine komplette Systemverschlüsselung.

TNTMaster

(Themenstarter)

Anmeldungsdatum:
30. Juli 2009

Beiträge: 875

encbladexp schrieb:

.. an dieser Stelle noch kein X-Server oder Wayland läuft ... müsste dann in der Initrd drin sein ...

Ja, leider. Ich hatte die Hoffnung, das mit einem zusätzlichen Paket, einem Plugin für Plymouth oder einer Änderung der bestehenden Konfiguration zu erreichen.

frostschutz schrieb:

Für mehr müsstest du dann in diese Richtung gehen: https://stackoverflow.com/a/28845362/2876682

Muß ich mir mal näher anschaun. Wenn man die Position am Bildschirm so ermitteln kann, könnte ich mir ein Plymouth Hintergrundbild basteln, auf dem alle Zeichen einer Tastatur dargestellt sind. Klick Position ermitteln, dem richtigen Buchstaben zuordnen und hoffen, daß diese ins Passwortfeld geleitet werden. Da kommt wohl etwas Arbeit auf mich zu 😉 Danke schonmal hierfür

TNT

frostschutz

Avatar von frostschutz

Anmeldungsdatum:
18. November 2010

Beiträge: 7744

Vermutlich einfacher, den cryptsetup Aufruf dann auch gleich selbst zu erledigen. (Ähnlich wie beim Aufsperren über SSH)

frostschutz

Avatar von frostschutz

Anmeldungsdatum:
18. November 2010

Beiträge: 7744

Eine minimalistische Touchscreen-Tastatur habe ich dir hier mal gebastelt: Twiddle Thumbs Touchscreen Keyboard

Funktionsprinzip quasi so wie hier: https://www.youtube.com/watch?v=HzUDAaYMNsA&t=1m12s

Mit der Maus oder auf dem Touchscreen Kreise zeichnen - geht die Liste der möglichen Zeichen durch (z.B. 0-9).

2 Sekunden nicht berühren: Aktueller Buchstabe wird hinzugefügt und auf die nächste Eingabe gewartet (symbolisiert durch _).

5 Sekunden nicht berühren: Ende der Eingabe. (symbolisiert durch _.)

Gewisses Frustrationspotential ist bei dem Ansatz enthalten. 😀

TNTMaster

(Themenstarter)

Anmeldungsdatum:
30. Juli 2009

Beiträge: 875

frostschutz schrieb:

Eine minimalistische Touchscreen-Tastatur habe ich dir hier mal gebastelt: Twiddle Thumbs Touchscreen Keyboard Gewisses Frustrationspotential ist bei dem Ansatz enthalten. 😀

Das ist mir dann doch zu frustig, deshalb habe ich meinen Ansatz mit Plymouth Hintergrundbild nun erfolgreich umgesetzt, obwohl ich einige Hürden zu nehmen hatte. 😀

Ich habe mir einen Screenshot der onboard Tastatur erstellt und die Beschriftung der Tasten meinen Vorstellungen entsprechend mit Gimp abgeändert. Im Plymouth Script des von mir verwendeten Ubuntu-Budgie-Themes habe ich statt dem original Logo den Dateinamen meiner Tastatur-Grafik (virtkey.png, im Anhang) angegeben und die Positionen der angezeigten Elemente angepaßt.

Im Skript wird die Touch Position ermittelt und dem jeweiligen Zeichen zugeordnet, /etc/crypttab geändert, um das Skript beim Booten auszuführen, benötigtes Modul hid_multitouch in initramfs integriert und einen Hook erstellt, damit benötige Befehle/Dateien zur Bootzeit zur Verfügung stehen. Wärmstens zu empfehlen: Bevor Änderungen vorgenommen werden, eine Kopie der aktuellen initrd in /boot speichern, um das System bei Fehlern starten zu können (Grub-Menü → edit → Kopie der initrd angeben).

Beim Booten erscheint nun die virt. Tastatur und für jedes Zeichen im PW wird ein * angezeigt, um ein optisches Feedback zu haben. Zu beachten ist dabei, daß gleichzeiges Touchen mehrerer Tasten nicht funktioniert, d.h. großes "A" wird in 2 Schritten eingeben: SHIFT/SHIFTLOCK touchen, "a" touchen. Um das PW mit der angeschlossenen Tastatur einzugeben: Enter drücken und es wird das bekannte Standard Passwortfeld angezeigt.

Am Anfang des Skripts habe ich noch ein paar Hinweise eingefügt, die gelesen werden dürfen. 😉 Ich hoffe, ich habe mich halbwegs verständlich ausgedrückt. Anregungen, Fragen, Verbesserungen, Fehler? Nur her damit.

Gruß TNT

Änderungen an Dateien:

in /etc/crypttab Pfad zum Skript hinzufügen, UUID unterscheidet sich natürlich:

#lukslvm UUID=81e1eb55-7853-4230-9206-a932fbef1bf8 none luks,discard
lukslvm UUID=81e1eb55-7853-4230-9206-a932fbef1bf8 none luks,discard,keyscript=/lib/cryptsetup/scripts/virtkey.sh

in /etc/initramfs-tools/modules hinzufügen:

hid_multitouch

Hook speichern nach: /etc/initramfs-tools/hooks/virtkey

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
#!/bin/sh

PREREQ=""

prereqs(){
    echo "$PREREQS"
}

case $1 in
prereqs)
    prereqs
    exit 0
    ;;
esac

. /usr/share/initramfs-tools/hook-functions

# Benötigte Dateien in initramfs kopieren
if command -v /usr/bin/evtest >/dev/null 2>&1; then
    copy_exec /usr/bin/evtest bin
fi
if command -v /usr/bin/killall >/dev/null 2>&1; then
    copy_exec /usr/bin/killall bin
fi
if [ -r /lib/udev/rules.d/60-persistent-input.rules ]; then
    mkdir -p $DESTDIR/lib/udev/rules.d
    cp -a /lib/udev/rules.d/60-persistent-input.rules $DESTDIR/lib/udev/rules.d
fi

Skript speichern nach: /lib/cryptsetup/scripts/virtkey.sh und ausführbar machen

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
#!/bin/sh
set -f noglob


################### Info ##################################

### Skript ist angepaßt an Plymouth Auflösung 1920x1080 Pixel
### mit virtkey.png (virt. Tastatur) Größe 1600 x 400 Pixel
### Anzeige der Tastatur beim Booten: horizontal mittig, 5 Pixel Abstand vom unteren Bildschirmrand

### virtkey.png nach /usr/share/plymouth/themes/<THEME>-logo/ kopieren
### Im Plymouth Skript sind alle Positionen in Pixel anzugeben
### Meine Änderungen in /usr/share/plymouth/themes/ubuntu-budgie-logo/ubuntu-budgie-logo.script
# logo_filename = "virtkey.png";
# logo.y = 675;
# progress_indicator.y = 620;
# message_label.y = 570;
# entry.y = 550;
# field.y = 570

### Alle X und Y Werte im Skript müssen von Pixel auf Touch Auflösung umgerechnet werden
### Touch Auflösung ermitteln, Max. Wert auslesen:
# sudo evtest <TOUCH DEVICE>
# <...>
#    Event code 0 (ABS_X)
#      Value   1869
#      Min        0
#      Max     4095
#      Resolution      16
#    Event code 1 (ABS_Y)
#      Value   2630
#      Min        0
#      Max     4095
#      Resolution      28
# <...>
### Hier also: 4095 x 4095
### X-Werte: Pixel * 4095 / 1920
### Y-Werte: Pixel * 4095 / 1080

### Fehlermeldungen werden im Kernel-Ring-Puffer zwischengespeichert
### und nach /var/log/boot.log geschrieben, sobald Zugriff auf die Datei besteht.
### Das kann man zur Fehleranalyse nutzen, indem man die Ausgabe eines Befehls auf stderr umleitet
### z.B.: ls -l /dev/input/by-id >&2


################### Konfiguration #########################

### Touchdevice angeben oder autom. Erkennung
### ! Kann in initrd anders lauten als im gestarteten System
#touchdev=/dev/input/by-id/usb-Atmel_Atmel_maXTouch_Digitizer-event-if00

### phys. Tastatur Device angeben oder autom. Erkennung
### ! Kann in initrd anders lauten als im gestarteten System
#keyboarddev=/dev/input/by-id/usb-0911_2188-event-if00

### Abstand virtkey.png von Bildschirmrand, Bezugspunkt jeweils linke obere Ecke
offset_x=341
offset_y=2559

### Eingabeverzögerung in Sekunden; Doppelanschlag einer Taste ignorieren
inputwait=0.15
inputwaitpid=dummy

### Keyboard Setup
### Y-Werte der Tastenreihen
rows="0 303 607 910 1213 1517"

### X-Werte und zugehörige Tasten der jeweiligen Reihe ohne/mit aktivierter Shift Taste (NUL=keine Funktion)
row_1="       0 220 448 674 904 1130 1358 1584 1812 2041 2267 2497 2723     2952      3180   3406"
chars_1="      ^   1   2   3   4    5    6    7    8    9    0    ?    BTICK    BSPACE    DEL"
chars_shift_1='~   !   "   #   $    %    &    /    (    )    =    \     NUL     BSPACE    DEL'

row_2="     367 590 819 1047 1275 1502 1730 1958 2186 2414 2640 2866   3097     3406"
chars_2="      q   w   e    r    t    z    u    i    o    p    +     @     ENTER"
chars_shift_2="Q   W   E    R    T    Z    U    I    O    P    *    NUL    ENTER"

row_3="       0     418 646 874 1100 1326 1557 1785 2011 2239 2468 2694 2922 3170     3406"
chars_3="      SLOCK   a   s   d    f    g    h    j    k    l    [    ]    #    ENTER"
chars_shift_3="SLOCK   A   S   D    F    G    H    J    K    L    {    }    '    ENTER"

row_4="       0     335 561 789 1017 1245 1472 1700 1928 2156 2382 2610 2839     3406"
chars_4="      SHIFT   <   y   x    c    v    b    n    m    ,    .    -    SHIFT"
chars_shift_4="SHIFT   >   Y   X    C    V    B    N    M    ;    :    _    SHIFT"

row_5="     908     2222"
chars_5="      SPACE"
chars_shift_5="SPACE"


send_pw() {
    ### Passwort verifizieren, bei Erfolg lukslvm aufschließen und Bootvorgang fortsetzen
    plymouth display-message --text="Prüfe Passwort"
    if echo -n "$1" | /sbin/cryptsetup -T 1 open UUID=${cryptsource##*/} $crypttarget --test-passphrase; then
        plymouth display-message --text="Passwort OK"
        echo -n "$1"
        killall evtest
    else
        plymouth display-message --text="Passwort falsch, nochmal"
        sleep 2
        return 1
    fi
}

watch_keyboard() {
    # Phys. Tastatur auf Drücken von Enter überwachen,
    # Touch Eingabe beenden und Fallback starten
    if evtest $keyboarddev | grep -q "(EV_KEY).*(KEY_ENTER)"; then
        killall evtest
        ask_for_password
    fi
}

ask_for_password() {
    ### Fallback, Eingabe mit phys. Tastatur nach Drücken von Enter
    plymouth display-message --text=""
    if [ -x /bin/plymouth ] && plymouth --ping; then
        plymouth ask-for-password --prompt="$msg"
    else
        /lib/cryptsetup/askpass "$msg"
    fi
}

plymouth_welcome() {
    local msg
    if [ "$keyboardfound" = "y" ]; then
        msg=$(printf "$msg\nEnter drücken, um Touch Eingabe zu beenden")
    fi
    plymouth display-message --text="$msg"
}

pos_to_char() {
    local pos_x pos_y char
    pos_x=$(($1 - offset_x))
    pos_y=$(($2 - offset_y))

    ### Tastenreihe finden
    for row_nr in $(seq 1 5); do
        [ $pos_y -lt $(echo "$rows" | awk -v i=$row_nr '{print $i}') \
            -o $pos_y -gt $(echo "$rows" | awk -v i=$((row_nr+1)) '{print $i}') ] && continue
        case $row_nr in
            1) row="$row_1"; chars="$chars_1"; chars_shift="$chars_shift_1" ;;
            2) row="$row_2"; chars="$chars_2"; chars_shift="$chars_shift_2" ;;
            3) row="$row_3"; chars="$chars_3"; chars_shift="$chars_shift_3" ;;
            4) row="$row_4"; chars="$chars_4"; chars_shift="$chars_shift_4" ;;
            5) row="$row_5"; chars="$chars_5"; chars_shift="$chars_shift_5"; ;;
        esac
        ### Zeichen in Tastenreihe finden
        for column_nr in $(seq 1 $(echo "$chars" | wc -w)); do
            [ $pos_x -lt $(echo "$row" | awk -v i=$column_nr '{print $i}') \
                -o $pos_x -gt $(echo "$row" | awk -v i=$((column_nr+1)) '{print $i}') ] && continue
            case "$mod" in
                SHIFT) char=$(echo "$chars_shift" | awk -v i=$column_nr '{print $i}'); [ "$char" != "SHIFT" ] && unset mod ;;
                SLOCK) char=$(echo "$chars_shift" | awk -v i=$column_nr '{print $i}') ;;
                    *) char=$(echo "$chars" | awk -v i=$column_nr '{print $i}') ;;
            esac
            ### Besondere Tasten/Zeichen
            case "$char" in
                SHIFT) [ "$mod" = "SHIFT" -o "$mod" = "SLOCK" ] && unset mod || mod="SHIFT"; break ;;
                SLOCK) [ "$mod" = "SHIFT" -o "$mod" = "SLOCK" ] && unset mod || mod="SLOCK"; break ;;
                ENTER) send_pw "$pw" && break; unset pw char ;;
               BSPACE) pw="${pw%?}"; unset char ;;
                BTICK) char='`' ;;
                SPACE) char=' ' ;;
                  DEL) unset pw char ;;
                  NUL) break ;;
            esac
            pw="$pw$char"
            ### Sternchen für jedes Zeichen im Passwort generieren
            dot='*'
            unset dots
            for i in $(seq 1 ${#pw}); do
                dots="$dots$dot"
            done
            ### Sternchen anzeigen
            [ -n "$dots" ] && plymouth display-message --text="$dots" || plymouth_welcome
            break
        done
    done
}

process_line() {
    local pos_x pos_y
    while read line; do
        input=$(echo "$line" | sed '/^Event: .*ABS_[XY]/!d; s/.*(ABS_\([XY]\)), value \([0-9]\+\)/\1\2/')
        if echo "$input" | grep -q ^X; then
            pos_x=${input#X}
            unset pos_y
            continue
        fi
        if echo "$input" | grep -q ^Y; then
            pos_y=${input#Y}
            if [ -n "$pos_x" -a -n "$pos_y" ]; then
                ### Touch Position ausgeben
                [ -e /proc/$inputwaitpid ] || pos_to_char $pos_x $pos_y
                unset pos_x pos_y
            fi
            sleep $inputwait &
            inputwaitpid=$!
        fi
    done
}

luksdev=$(readlink -f $cryptsource)
msg="Passwort eingeben für $crypttarget auf $luksdev"

### Autom. Erkennung der Tastatur, 1. Treffer wird verwendet
keyboardfound=n
if [ -z "$keyboarddev" ] || [ ! -c "$keyboarddev" ]; then
    keyboarddev=/dev/input/$(awk -v RS= '/EV=120013/ && !/Vendor=000[01]/ {print; exit}' /proc/bus/input/devices | \
        sed -r '/Handlers=/!d; s/.* (event[0-9]+) .*/\1/')
fi

### Autom. Erkennung des Touchscreens, 1. Treffer wird verwendet
if [ -z "$touchdev" ] || [ ! -c "$touchdev" ]; then
    touchdev=/dev/input/$(awk -v RS= '/EV=b/ {print; exit}' /proc/bus/input/devices | \
        sed -r '/Handlers=/!d; s/.* (event[0-9]+) .*/\1/')
fi

#ls -l /dev/input/by-id >&2
[ -c "$keyboarddev" ] && keyboardfound=y

if [ -c "$touchdev" ]; then
    [ "$keyboardfound" = "y" ] && watch_keyboard &
    plymouth_welcome
    evtest $touchdev | process_line
else
    if [ "$keyboardfound" = "y" ]; then
        ask_for_password
    else
        plymouth display-message --text="Kein Eingabegerät gefunden. Bitte neustarten"
        sleep 10
    fi
fi

initrd bauen und Neustart:

sudo update-initramfs -u -k all
Bilder

frostschutz

Avatar von frostschutz

Anmeldungsdatum:
18. November 2010

Beiträge: 7744

Wow. Prima! 👍

TNTMaster

(Themenstarter)

Anmeldungsdatum:
30. Juli 2009

Beiträge: 875

frostschutz schrieb:

Wow. Prima! 👍

Stecken auch so einige Stunden Arbeit drin, viel davon ging für Trial&Error und "Grundlagenforschung" drauf.

Ein Fehler ist mir noch untergekommen: Das Hook Skript /etc/initramfs-tools/hooks/virtkey muß ausführbar gemacht werden.

mifritscher

Anmeldungsdatum:
12. Januar 2008

Beiträge: Zähle...

Kann bestätigen, dass das Script unter 18.04 läuft ☺

Unter 20.04 ist eine Anpassung nötig:

Da gibt es die Variablen cryptsource und crypttarget nicht mehr. Ein

cryptsource=$CRYPTTAB_SOURCE
crypttarget=$CRYPTTAB_NAME

hilft.

Diese Variablen scheinen auch die "offiziellen" zu sein, wenn man sich die manpage zur crypttab so anschaut - auch schon bei 18.04. Weiterer Vorteil: cryptsource hat den "rohen" Devicenamen als /dev/sda5, d.h. man kann (bzw. muss) unten das UUID=${cryptsource##/*} oder so einfach durch $cryptsource ersetzen.

Funktioniert ansonsten astrein!

Antworten |