Crea sito
29 Ottobre 2020

Officine Informatiche Roma

ICT SERVICES ROMA – BAZAAR INFORMATICO

I file di log

9 min read
Uno dei software meno conosciuti e più sottovalutati dai nuovi utenti Linux è certamente syslog, il preziosissimo sistema di log che ogni distribuzione decentemente completa fornisce. Grazie a questo silenzioso aiutante un utente esperto è in grado di diagnosticare problemi di ogni genere del kernel e dei principali daemoni e  sottosistemi (come mail, news e web server).

Uno dei software meno conosciuti e più sottovalutati dai nuovi utenti Linux è certamente syslog, il preziosissimo sistema di log che ogni distribuzione decentemente completa fornisce.

Grazie a questo silenzioso aiutante un utente esperto è in grado di diagnosticare problemi di ogni genere del kernel e dei principali daemoni e  sottosistemi (come mail, news e web server).

In questo articolo cominceremo analizzando a grandi linee il sistema di log, concentrandoci prima di tutto sulle parti più visibili al normale utente, in particolare sulla configurazione e personalizzazione; in seguito potremo addentrarci maggiormente sul funzionamento di questo sistema piuttosto complesso, per concludere con accenni alla programmazione.

Spostatevi nella directory /var/log ed eseguite il comando ls; quelli che state vedendo sono i file di log del vostro sistema: qui sono conservate tutte le informazioni sul normale funzionamento della macchina e soprattutto le registrazioni di errori e problemi; leggendo questi file potrete ottenere preziosi dettagli su come risolvere i problemi di funzionamento del vostro computer.
Ogni file contiene i log di specifici aspetti del sistema; il file principale che determina la configurazione del processo di logging è /etc/syslog.conf.
La sintassi dei file di log è uniforme: ogni messaggio viene scritto su una singola riga: inizia sempre con l’indicazione del momento in cui viene effettuata la registrazione, il nome del computer su cui gira il programma che ha generato il log, di solito (anche se non è obbligatorio) il nome del programma stesso ed infine, preceduto da un due punti, il messaggio vero e proprio. Ad esempio, nel file /var/log/mail.info trovo:

Mar 26 12:18:04 snoopy fetchmail[12106]: starting fetchmail 4.3.9 daemon

che significa questo: il 26 marzo alle ore 12, 18 minuti e 4 secondi il daemon di log ha ricevuto una richiesta dal processo fetchmail, che in quel momento stava girando con PID3 12106 sulla macchina snoopy (che è il nome locale del mio computer); il messaggio era "starting fetchmail 4.3.9 daemon" e serve solo per segnalare che qualcuno lo ha eseguito.
Ovviamente questo era il tipico messaggio puramente informativo; altri possono essere di ben maggior aiuto nella risoluzione dei problemi, analizziamo ad esempio una riga di /var/log/news/news.err che contiene i log degli errori ricevuti dal sistema che gestisce il news server locale:

Dec 27 12:39:39 snoopy fetchnews[1717]: error writing groupinfo file (disk full?)

indica che il 27 dicembre il programma fetchnews ha incontrato un errore piuttosto grave non essendo riuscito a scrivere un file. Non essendo riuscito a continuare ha smesso di operare ed ha segnalato la cosa nei log; grazie a questo avvertimento sono riuscito immediatamente a capire cosa era andato storto ed a risolvere la situazione.
Se si pensa che anche i programmi del sottosistema di rete (come tcpd xinetd(1)ipchains(8)) si appoggia su syslog per registrare il proprio normale funzionamento e soprattutto per segnalare eventi sospetti, appare immediatamente chiaro quanto sia importante imparare ad utilizzare al meglio i log.

Analizziamo ora a grandi linee il funzionamento del sistema: i programmi che hanno necessità di lasciare una traccia nei log si appoggiano sul sistema di logging che nelle moderne installazioni è formato da due daemon: syslogd e klogd che si occupano rispettivamente di gestire i messaggi provenienti dai normali programmi e dal kernel; normalmente klogd si appoggia su syslogd, il cui file di configurazione /etc/syslog.conf è quindi la parte più interessante da analizzare.

/etc/syslog.conf
Questo file contiene una serie di righe formate da coppie di campi selettore e azione, dove selettore definisce cosa loggare, e azione dove scrivere i log; i due campi sono separati da spazi o tabulazioni. Ogni selettore è definito da una coppia facility e priorità separati da un punto: facility stabilisce il genere di dati da considerare per i log (ad esempio le informazioni provenienti dal processo che si occupa di gestire le stampanti, lpd), mentre priorità pone un filtro alla gravità dei messaggi da loggare. Andiamo ad analizzare un esempio banale:
mail.err /var/log/mail.err significa che di tutti i messaggi provenienti dai programmi che gestiscono il sistema di posta (ad esempio sendmail, postfix, qmail, smail o simili) dobbiamo loggare nel file /var/log/mail.err solamente quelli la cui priorità corrisponde o supera il livello err.

Cosa è possibile loggare

Le facility predefinite si possono trovare nei sorgenti delle libc, nel file /usr/include/sys/syslog.h; vediamole:
auth: messaggi relativi alla sicurezza del sistema, come ad esempio registrazioni di login e logout (è usato da programmi come su, sudo, login).
authpriv: come auth, ma il messaggio potrebbe contenere dati sensibili, quindi è bene dirigerlo su un file separato che ci si preoccuperà di non rendere leggibile a tutti.
cron: il sottosistema di temporizzazione degli eventi: comprende ad esempio daemon come cron, anacron, atd.
daemon: generico per i daemon di sistema.
kern: messaggi del kernel.
lpr: il sottosistema che gestisce le stampanti.
mail: tutto ciò che ha a che fare con la consegna o ricezione di email.
news: gestione delle news Usenet.
syslog: messaggi generati dallo stesso syslog.
user: messaggi generici provenienti da programmi in user space (in contrapposizione ai log generati dal kernel).
uucp: il sottosistema UUCP.Il termine UUCP, abbreviazione di Unix-to-Unix Copy Program (copia da Unix a Unix), è riferito a un insieme di programmi per l’esecuzione di comandi e il trasferimento di file, email e netnews tra computer. uucp è anche il nome di uno di questi programmi, che ne fornisce l’interfaccia utente. Il collegamento può avvenire tramite modem, connessione diretta via cavo, connessione IP.

Nella suite di programmi sono generalmente presenti anche uux (interfaccia per le esecuzioni remote), uucico (demone), uustat (statistiche sull’attività recente), uuxqt (esecuzione di comandi richiesti da altre macchine) e uuname (nome del sistema locale).

Il sistema UUCP è stato inizialmente sviluppato per la condivisione tramite la linea telefonica dei codici del sistema operativo Unix e dei programmi scientifici sviluppati in questo ambiente.

E’ ormai in disuso.
ftp: introdotto con le libc2.0, è riservato ai server ftp.
da local0 a local7: riservati per utilizzi locali.
Oltre a questi sono validi security che però è obsoleto e andrebbe sostituito con auth, e mark che è ad esclusivo uso interno (utile per dirigere in un unico file tutti i marcatori, dei quali si parlerà in seguito).

Priorità
Insieme al tipo di dato da loggare, l’applicazione specifica anche la gravità e l’urgenza del messaggio. Sempre in /usr/include/sys/syslog.h si trovano le definizioni dei vari livelli di priorità.

Vediamoli in ordine dal meno importante al più urgente:
debug: non mostrati normalmente ma solo quando si vuole ottenere informazioni dettagliate da un programma.
info: informazioni poco significative circa il funzionamento del programma.
notice: segnala una situazione significativa, ma sempre all’interno del normale funzionamento di un programma.

warning: messaggio generato in seguito a comportamenti più o meno anomali, che potrebbero essere legati a problemi di funzionamento.
err: si è verificata un errore.
crit: indica una situazione critica, che compromette seriamente il normale funzionamento del sottosistema coinvolto.
alert: condizione che impone un immediato intervento da parte dell’operatore.
emerg: il sistema risulta inutilizzabile.
Oltre a questi esistono anche warn, error e panic che però sono obsolete e corrispondono rispettivamente a warning, err ed emerg.

Sintassi avanzata di /etc/syslog.conf
È possibile creare righe di configurazione anche piuttosto complesse combinando in vari modi più facility e più livelli di priorità. Prima di tutto è possibile utilizzare il carattere * come jolly per tutte le facility o priorità, e la parola chiave none per indicare nessuna priorità. Ad esempio:
lpr.* /var/log/lpr.log
raccoglie i messaggi del sottosistema di stampa di ogni priorità e li scrive nel file /var/log/lpr.log (nella pratica è del tutto equivalente a lpr.debug).
È poi possibile specificare più facility con la medesima priorità separandole con virgole:

user,daemon.crit /var/log/misc.crit
salva nel file indicato i messaggi critici appartenenti alle facility user e daemon. Continuiamo con gli esempi:
*.emerg /var/log/all.emerg
memorizza tutti i messaggi relativi ad emergenze.
È anche possibile scegliere diversi tipi di dati da inviare allo stesso file; basta separare le diverse entry con punti e virgola:

uucp.*;news.info /var/log/uucp_and_news.log
salva tutti i messaggi provenienti dal sottosistema UUCP e i messaggi che siano di informazione (o più gravi) dal news server.
*.*;auth,authpriv.none /var/log/quasi_tutto.log
salva pressoché ogni tipo di messaggio da ogni sistema, tranne tutti i messaggi (grazie alla keyword none) relativi alla sicurezza.
Come detto quando si specifica una priorità significa che tutti i messaggi del dato livello e tutti i messaggi più gravi vengono salvati nel file indicato. È anche possibile specificare che si desidera esclusivamente una data priorità anteponendole un uguale:

mail.=info /var/log/mail.info
mail.=warning /var/log/mail.warn
salva in /var/log/mail.warn solo i messaggi di warning del sottosistema che si occupa della gestione delle email, mentre in /var/log/mail.info si troveranno solo quelli informativi: se qui non si fosse aggiunto l’uguale avrebbe raccolto anche i messaggi di tipo notice, warning e degli altri livelli superiori.
Sempre per quanto riguarda le priorità è possibile invertire la selezione facendola precedere da un punto esclamativo:

mail.*;mail.!notice /var/log/mail.log
che salva solo i messaggi di tipo debug e info, o anche:
mail.*;mail.!=debug /var/log/mail.nodebug
che memorizza tutti i messaggi del dato sottosistema ad esclusione di quelli relativi al debug (questo esempio equivale quindi a mail.info).
In ogni punto lungo le righe di configurazione è possibile andare a capo terminando la riga con un backslash:

*.=info;*.=notice;*.=warning;\
auth,authpriv.none;\
cron,daemon.none;\
mail,news.none /var/log/messages
salva tutti i messaggi di tipo info, notice o warning tralasciando quelli dai sistemi di sicurezza, cron, daemon vari, mail e news.

I file di log
Finora abbiamo visto come riempirci il disco fisso di file di log, ma in realtà ci sono molte altre possibilità. Vediamo di seguito come personalizzare ulteriormente il file di configurazione agendo sul campo azione.

Normali file
Come sopra descritto negli esempi i nomi di file vanno obbligatoriamente scritti con il percorso completo (ovvero devono cominciare con uno /). Bisogna ricordare che ogni volta che il sistema di log va a scrivere una riga nei suoi file effettua una chiamata alla funzione di sistema fsync(2) che svuota il buffer riversandolo su disco fisso; nel caso che numerose righe debbano essere scritte in pochissimo tempo è possibile assistere ad una certa perdita di performance del sistema, completamente impegnato a tenere aggiornati quei file. Per evitare questi problemi è possibile disabilitare la continua sincronizzazione facendo precedere un meno (-) al nome del file: in questo modo il sistema risulterà meno impegnato; c’è ovviamente il rischio che in caso di crash alcune delle ultime righe del file non siano state ancora salvate: questo però non è di norma un grosso problema, se non per i log di eventi critici di parti fondamentali del sistema.
cron.* -/var/log/cron.log
non sincronizza il file /var/log/cron.log ogni volta che una riga viene aggiunta; anche in caso di crash difficilmente i messaggi del sistema di temporizzazione saranno di nostro interesse.

Named pipe (o FIFO)

Anteponendo il carattere | al nome del file è possibile indicare che il file è in realtà una FIFO, o named pipe (per fare un esempio il file /dev/xconsole è una FIFO); potete creare named pipe con i comandi mkfifo(1) o mknod(1).

Terminali virtuali

Caratteristica molto utile è la facoltà di inviare i messaggi non ad un normale file, ma ad un terminale virtuale (come ad esempio i vari /dev/tty* e /dev/console):
kern.* /var/log/kern.log
kern.* /dev/tty9
Logga tutti i messaggi provenienti dal kernel nel file /var/log/kern.log ed inoltre li stampa sulla tty numero 9: potrete ora passare su quella console con la combinazione Alt+F9 (Ctrl+Alt+F9 se siete in ambiente X Window System) e leggere gli ultimi messaggi che il vostro kernel ha inviato.

Macchina remota

Possibilità che fa felici gli amministratori di sistema è quella di inviare i log ad un’altra macchina, scrivendone il nome preceduto da un @:
daemon.* @ginopino
invia tutti i messaggi specificati alla macchina ginopino; da notare che su questa macchina deve necessariamente girare il daemon syslogd lanciato con l’opzione -r che lo pone in ascolto di messaggi dalla rete. Ovviamente nel file di log di questa macchina comparirà il nome del computer che ha generato il messaggio.


Se si dispone di una rete locale è da prendere in considerazione l’opportunità di loggare anche su una macchina remota almeno i log critici: questi infatti possono essere generati anche da problemi fisici dei dischi fissi, che potrebbero quindi rendere inaccessibili i file locali.

Utenti

Al posto del classico nome di file si può indicare una lista di utenti, separati da virgole, che riceveranno gli avvisi se sono loggati:
*.alert root,davide
mostra in console i messaggi indicati agli utenti root e davide.
Chiunque sia attualmente loggato
Come visto analizzando le priorità, alcune di esse indicano la necessità di prendere immediati provvedimenti; in questo caso è utile fare in modo che chiunque sia attualmente loggato riceva il messaggio (tramite wall(1)):
*.emerg *
tutti i messaggi di emergenza vengono ricevuti da tutti gli utenti, come specificato dal carattere * al posto del nome di file.

Translate »