Einlesen der Terminalantwortzeichenfolge in eine Variable

Einlesen der Terminalantwortzeichenfolge in eine Variable

Verwenden vonSchlag, wie kann ich die Antwort des Terminals ohne Benutzerinteraktion in eine Variable einlesen? Der folgende Einzeiler muss trotzdem Entereinmal gedrückt werden:

echo -ne '\005' && read -s && echo ${REPLY}

Wie kann ich außerdem konfigurierenXtermum etwas Sinnvolles als Antwort zu senden ^E? Bisher ist der einzige Terminalemulator, den ich gesehen habe, der eine Antwort sendet,Kitt.

Antwort1

Der Answerback-String ist in xterm konfigurierbar mit demanswerbackStringRessource. Diese Ressource wurde hinzugefügt in1998. Ursprünglich wurde "xterm" zurückgegeben, da1999Der Standardwert ist eine leere Zeichenfolge, da einige Benutzer das Missbrauchspotenzial von Steuersequenzen erkannt haben, die möglicherweise einen unerwarteten Befehl an den Computer senden.

Andere Terminals geben möglicherweise immer eine leere Zeichenfolge zurück (konsole, mlterm, vte). Aber rxvt (und rxvt-unicode) geben eine unerwartete Antwort zurück: die Antwort auf die Geräteattribute für VT102 (eine Escape-Sequenz). PuTTY gibt „PuTTY“ zurück(wahrscheinlich aufgrund des frühen Einflusses von xterm).

Bei einer schnellen Überprüfung zeigt die Linux-Konsole ein „a“ an (wahrscheinlich ein Fehler).

Da das ursprüngliche VT100 dies als Setup-/Konfigurierfunktion bereitstellte, wäre dies beschränkt gewesen aufdruckbarZeichen. Aus diesem Grund ist die Antwort von rxvt/urxvt unerwartet. Die Manualpage enthält dazu einen obskuren Kommentar:

answerbackString:Schnur
Geben Sie die Antwort an, die rxvt-unicode an die Shell sendet, wenn ein ENQ-Zeichen (Strg-E) übergeben wird. Sie kann Escape-Werte enthalten, wie im Eintrag unter beschrieben.keysymfolgen.

(die versprochene Beschreibung fehlt).

Da die Länge der Antwortzeichenfolge unbekannt ist, muss eine Anwendung, die sie liest, eine Wartezeit einplanen (falls die Zeichen in mehr als einem Lesevorgang eintreffen). Es gibt natürlich die ksh/bash-spezifische TMOUTFunktion, die beim Shell-Scripting hilfreich sein kann, zusammen mit der -tOption für den readBefehl. Für den allgemeinen Gebrauch vermeide ich dies, indem ich sttybeispielsweise verwende (siehedynamic.sh):

stty raw -echo min 0 time 5

um das Terminal vorübergehend so einzustellen, dass es readnach 0,5 Sekunden abläuft und ohne Lesen von Zeichen zurückkehren kann. Um zu sehen, wie die Einstellungen gespeichert/wiederhergestellt werden, ist es hilfreich, das Skript zu lesen.

Weiterführende Literatur:

Antwort2

Sogar bei einem Timeout und (einer gewissen) Anzahl zu lesender Zeichen scheint es, dass bash( version 4.2.46(1)-release) die nicht speichern kann REPLY, hier durch Ausgeben der Steuersequenz „Cursorposition melden“, zuerst mit Eingabe einer neuen Zeile und dann durch Warten auf das Timeout:

$ echo -ne '\033[6n' && read -n 16 -s -t 3; echo -n $REPLY | xxd
0000000: 1b5b 3234 3b31 52                        .[24;1R
$ echo -ne '\033[6n' && read -n 16 -s -t 3; echo -n $REPLY | xxd
$ 

Das Problem hierbei ist, dass -ngrößer ist als die Anzahl der zurückgegebenen Bytes. Wenn -nstattdessen genau die richtige Größe oder kleiner ist, wird die Antwort gelesen, ohne dass eine Eingabe (oder ein Timeout) erforderlich ist. Wenn Sie ein letztes eindeutiges Zeichen der Antwortzeichenfolge kennen, können Sie eine Antwort erhalten, indem Sie „Zeilen“ nach diesem Zeichen aufteilen. Für die Eingabeaufforderung für die Zeichenposition des Berichts könnte dieses Trennzeichen wie folgt verwendet werden R:

$ echo -ne '\033[6n' && read -n 999 -d R -s; echo -n $REPLY | xxd
0000000: 1b5b 3234 3b31                           .[24;1
$ 

Bei unbekannten Eingaben unbekannter Länge müssten Sie entweder einen Fehler melden bashoder vielleicht mühsam Byte für Byte abknabbern, bis das Timeout ausgelöst wird:

$ out="got "; echo -ne '\033[6n'; while read -n 1 -s -t 1; do out="$out$REPLY"; done
$ echo -n $out | xxd
0000000: 676f 7420 1b5b 3234 3b31 52              got .[24;1R
$ 

Für die control+eSache, die ich annehmeein Terminal könnte etwas zurücksenden, müsste aber entsprechend konfiguriert werden:

ENQ       Return Terminal Status (Ctrl-E).  Default response is an empty
          string, but may be overridden by a resource answerbackString.

verwandte Informationen