|
Die Kommandos stty und tput
UNIX arbeitet terminalorientiert, d. h. der Benutzer sitzt an einen
wie auch immer ausgestatteten Text-Terminal. Auch der PC-Bildschirm bei Linuxist ein solches Text-Terminal. Ebenso ist ein "xterm" auf dem Grafikbildschirm nichts anderes als ein emuliertes Text-Terminal. Sobald Kontakt zu einem Terminal hergestellt ist, greift die Terminalsteuerung auf zwei Dateien zurück: /etc/ttydefs oder /etc/gettydefs, in der hauptsächlich Steuerungswerte für die Datenübertragung gespeichert sind (z. B. Baudrate, Datenformat, Handshake, etc.). Das ist natürlich nur nochdann interessant, wenn das Terminal über eine serielle Schnittstelle oderper Modem angeschlossen ist. Bei den Pseudo-Terminals, die über das Netzmit dem UMIX-Rechner verbunden sind, spielen die Inhalte der Dateien nur noch
eine untergeordnete Rolle (z. B. bei der Definition einiger Steuertasten wie
Backspace).
Beim Programmieren keimt recht schnell der Wunsch auf, den Bildschirm anzusteuern,
z. B. den Bildschirm zu löschen, den Cursor zu positionieren etc. Es existieren
verschiedene Möglichkeiten, dies zu realisieren. In den frühen Jahre
von UNIX gab es zahlreiche Anbiter von Bildschirmterminals und jeds dieser
Terminals wurde mit anderen Kombinationen von ASCII-Zeichen angesteuert.
Selbst unter MS-DOS wurde diese Tradition noch gepflegt - in Form des ANSI-Treibers.
Welche Möglichkeiten der Bildschirmansteuerung gibt es? Ein Terminal
reagiert normalerweise auf Zeichenfolgen, die vom Programm aus geschickt
werden. Normale Zeichen werden als Buchstaben dargestellt, bestimmte Sonder-
zeichen oder Kombinationen bewirken aber bestimmte Funktionen. Da diese
Kombinationen meist bestimmte Sonderzeichen enthalten (z.B. ESCAPE), um sie
von Text zu unterscheiden, werden die Steuerfolgen auch Escape-Sequenzen
genannt. Wenn man nun z. B. den Bildschirm löschen möchte, dann sucht man
sich im Manual des Terminals die entsprechende Sequenz für "Bildschirm löschen"
heraus und schickt sie vom Programm aus an das Terminal. Weil es auch
nichtdruckbare Zeichen sein können, kann es sein, daß man ihre oktale oder
sedezimale Verschlüsselung angeben muß. Dazu ein Beispiel:
Bei einem VT100-Terminal ist die Sequenz für "Bildschirm löschen" die Zeichenfolge
[;H[2J
Man schickt das beispielsweise aus einem C-Programm heraus mit
printf("\033[;H\033[2J") ans Terminal. Dabei ist "\033" die oktale
Schreibweise für das Escape-Zeichen.
Bei bildschirmorientierten Programmen wie z. B. einem Editor muß es möglich sein,
den Cursor auf dem Bildschirm frei hin und her bewegen zu können. Das geht nicht ohne
weiteres, weil die Terminals dafür spezielle Steuercodes, meist ESC gefolgt von
einer bestimmten Zeichenkette, erwarten. Auch Fett- oder Kursivschrift lassen
sich oft über solche Steuersequenzen ein- bzw. ausschalten. Andere Funktionen
sind z. B. das Löschen des gesamten Bildschirms oder bis zum Ende der Zeile.
Leider sind die Steuersequenzen für die einzelnen Funktionen nicht einheitlich.
Auch haben die vielen verschieden Terminals unterschiedliche Möglichkeiten.
Deshalb gibt es eine Datenbank, in der, bei BSD-UNIX in der Datei etc/termcap im
Textformat und bei System V in kompilierter Form in einer Reihe von Dateien
unter dem Verzeichnis /usr/lib/terminfo, die Steuersequenzen zur Bildschirmansteuerung
bei verschiedenen Terminaltypen gespeichert sind. Die Termcap und Terminfo-Datenbanken
sind im wesentlichen äquivalent zueinander. Der Vorteil der Termcap-Variante ist die
leichte Lesbarkeit und Änderbarkeit. Dafür kann auf die kompilierte Terminfo-Datenbank
schneller zugegriffen werden.
Termcap
Je nachdem mit welchem Terminal man nun gerade arbeitet, sucht sich das UNIX-System die
richtigen Steuersequenzen für dieses Terminal aus der Datenbank, wenn ein
Anwendungsprogramm Funktionen wie "Bildschirm löschen" oder "Cursor nach oben" aufruft.
Auf diese Art sind auch bildschirmorientierte Programme ohne Veränderung mit praktisch
jedem Terminal einsatzfähig, vorausgesetzt natürlich, daß ein Termcap/Terminfo-Eintrag
für das Terminal existiert. Im allgemeinen sollte das für alle gängigen Terminaltypen
der Fall sein. Falls der Eintrag für ein verwendetes Terminal fehlt, können die
Datenbanken auch um eigene Einträge ergänzt werden.
Der Termcap-Eintrag für das oft verwendete VT100-Terminal von DEC sieht z. B.
folgendermaßen aus:
vtlO0|vt100-am|vt100am|dec vt100:\
:do=^J:co#80:]i#24:c1=50\1[;H\E[2J:sf=5\ED:\
:le=^H:bs:am:ce5\E[%i%d:%dH:nd=2\EEC:up=2\E[A:\
:ce=3\E[K:cd=50\E[J:so=2\E[7m:se=2\E[m:us=2\E[4m:ue=2\E[m:\
:md=2\E[lm:mr=2\E[7m:mb=2\E[5m:me=2\E[m:is=\E[1;24r\E[24;IH:\
:rf=/usr/share/lib/tabset/vt100:\
:rs=\E>\E[?31\E[?41\E[?51\E[?7h\E[?8h:ks=\E[?lh\E=:ke=\E[?11\E>:\
:ku=\EOA:kd=\EOB:kr=\EOC:kl=\EOD:kb=^H:\
:ho=\E[H:kl=\EOP:k2=\EOO:k3=\EOR:k4=\EOS:pt:sr=5\EM:vt#3:xn:\
:sc=\E7:rc=\E8:cs=\E[%i%d;%dr:
In der ersten Zeile stehen die Namen, unter denen dieser Termcap-Eintrag
angesprochen werden kann. Danach folgen durch Doppelpunkte getrennt die
zur Verfügung stehenden Funktionen und entsprechenden Steuersequenzen.
Die Steuercodes, um den Cursor auf den Bildschirm bewegen, findet man beispielsweise
in den ersten beiden Zeilen. do = ^J bedeutet,
daß der Cursor mit CTRL-J eine Zeile nach unten, und up=2\E[A, daß er mit
ESC-[A eine Zeile nach oben bewegt wird. Kombinationen mit der Control-Taste werden
also in der Form ^x angegeben, wobei x ein beliebiger Buchstabe sein kann. \E ist die Umschreibung für das Escape-Zeichen. Die Zahl 2 hinter dem Gleichheitszeichen bei der
Angabe der Steuersequenz für die Bewegung des Cursors nach oben hat eine besondere
Bedeutung. Grundsätzlich kann bei jeder Funktion an dieser Stelle eine Wartezeit in
Millisekunden angegeben werden, die nach dem Abschicken der Steuersequenz verstreichen muß,
bis der UNIX-Rechner weitere Zeichen an das Terminal schicken darf. Das ist notwendig, weil die Terminals für die Verarbeitung eines Steuercodes eine bestimmte Zeit brauchen, in der
alle ankommenden Zeichen im - meist sehr kleinen - internen Puffer zwischengespeichert werden
müssen, bis die Verarbeitung der Steuersequenz beendet ist. Bei einer schnellen Leitung
zwischen Terminal und Computer kann es so zum Verlust von Zeichen kommen, weil der interne
Puffer schnell überlaufen würde, wenn das Terminal beispielsweise damit beschäftigt ist, den
Bildschirminhalt zu löschen. Dieses Warten nach dem Abschicken einer Steuersequenz an das
Terminal nennt man englisch Padding.
Andere Angaben in dem Termcap-Eintrag sind die Zeilen- und Spaltenzahl des Terminals in der
zweiten Zeile mit den Kürzeln co#80 bzw. li#24. Sollte man tatsächlich
einmal in die Verlegenheit kommen, einen Termcap-Eintrag verändern oder gar neu schreiben zu
müssen, findet man weitere Informationen in den man-pages oder in weiterführender
Literatur.
Auch in Programmen werden symbolische Bezeichnungen für die Terminalfunktionen
verwendet, die in den entsprechenden Headerdateien der C-Bibliothek festgelegt sind.
Zur Änderung der Werte in ttydefs/gettydefs dient das Kommando stty, zur
Steuerung der Ausgabe kann das Kommando tput verwendet werden.
Terminfo
Mittlerweile gibt es einen Nachfolger für Termcap, die sogenannte
Terminfo-Datenbank. Sie ist ziemlich ähnlich, nur daß die Datenbank hier
nicht im ASCII-Format abgespeichert ist, sondern in einem Binärformat,
weil das geht. Im Normalfall haben die meisten verwendeten Unix-Varianten
noch beides, termcap und terminfo.
Curses
Mit termcap kann man flexible Programme schreiben, aber es könnte noch
einfacher gehen. Deshalb gibt es eine weitere Bibliothek, die auf termcap
aufbaut: "curses". Die curses-Bibliothek ermöglicht sämtliche
Terminal-E/A-Funktionen. Zusätzliches Ziel von "curses"
ist es, den Update des Bildschirms in optimaler Form durchzuführen, also
möglichst schnell mit möglichst wenig Zeichen, die geschickt werden müssen.
Curses geht dabei folgendermaßen vor: es gibt einen virtuellen Bildschirm
im Hauptspeicher. Ausgaben werden nun zuerst in diesem internen Speicherbereich
aufgebaut. Und erst beim Aufruf der Funktion refresh() werden alle seit dem
letzten refresh() angefallenen Aenderungen an den realen Bildschirm geschickt.
Zusätzlich ist es möglich, den Bildschirm in Bereiche (Windows, hat aber
nichts mit X Windows zu tun) einzuteilen und diese getrennt zu bearbeiten.
Am Anfang gibt es für den gesamten zur Verfügung stehenden Bildschirm das
vordefinierte Window stdscr.
Wie sieht ein curses-Programm aus? Hier ein Beispielprogramm, das in
der Mitte des Bildschirms den String "Hello, world!" invers ausgibt.
#include
int main(void)
{
char *text = "Hello, world!";
initscr(); /* Curses-Paket initialisieren */
clear(); /* Bildschirm löschen */
move(LINES/2-1,(COLS-strlen(text))/2-1);
/* Cursor zur richtigen Position */
/* LINES und COLS sind vordefiniert */
standout(); /* schalte auf Invers */
printw("%s\n",text); /* gib den Text aus */
standend(); /* wieder auf normal */
refresh(); /* reale Ausgabe */
endwin(); /* Ende Curses-Nutzung */
return 0;
}
Die Verwendung von Bibliotheken wie termcap oder curses hat natürlich
Auswirkungen auf die Portabilität des Programms. Schon verschiedene
Unix-Systeme haben verschiedene Curses-Bibliotheken.
stty [Optionen]
(set tty) Änderung der Standard-tty-Parameter.
Die Einstellungen sind nur solange gültig, wie der Shellprozeß
mit dem Terminal verbunden ist. Das Kommando kann alleine oder mit diversen
Parametern verwendet werden. stty ohne Parameter gibt die wichtigsten Einstellungen
aus; um alle Parameter zu sehen, verwendet man stty -a. Meist kann man
die Wirkung der entsprechenden Option durch ein "-"-Zeichen davor umkehren
(siehe Beispiel stty -echo). Weitere Info: man stty. Beispiele:
stty erase ^h
Setzen der Backspace-Funktion (in diesem Fall Control-H).
Bei direkter Eingabe kann man die entsprechende Taste direkt betätigen
(Steuertasten werden als zwei Zeichen "geechot", Backspace z. B. als "^h").
Bei Eingabe in Skripts mit dem vi kann man mit Ctrl-D erreichen, daß
das folgende Zeichen unverändert übernommen wird. Manche Shells
aktzeptieren auch die Kombination aus zwei Zeichen, "^" + Buchstabe.
stty eb
Einschalten der akustischen Fehleranzeige (error bell).
stty echo stty -echo
Echo auf dem Bildschirm ein- und ausschalten. Bei der folgenden Kommandosequenz
wird die Eingabe des Paßworts auf dem Bildschirm nicht wiedergegeben.
echo "Paßwort eingeben: \c"
stty -echo
read PASS
stty echo
tput Parameter
(terminal put) Senden von Steuerbefehlen an das Terminal,
wobei die "echte" Steuerinfo der terminfo-Datenbasis entnommen wird. Als
Parameter dient der symbolische Name der entsprechenden Steuerfunktion.
Je nach Terminaltyp sind sehr viele Steuerfunktionen möglich. Derzeit
akzeptiert tput nur einen Parameter, mehrere Steuerbefehle müssen
also nacheinander gegeben werden. Die in der Praxis am häufigsten
gebrauchten Parameter sind:
bel | Signalton |
blink | Text auf Blinken schalten |
bold | Text heller darstellen (hohe intensität) |
clear | Bildschirm löschen,Cursor in die linke obere Ecke |
cr | Carriage Return |
cup | Cursor positionieren. Hinter cup folgen Zeilennummer und
Spaltennummer der Cursorposition, z. B. cup 10 40 |
ed | Bildschirm von Cursorposition bis Ende löschen |
el | Von Cursorposition bis Zeilenende löschen |
home | Cursor in linke obere Ecke |
ind | Schirm nach oben rollen |
rev | Text aud Inversdarstellung schalten |
ri | Schirm nach unten rollen rmso Wieder auf normale Zeichendarstellung
schalten |
Beispiel:
tput bel
tput bold
echo "\nAchtung! Alle Daten werden gelöscht!\n"
tput rmso
|
|
|