NAME ersetzt. Der Bezeichner NAME darf dabei nur
aus Buchstaben, Ziffern und Unterstrichen bestehen.
Ist die Environmentvariable name nicht gesetzt, wird ein
Leerstring eingesetzt.
NAME
auch Sonderzeichen mit Ausnahme der geschlossenen Klammer
enthalten darf.
\0101 wird durch das Zeichen A ersetzt.
0, einem x und hexadezimalen
Zahlen, wird durch das ASCII-Zeichen ersetzt, dessen Wertigkeit der Zahl
entspricht.
0\x42 wird durch das Zeichen B ersetzt.
1 und
9 einschliesslich, sowie optional weiteren Ziffern von 0
bis 9, wird durch das ASCII-Zeichen ersetzt, dessen Wertigkeit der Zahl
entspricht.
\67 wird durch das Zeichen C ersetzt.
\) ersetzt
CR, einen Wagenruecklauf ersetzt.
$) ersetzt.
~) ersetzt.
Wenn das Heimatverzeichnis/home/uweist, dann wird~durch/home/uweersetzt.
name ersetzt.
~uwewird durch/home/uweersetzt.
name ersetzt. Diese Version ist
vorzuziehen, wenn name Sonderzeichen enthaelt oder
sich direkt daran weitere Zeichen oder Buchstaben
anschliessen.
~(uwe)/tmpwird durch/home/uwe/tmpersetzt.
~) ersetzt.
Das $[-Konstrukt ermoeglicht eine Textersetzung in Abhaengigkeit
vom Ergebnis einer Bedingung. Die Syntax ist:
$[bedingung?was-wenn-wahr:was-wenn-falsch]
Der else-Teil der Bedingung darf weggelassen werden:
$[bedingung?was-wenn-wahr]
bedingung kann sein:
something und something-else gleich sind.
something und something-else ungleich sind.
something nicht leer ist.
Der Term in den eckigen Klammern wird erst in seine Einzelteile
zerlegt, dann erst werden die notwendigen Interpretationen ausgefuehrt.
Nicht notwendige Interpretationen (zum Beispiel der else-Teil
einer wahren Bedinungen) werden nicht durchgefuehrt.
Der Einsatz der Library erfordert nur geringe Aenderungen am Programm:
Die Textersetzung wird durch die Routine tip_interpret durchgefuehrt:
Die Funktion fuehrt die Ersetzung durch. Sie durchsucht den String
format zeichenweise. Falls das Zeichen einem magic der Tabelle
entspricht oder die nächsten Zeichen einem der magicstrings in
der Tabelle entsprechen, wird die assozierte Routine tab->interp
aufgerufen. Falls tab->interp nicht zustaendig ist
(TIP_NOTDONE zurueckliefert), wird die Tabelle weiter durchsucht.
tip_interpret liefert die
die Anzahl der geschriebenen Zeichen ohne das abschliessende
'\0', also strlen(to), oder TIP_ERROR,
falls ein Fehler auftrat, zurueck.
Die tip_interpret zu uebergebende Tabelle tab wird durch ein
Element beendet, dessen magic '\0' und dessen
magicstring NULL ist. Der Datentyp ist
definiert als:
typedef struct
{
char magicchar;
const char *magicstring;
size_t magiclen;
tip_fn_t interp;
} tip_t;
Die Routine interp wird aufgerufen, falls:
magicchar ungleich '\0' und das nächste Zeichen im zu
interpretierenden Text gleich magicchar ist, oder
magicstring ungleich NULL ist und die nächsten
magiclen Zeichen im zu interpretierenden Text gleich magicstring
sind.
interp wird unter section Ersetzungsunterroutinen: tip_fn_t beschrieben.
tip_t wird niemals einzeln verwendet, sondern immer nur als
Array, dessen letztes Element als magic ein '\0' hat
und dessen magicstring NULL ist.
Die Funktion arbeitet wie tip_interpret, alloziert aber den Speicherbereich für das Ergebnis selbst. Das verwendete Verfahren führt unter Umständen dazu, daß einzelne Interpretationen mehrfach durchgeführt werden.
Die Funktion wird aufgerufen, wenn tip_interpret (siehe section Durchfuehrung der Ersetzung)
im format-String ein oder mehrere Zeichen fand, die
der tip_function
in der Tabelle tab zugeordnet wurden. Sie erhaelt folgende
Parameter:
tip_function eine Ersetzung durchfuehren konnte.
Returncodes:
Wird eine Ersetzung durchgefuehrt, ist der String mit einer 0 abzuschliessen.
Folgende Ersatzroutinen enthaelt die Library:
magic das
Zeichen $. Siehe section Ersetzung durch Environmentvariablen.
magic das Zeichen ~.
Bei Einsatz von tip_tilde ist Vorsicht geboten. Die Zugriffe auf die
Passwortdatei, die notwendig sind, um das Heimatverzeichnis feststellen
zu können, geschehen mit Hilfe der Funktionen getpwuid
und getpwnam, und verstellen daher den Dateizeiger
saemtlicher `/etc/passwd' mit Hilfe der Routinen
aus <pwd.h> lesender oder schreibender Funktionen. Bei Aufruf von
tip_deinit wird endpwent aufgerufen, falls tip_tilde vorher
aufgerufen worden ist.
magic das Zeichen
\\.
magicstring wird $[ erwartet. Die Bedinungen muß
außerdem mit einem ] abgeschlossen werden.
magicstring wird ${strip erwartet. Der
Ausdruck muß außerdem mit einem } abgeschlossen werden.
Die Funktion kann als Beispiel für eigene Funktionen dienen.
undefined eingesetzt. Der Ausdruck
muß mit einem } abgeschlossen werden.
Das Beispiel setzt den Inhalt des Makros test ein.
${macro test}
} abgeschlossen werden. Fehlt value,
wird ein leerer String als Wert eingesetzt.
Das Beispiel setzt das Makro test auf hallo:
${defmacro test hallo}
tip_defmacro ist über die Funktion tip_defmacro_intern
realisiert, siehe section Definition und Nutzung von Makros.
} abgeschlossen werden. Der Scanner,
der nach der abschliessenden Klammer sucht, ist recht empfindlich, und
verlangt, daß der Parameterstring der Syntax der Interpretationsroutinen
genügt.
Das Beispiel setzt einen einzelnen $ ein, ist also eine aufwendigere
Schreibweise für \$:
${literal %}
} abgeschlossen werden.
Das Beispiel zeigt, wie man aus vier Backslashs einen machen kann:
Das Beispiel setzt den Inhalt des Makros test ein.
${force \\\\}
Makros dienen als Schreiberleichterung. Sie behalten ihren Inhalt bis sie gelöscht werden oder das Programm endet.
Es gibt zwei Arten, Makros einen Wert zuzuweisen:
defmacro aufgerufen, kann also benutzt
werden, um aus einer interpretierten Datei heraus einen Makrowert
zu setzen.
intern
bezieht sich darauf, daß ihr Aufruf in das Programm eincodiert
werden muß.
Es gibt zwei Arten, ein Makros zu löschen:
undefmacro
aufgerufen, kann also benutzt werden, um aus einer interpretierten
Datei heraus ein Makro zu löschen.
Ein Makro kann auch einen leeren Wert haben.
Beide Arten, eine Makro zu definieren oder zu löschen sind identisch und arbeiten auf derselben Datenbasis.
Mit dieser Funktion kann man aus einem C-Programm heraus ein Makro auf einen Wert setzen (value != NULL) oder ein Makro löschen (value == NULL).
endpwent auf,
und auch nur, falls tip_tilde eine der Routinen aus <pwd.h> benutzt hat.
Liefert 0 bei Erfolg, sonst einen Wert ungleich 0.
static size_t my_tip_prozent(const char *this, const char **next,
char *to, size_t maxlen);
tip_t tab[]=
{
{'$',tip_dollar},
{'\\',tip_backslash},
{'%',my_tip_prozent},
{0,NULL},
};
static void mylog(const char *format);
static size_t my_tip_prozent(const char *this, const char **next,
char *to, size_t maxlen)
{
char buf[128];
time_t t;
size_t l;
switch(this[1])
{
case 't': /* %t -> Ausgabe von ctime() ohne \n */
if (maxlen<25) /* strlen(ctime) */
return TIP_ERROR;
time(&t);
strcpy(to,ctime(&t));
*strchr(to,'\n')=0;
return 24;
case 'p': /* %p -> pid */
sprintf(buf,"%ld",(long) getpid());
l=strlen(buf);
if (l+1>maxlen)
return TIP_ERROR;
strcpy(to,buf);
return l;
}
return TIP_NOTDONE;
};
extern FILE *logfile;
static void mylog(const char *format)
{
char buf[4096];
if (tip_interpret(tab,format,buf,sizeof(buf))!=TIP_ERROR)
fprintf(logfile,"%s\n",buf);
}
Go to the first, previous, next, last section, table of contents.