Due nuovi programmi per illustrare i semafori POSIX.
[gapil.git] / signal.tex
index 001623b38d0b21865bbe7c254e80a8e56202e0db..66b434b68ca88edc888aeb3cc4a314e542f0391c 100644 (file)
@@ -865,6 +865,9 @@ sez.~\ref{sec:sig_sigaction}). 
 interruzione nel mezzo di un trasferimento parziale di dati, le system call
 ritornano sempre indicando i byte trasferiti.
 
+% TODO: alcune syscall danno EINTR anche se il segnale è installato con
+% SA_RESTART, vedi signal(7)
+
 
 \subsection{La funzione \func{signal}}
 \label{sec:sig_signal}
@@ -1988,7 +1991,9 @@ rispettivamente lo stato di uscita, l'\textit{user time} e il \textit{system
 \var{si\_addr} con l'indirizzo in cui è avvenuto l'errore, \const{SIGIO} (vedi
 sez.~\ref{sec:file_asyncronous_io}) avvalora \var{si\_fd} con il numero del
 file descriptor e \var{si\_band} per i \itindex{out-of-band} dati urgenti
-(vedi sez.~\ref{sec:TCP_urgent_data}) su un socket.
+(vedi sez.~\ref{sec:TCP_urgent_data}) su un socket, il segnale inviato alla
+scadenza di un timer POSIX (vedi sez.~\ref{sec:sig_timer_adv}) avvalora i
+campi \var{si\_timerid} e \var{si\_overrun}.
 
 Benché sia possibile usare nello stesso programma sia \func{sigaction} che
 \func{signal} occorre molta attenzione, in quanto le due funzioni possono
@@ -2204,181 +2209,6 @@ dell'esecuzione di \func{sigsuspend}.
 \itindend{signal~mask}
 
 
-\subsection{Ulteriori funzioni di gestione}
-\label{sec:sig_specific_features}
-
-In questo ultimo paragrafo esamineremo le rimanenti funzioni di gestione dei
-segnali non descritte finora, relative agli aspetti meno utilizzati e più
-``\textsl{esoterici}'' della interfaccia.
-
-La prima di queste funzioni è \funcd{sigpending}, anch'essa introdotta dallo
-standard POSIX.1; il suo prototipo è:
-\begin{prototype}{signal.h}
-{int sigpending(sigset\_t *set)} 
-  
-Scrive in \param{set} l'insieme dei segnali pendenti.
-  
-  \bodydesc{La funzione restituisce zero in caso di successo e $-1$ per un
-    errore.}
-\end{prototype}
-
-La funzione permette di ricavare quali sono i segnali pendenti per il processo
-in corso, cioè i segnali che sono stati inviati dal kernel ma non sono stati
-ancora ricevuti dal processo in quanto bloccati. Non esiste una funzione
-equivalente nella vecchia interfaccia, ma essa è tutto sommato poco utile,
-dato che essa può solo assicurare che un segnale è stato inviato, dato che
-escluderne l'avvenuto invio al momento della chiamata non significa nulla
-rispetto a quanto potrebbe essere in un qualunque momento successivo.
-
-Una delle caratteristiche di BSD, disponibile anche in Linux, è la possibilità
-di usare uno \itindex{stack} \textit{stack} alternativo per i segnali; è cioè
-possibile fare usare al sistema un altro \itindex{stack} \textit{stack}
-(invece di quello relativo al processo, vedi sez.~\ref{sec:proc_mem_layout})
-solo durante l'esecuzione di un gestore.  L'uso di uno \textit{stack}
-alternativo è del tutto trasparente ai gestori, occorre però seguire una certa
-procedura:
-\begin{enumerate*}
-\item allocare un'area di memoria di dimensione sufficiente da usare come
-  \textit{stack} alternativo;
-\item usare la funzione \func{sigaltstack} per rendere noto al sistema
-  l'esistenza e la locazione dello \textit{stack} alternativo;
-\item quando si installa un gestore occorre usare \func{sigaction}
-  specificando il flag \const{SA\_ONSTACK} (vedi tab.~\ref{tab:sig_sa_flag})
-  per dire al sistema di usare lo \textit{stack} alternativo durante
-  l'esecuzione del gestore.
-\end{enumerate*}
-
-In genere il primo passo viene effettuato allocando un'opportuna area di
-memoria con \code{malloc}; in \file{signal.h} sono definite due costanti,
-\const{SIGSTKSZ} e \const{MINSIGSTKSZ}, che possono essere utilizzate per
-allocare una quantità di spazio opportuna, in modo da evitare overflow. La
-prima delle due è la dimensione canonica per uno \itindex{stack}
-\textit{stack} di segnali e di norma è sufficiente per tutti gli usi normali.
-
-La seconda è lo spazio che occorre al sistema per essere in grado di lanciare
-il gestore e la dimensione di uno \textit{stack} alternativo deve essere
-sempre maggiore di questo valore. Quando si conosce esattamente quanto è lo
-spazio necessario al gestore gli si può aggiungere questo valore per allocare
-uno \itindex{stack} \textit{stack} di dimensione sufficiente.
-
-Come accennato, per poter essere usato, lo \itindex{stack} \textit{stack} per
-i segnali deve essere indicato al sistema attraverso la funzione
-\funcd{sigaltstack}; il suo prototipo è:
-\begin{prototype}{signal.h}
-{int sigaltstack(const stack\_t *ss, stack\_t *oss)}
-  
-Installa un nuovo \textit{stack} per i segnali.
-  
-  \bodydesc{La funzione restituisce zero in caso di successo e $-1$ per un
-    errore, nel qual caso \var{errno} assumerà i valori:
-
-  \begin{errlist}
-  \item[\errcode{ENOMEM}] la dimensione specificata per il nuovo
-    \textit{stack} è minore di \const{MINSIGSTKSZ}.
-  \item[\errcode{EPERM}] uno degli indirizzi non è valido.
-  \item[\errcode{EFAULT}] si è cercato di cambiare lo \textit{stack}
-    alternativo mentre questo è attivo (cioè il processo è in esecuzione su di
-    esso).
-  \item[\errcode{EINVAL}] \param{ss} non è nullo e \var{ss\_flags} contiene un
-  valore diverso da zero che non è \const{SS\_DISABLE}.
-  \end{errlist}}
-\end{prototype}
-
-La funzione prende come argomenti puntatori ad una struttura di tipo
-\var{stack\_t}, definita in fig.~\ref{fig:sig_stack_t}. I due valori
-\param{ss} e \param{oss}, se non nulli, indicano rispettivamente il nuovo
-\itindex{stack} \textit{stack} da installare e quello corrente (che viene
-restituito dalla funzione per un successivo ripristino).
-
-\begin{figure}[!htb]
-  \footnotesize \centering
-  \begin{minipage}[c]{15cm}
-    \includestruct{listati/stack_t.h}
-  \end{minipage} 
-  \normalsize 
-  \caption{La struttura \structd{stack\_t}.} 
-  \label{fig:sig_stack_t}
-\end{figure}
-
-Il campo \var{ss\_sp} di \struct{stack\_t} indica l'indirizzo base dello
-\itindex{stack} \textit{stack}, mentre \var{ss\_size} ne indica la dimensione;
-il campo \var{ss\_flags} invece indica lo stato dello \textit{stack}.
-Nell'indicare un nuovo \textit{stack} occorre inizializzare \var{ss\_sp} e
-\var{ss\_size} rispettivamente al puntatore e alla dimensione della memoria
-allocata, mentre \var{ss\_flags} deve essere nullo.  Se invece si vuole
-disabilitare uno \textit{stack} occorre indicare \const{SS\_DISABLE} come
-valore di \var{ss\_flags} e gli altri valori saranno ignorati.
-
-Se \param{oss} non è nullo verrà restituito dalla funzione indirizzo e
-dimensione dello \itindex{stack} \textit{stack} corrente nei relativi campi,
-mentre \var{ss\_flags} potrà assumere il valore \const{SS\_ONSTACK} se il
-processo è in esecuzione sullo \textit{stack} alternativo (nel qual caso non è
-possibile cambiarlo) e \const{SS\_DISABLE} se questo non è abilitato.
-
-In genere si installa uno \itindex{stack} \textit{stack} alternativo per i
-segnali quando si teme di avere problemi di esaurimento dello \textit{stack}
-standard o di superamento di un limite (vedi
-sez.~\ref{sec:sys_resource_limit}) imposto con chiamate del tipo
-\code{setrlimit(RLIMIT\_STACK, \&rlim)}.  In tal caso infatti si avrebbe un
-segnale di \const{SIGSEGV}, che potrebbe essere gestito soltanto avendo
-abilitato uno \itindex{stack} \textit{stack} alternativo.
-
-Si tenga presente che le funzioni chiamate durante l'esecuzione sullo
-\textit{stack} alternativo continueranno ad usare quest'ultimo, che, al
-contrario di quanto avviene per lo \itindex{stack} \textit{stack} ordinario
-dei processi, non si accresce automaticamente (ed infatti eccederne le
-dimensioni può portare a conseguenze imprevedibili).  Si ricordi infine che
-una chiamata ad una funzione della famiglia \func{exec} cancella ogni
-\textit{stack} alternativo.
-
-Abbiamo visto in fig.~\ref{fig:sig_sleep_incomplete} come si possa usare
-\func{longjmp} per uscire da un gestore rientrando direttamente nel corpo
-del programma; sappiamo però che nell'esecuzione di un gestore il segnale
-che l'ha invocato viene bloccato, e abbiamo detto che possiamo ulteriormente
-modificarlo con \func{sigprocmask}. 
-
-Resta quindi il problema di cosa succede alla maschera dei segnali quando si
-esce da un gestore usando questa funzione. Il comportamento dipende
-dall'implementazione; in particolare la semantica usata da BSD prevede che sia
-ripristinata la maschera dei segnali precedente l'invocazione, come per un
-normale ritorno, mentre quella usata da System V no.
-
-Lo standard POSIX.1 non specifica questo comportamento per \func{setjmp} e
-\func{longjmp}, ed il comportamento delle \acr{glibc} dipende da quale delle
-caratteristiche si sono abilitate con le macro viste in
-sez.~\ref{sec:intro_gcc_glibc_std}.
-
-Lo standard POSIX però prevede anche la presenza di altre due funzioni
-\funcd{sigsetjmp} e \funcd{siglongjmp}, che permettono di decidere quale dei
-due comportamenti il programma deve assumere; i loro prototipi sono:
-\begin{functions}
-  \headdecl{setjmp.h} 
-  
-  \funcdecl{int sigsetjmp(sigjmp\_buf env, int savesigs)} Salva il contesto
-  dello \textit{stack} per un \index{salto~non-locale} salto non-locale.
-  \funcdecl{void siglongjmp(sigjmp\_buf env, int val)} Esegue un salto
-  non-locale su un precedente contesto.
-
-  \bodydesc{Le due funzioni sono identiche alle analoghe \func{setjmp} e
-    \func{longjmp} di sez.~\ref{sec:proc_longjmp}, ma consentono di specificare
-    il comportamento sul ripristino o meno della maschera dei segnali.}
-\end{functions}
-
-Le due funzioni prendono come primo argomento la variabile su cui viene
-salvato il contesto dello \itindex{stack} \textit{stack} per permettere il
-\index{salto~non-locale} salto non-locale; nel caso specifico essa è di tipo
-\type{sigjmp\_buf}, e non \type{jmp\_buf} come per le analoghe di
-sez.~\ref{sec:proc_longjmp} in quanto in questo caso viene salvata anche la
-maschera dei segnali.
-
-Nel caso di \func{sigsetjmp}, se si specifica un valore di \param{savesigs}
-diverso da zero la maschera dei valori sarà salvata in \param{env} e
-ripristinata in un successivo \func{siglongjmp}; quest'ultima funzione, a
-parte l'uso di \type{sigjmp\_buf} per \param{env}, è assolutamente identica a
-\func{longjmp}.
-
-
 \subsection{Criteri di programmazione per i gestori dei segnali}
 \label{sec:sig_signal_handler}
 
@@ -2598,28 +2428,30 @@ per la restituzione dei dati viene usato il campo \var{si\_value}.
     \includestruct{listati/sigval_t.h}
   \end{minipage} 
   \normalsize 
-  \caption{La unione \structd{sigval\_t}.}
+  \caption{La definizione dell'unione \structd{sigval}, definita anche come
+    tipo \type{sigval\_t}.}
   \label{fig:sig_sigval}
 \end{figure}
 
-Questo è una \ctyp{union} di tipo \struct{sigval\_t} (la sua definizione è in
+Questo è una \ctyp{union} di tipo \struct{sigval} (la sua definizione è in
 fig.~\ref{fig:sig_sigval}) in cui può essere memorizzato o un valore numerico,
 se usata nella forma \var{sival\_int}, o un indirizzo, se usata nella forma
 \var{sival\_ptr}. L'unione viene usata dai segnali \textit{real-time} e da
 vari meccanismi di notifica\footnote{un campo di tipo \struct{sigval\_t} è
   presente anche nella struttura \struct{sigevent} (definita in
-  fig.~\ref{fig:file_sigevent}) che viene usata dai meccanismi di notifica
-  come quelli per l'I/O asincrono (vedi sez.~\ref{sec:file_asyncronous_io}) o
-  le code di messaggi POSIX (vedi sez.~\ref{sec:ipc_posix_mq}).} per
-restituire dati al gestore del segnale; in alcune definizioni essa viene
-identificata anche come \code{union sigval}.
+  fig.~\ref{fig:struct_sigevent}) che viene usata dai meccanismi di notifica
+  come quelli per i timer POSIX (vedi sez.~\ref{sec:sig_timer_adv}), l'I/O
+  asincrono (vedi sez.~\ref{sec:file_asyncronous_io}) o le code di messaggi
+  POSIX (vedi sez.~\ref{sec:ipc_posix_mq}).} per restituire dati al gestore
+del segnale; in alcune definizioni essa viene identificata anche con
+l'abbreviazione \type{sigval\_t}.
 
 A causa delle loro caratteristiche, la funzione \func{kill} non è adatta ad
 inviare segnali \textit{real-time}, poiché non è in grado di fornire alcun
-valore per \struct{sigval\_t}; per questo motivo lo standard ha previsto una
+valore per \struct{sigval}; per questo motivo lo standard ha previsto una
 nuova funzione, \funcd{sigqueue}, il cui prototipo è:
 \begin{prototype}{signal.h}
-  {int sigqueue(pid\_t pid, int signo, const sigval\_t value)}
+  {int sigqueue(pid\_t pid, int signo, const union sigval value)}
   
   Invia il segnale \param{signo} al processo \param{pid}, restituendo al
   gestore il valore \param{value}.
@@ -2715,7 +2547,7 @@ prevalentemente con i \itindex{thread} \textit{thread}; \funcd{sigwaitinfo} e
   segnale in \param{info}.
   
   \funcdecl{int sigtimedwait(const sigset\_t *set, siginfo\_t *info, const
-    struct timespec *timout)}
+    struct timespec *timeout)}
   
   Analoga a \func{sigwaitinfo}, con un la possibilità di specificare un
   timeout in \param{timeout}.
@@ -2753,9 +2585,9 @@ incaricato della gestione, che al ritorno della funzione esegue il codice che
 usualmente sarebbe messo nel gestore, per poi ripetere la chiamata per
 mettersi in attesa del segnale successivo. Questo ovviamente comporta che non
 devono essere installati gestori, che solo il \textit{thread} di gestione deve
-usare \func{sigwait} e che, per evitare che venga eseguita l'azione
-predefinita, i segnali gestiti in questa maniera devono essere mascherati per
-tutti i \textit{thread}, compreso quello dedicato alla gestione, che potrebbe
+usare \func{sigwait} e che i segnali gestiti in questa maniera, per evitare
+che venga eseguita l'azione predefinita, devono essere mascherati per tutti i
+\textit{thread}, compreso quello dedicato alla gestione, che potrebbe
 riceverlo fra due chiamate successive.
 
 \itindend{thread} 
@@ -2833,11 +2665,11 @@ tab.~\ref{tab:sig_timer_clockid_types}.
                                   amministrativi.\\ 
     \const{CLOCK\_MONOTONIC}    & Orologio che indica un tempo monotono
                                   crescente (a partire da un tempo iniziale non
-                                  specificati) che non può essere modificato.\\
+                                  specificato) che non può essere modificato.\\
     \const{CLOCK\_MONOTONIC\_RAW}&Simile al precedente, ma non subisce gli
                                   aggiustamenti dovuti all'uso di NTP (viene
                                   usato per fare riferimento ad una fonte
-                                  hardware.\footnotemark\\
+                                  hardware).\footnotemark\\
     \const{CLOCK\_PROCESS\_CPUTIME\_ID}& contatore del tempo di CPU usato 
                                   da un processo (il \textit{process time} di
                                   sez.~\ref{sec:sys_cpu_times}, nel totale di
@@ -2863,7 +2695,7 @@ tab.~\ref{tab:sig_timer_clockid_types}.
 Per poter utilizzare queste funzionalità le \acr{glibc} richiedono che la
 macro \macro{\_POSIX\_C\_SOURCE} sia definita ad un valore maggiore o uguale
 di \texttt{199309L} (vedi sez.~\ref{sec:intro_gcc_glibc_std}), inoltre i
-programmi che le usano devono essere linkati con la libreria delle estensioni
+programmi che le usano devono essere collegati con la libreria delle estensioni
 \textit{real-time} usando esplicitamente l'opzione \texttt{-lrt}. Si tenga
 presente inoltre che la disponibilità di queste funzionalità avanzate può
 essere controllato dalla definizione della macro \macro{\_POSIX\_TIMERS} ad un
@@ -2872,10 +2704,10 @@ valore maggiore di 0, e che le ulteriori macro
 \macro{\_POSIX\_THREAD\_CPUTIME} indicano la presenza dei rispettivi orologi
 di tipo \const{CLOCK\_MONOTONIC}, \const{CLOCK\_PROCESS\_CPUTIME\_ID} e
 \const{CLOCK\_PROCESS\_CPUTIME\_ID}.\footnote{tutte queste macro sono definite
-  in \texttt{unistd.h}, che peranto deve essere incluso per poterle
+  in \texttt{unistd.h}, che pertanto deve essere incluso per poterle
   controllarle.} Infine se il kernel ha il supporto per gli \textit{high
   resolution timer} un elenco degli orologi e dei timer può essere ottenuto
-tremite il file \procfile{/proc/timer\_list}.
+tramite il file \procfile{/proc/timer\_list}.
 
 Le due funzioni che ci consentono rispettivamente di modificare o leggere il
 valore per uno degli orologi \textit{real-time} sono \funcd{clock\_settime} e
@@ -2907,7 +2739,7 @@ tab.~\ref{tab:sig_timer_clockid_types} o con il risultato di una chiamata a
 \func{clock\_getcpuclockid} (che tratteremo a breve), il secondo argomento
 invece è sempre il puntatore \param{tp} ad una struttura \struct{timespec}
 (vedi fig.~\ref{fig:sys_timespec_struct}) che deve essere stata
-precedentemente allocata; nel primo caso questa devrà anche essere stata
+precedentemente allocata; nel primo caso questa dovrà anche essere stata
 inizializzata con il valore che si vuole impostare sull'orologio, mentre nel
 secondo verrà restituito al suo interno il valore corrente dello stesso.
 
@@ -2944,14 +2776,14 @@ orologio, la funzione 
 }
 \end{functions}
 
-La funzione richiede come primo argomento l'indicazione dell' orologio di cui
+La funzione richiede come primo argomento l'indicazione dell'orologio di cui
 si vuole conoscere la risoluzione (effettuata allo stesso modo delle due
 precedenti) e questa verrà restituita in una struttura \struct{timespec}
 all'indirizzo puntato dall'argomento \param{res}. 
 
 Come accennato il valore di questa risoluzione dipende sia dall'hardware
 disponibile che dalla implementazione delle funzioni, e costituisce il limite
-minimo di un intervallo di tempo che si può indicare, qualunque valore si
+minimo di un intervallo di tempo che si può indicare. Qualunque valore si
 voglia utilizzare nelle funzioni di impostazione che non corrisponda ad un
 multiplo intero di questa risoluzione, sarà troncato in maniera automatica. 
 
@@ -2966,9 +2798,10 @@ pu
 
 Con i sistemi multiprocessore infatti ogni singola CPU ha i suoi registri
 interni, e se ciascuna di esse utilizza una base di tempo diversa (se cioè il
-clock del processore non è unico) avendo queste in genere frequenze
-leggermente diverse, otterremo dei valori dei contatori scorrelati fra loro
-senza possibilità di sincronizzazione. 
+segnale di temporizzazione inviato ai processori non ha una sola provenienza)
+in genere ciascuna di queste potrà avere delle frequenze leggermente diverse,
+e si otterranno pertanto dei valori dei contatori scorrelati fra loro, senza
+nessuna possibilità di sincronizzazione.
 
 Il problema si presenta, in forma più lieve, anche se la base di tempo è la
 stessa, dato che un sistema multiprocessore non avvia mai tutte le CPU allo
@@ -2989,35 +2822,63 @@ associato al \textit{process time} di un processo, la funzione 
   
   Ottiene l'identificatore dell'orologio di CPU usato da un processo.
   
-  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
-    errore, nel qual caso \var{errno} assumerà uno dei seguenti valori:
+  \bodydesc{La funzione restituisce 0 in caso di successo o un numero positivo
+    in caso di errore, nel qual caso \var{errno} assumerà uno dei seguenti
+    valori:
   \begin{errlist}
-  \item[\errcode{ENOSYS}] non e.
-  \item[\errcode{EPERM}] l'indirizzo di \param{res} non è valido.
-  \item[\errcode{ENOENT}] non c'è modo di avere un
+  \item[\errcode{ENOSYS}] non c'è il supporto per ottenere l'orologio relativo
+    al \textit{process time} di un altro processo, e \param{pid} non
+    corrisponde al processo corrente.
+  \item[\errcode{EPERM}] il chiamante non ha il permesso di accedere alle
+    informazioni relative al processo \param{pid}.
   \item[\errcode{ESRCH}] non esiste il processo \param{pid}.
   \end{errlist}
 }
 \end{functions}
 
 
-% TODO trattare gli orologi ad alta definizione e le funzioni POSIX per gli
-% stessi cioè:
-% clock_getres clock_gettime clock_settime (vedi man page)
+La funzione ritorna l'identificativo di un orologio di sistema associato ad un
+processo indicato tramite l'argomento \param{pid}. Un utente normale, posto
+che il kernel sia sufficientemente recente da supportare questa funzionalità,
+può accedere soltanto ai dati relativi ai propri processi.
 
-Abbiamo visto in sez.~\ref{sec:sig_alarm_abort} come l'interfaccia di
-\func{setitimer} derivata da BSD presenti delle limitazioni,\footnote{in
-  particolare la possibilità di perdere un segnale sotto carico.} tanto che
-nello standard POSIX.1-2008 questa viene marcata come obsoleta, e ne viene
-fortemente consigliata la sostituzione con nuova interfaccia definita dallo
-standard POSIX.1-2001 che va sotto il nome di \textit{Posix Timer API}.
+Del tutto analoga a \func{clock\_getcpuclockid}, ma da utilizzare per ottenere
+l'orologio associato ad un \textit{thread} invece che a un processo, è
+\funcd{pthread\_getcpuclockid},\footnote{per poter usare la funzione, come per
+  qualunque funzione che faccia riferimento ai \textit{thread}, occorre
+  effettuare il collegamento alla relativa libreria di gestione compilando il
+  programma con \texttt{-lpthread}.} il cui prototipo è:
+\begin{functions}
+  \headdecl{pthread.h}
+  \headdecl{time.h}
 
-La \textit{system call} per la nuova interfaccia sono stata introdotte a
-partire dal kernel 2.6, ma fino al kernel 2.6.16 la precisione degli allarmi
-era limitata dalla risoluzione del timer di sistema, e solo a partire dal
-kernel 2.6.21, con la implementazione delle temporizzazioni ad alta
-definizione, la risoluzione corrisponde a quella fornita dall'hardware
-disponibile.
+  \funcdecl{int pthread\_getcpuclockid(pthread\_t thread, clockid\_t *clockid)}
+  
+  Ottiene l'identificatore dell'orologio di CPU associato ad un
+  \textit{thread}.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo o un numero positivo
+    in caso di errore, nel qual caso \var{errno} assumerà uno dei seguenti
+    valori:
+  \begin{errlist}
+  \item[\errcode{ENOENT}] la funzione non è supportata dal sistema.
+  \item[\errcode{ESRCH}] non esiste il \textit{thread} identificato
+    da \param{thread}.
+  \end{errlist}
+}
+\end{functions}
+
+
+Con l'introduzione degli orologi ad alta risoluzione è divenuto possibile
+ottenere anche una gestione più avanzata degli allarmi; abbiamo già visto in
+sez.~\ref{sec:sig_alarm_abort} come l'interfaccia di \func{setitimer} derivata
+da BSD presenti delle serie limitazioni,\footnote{in particolare la
+  possibilità di perdere un segnale sotto carico.} tanto che nello standard
+POSIX.1-2008 questa viene marcata come obsoleta, e ne viene fortemente
+consigliata la sostituzione con nuova interfaccia definita dallo standard
+POSIX.1-2001 che va sotto il nome di \textit{Posix Timer API}. Questa
+interfaccia è stata introdotta a partire dal kernel 2.6, anche se il supporto
+di varie funzionalità è stato aggiunto solo in un secondo tempo.
 
 Una delle principali differenze della nuova interfaccia è che un processo può
 utilizzare un numero arbitrario di timer; questi vengono creati (ma non
@@ -3032,8 +2893,7 @@ avviati) tramite la funzione \funcd{timer\_create}, il cui prototipo 
   Crea un nuovo timer Posix.
   
   \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
-    errore, nel qual caso \var{errno} assumerà uno dei valori già visti per
-    \func{sigwait}, ai quali si aggiunge, per \func{sigtimedwait}:
+    errore, nel qual caso \var{errno} assumerà uno dei seguenti valori:
   \begin{errlist}
   \item[\errcode{EAGAIN}] fallimento nel tentativo di allocare le strutture
     dei timer.
@@ -3045,40 +2905,476 @@ avviati) tramite la funzione \funcd{timer\_create}, il cui prototipo 
 }
 \end{functions}
 
-La funzione richiede tre argomenti, il primo serve ad indicare quale tipo di
-orologio 
+La funzione richiede tre argomenti: il primo argomento serve ad indicare quale
+tipo di orologio si vuole utilizzare e prende uno dei valori di
+tab.~\ref{tab:sig_timer_clockid_types},\footnote{di detti valori però non è
+  previsto l'uso di \const{CLOCK\_MONOTONIC\_RAW} mentre
+  \const{CLOCK\_PROCESS\_CPUTIME\_ID} e \const{CLOCK\_THREAD\_CPUTIME\_ID}
+  sono disponibili solo a partire dal kernel 2.6.12.} si può così fare
+riferimento sia ad un tempo assoluto che al tempo utilizzato dal processo (o
+\textit{thread}) stesso. 
+
+Il secondo argomento richiede una trattazione più dettagliata, in quanto
+introduce una struttura di uso generale, \struct{sigevent}, che viene
+utilizzata anche da altre funzioni, come quelle per l'I/O asincrono (vedi
+sez.~\ref{sec:file_asyncronous_io}) o le code di messaggi POSIX (vedi
+sez.~\ref{sec:ipc_posix_mq})) e che serve ad indicare in maniera generica un
+meccanismo di notifica. 
+
+\begin{figure}[!htb]
+  \footnotesize \centering
+  \begin{minipage}[c]{15cm}
+    \includestruct{listati/sigevent.h}
+  \end{minipage} 
+  \normalsize 
+  \caption{La struttura \structd{sigevent}, usata per specificare in maniera
+    generica diverse modalità di notifica degli eventi.}
+  \label{fig:struct_sigevent}
+\end{figure}
+
+La struttura \struct{sigevent} (accessibile includendo \texttt{time.h}) è
+riportata in fig.~\ref{fig:struct_sigevent};\footnote{la definizione effettiva
+  dipende dall'implementazione, quella mostrata è la versione descritta nella
+  pagina di manuale di \func{timer\_create}.} il campo \var{sigev\_notify} è il
+più importante essendo quello che indica le modalità della notifica, gli altri
+dipendono dal valore che si è specificato per \var{sigev\_notify}, si sono
+riportati in tab.~\ref{tab:sigevent_sigev_notify}. La scelta del meccanismo di
+notifica viene fatta impostando uno dei valori di
+tab.~\ref{tab:sigevent_sigev_notify} per \var{sigev\_notify}, e fornendo gli
+eventuali ulteriori argomenti necessari a secondo della scelta
+effettuata. Diventa così possibile indicare l'uso di un segnale o l'esecuzione
+(nel caso di uso dei \textit{thread}) di una funzione di modifica in un
+\textit{thread} dedicato.
+
+\begin{table}[htb]
+  \footnotesize
+  \centering
+  \begin{tabular}[c]{|l|p{10cm}|}
+    \hline
+    \textbf{Valore} & \textbf{Significato} \\
+    \hline
+    \hline
+    \const{SIGEV\_NONE}    & Non viene inviata nessuna notifica.\\
+    \const{SIGEV\_SIGNAL}  & La notifica viene effettuata inviando al processo
+                             chiamante il segnale specificato dal campo
+                             \var{sigev\_signo}; se il gestore di questo
+                             segnale è stato installato con
+                             \const{SA\_SIGINFO} gli verrà restituito il
+                             valore specificato con \var{sigev\_value} (una
+                             \ctyp{union} \texttt{sigval}, la cui definizione
+                             è in fig.~\ref{fig:sig_sigval}) come valore del
+                             campo \var{si\_value} di \struct{siginfo\_t}.\\
+    \const{SIGEV\_THREAD}  & La notifica viene effettuata creando un nuovo
+                             \itindex{thread} \textit{thread} che esegue la
+                             funzione di notifica specificata da
+                             \var{sigev\_notify\_function} con argomento
+                             \var{sigev\_value}, se diverso da \val{NULL} il
+                             \textit{thread} viene creato con gli attributi
+                             specificati da \var{sigev\_notify\_attribute}.\\
+                             \footnotemark
+    \const{SIGEV\_THREAD\_ID}& Invia la notifica come segnale (con le stesse
+                             modalità di \const{SIGEV\_SIGNAL}) che però viene
+                             recapitato al \textit{thread} indicato dal campo
+                             \var{sigev\_notify\_thread\_id}. Questa modalità
+                             è una estensione specifica di Linux, creata come
+                             supporto per le librerie di gestione dei
+                             \textit{thread}, pertanto non deve essere usata
+                             da codice normale.\\
+    \hline
+  \end{tabular}
+  \caption{Valori possibili per il campo \var{sigev\_notify} in una struttura
+    \struct{sigevent}.} 
+  \label{tab:sigevent_sigev_notify}
+\end{table}
+
+\footnotetext{questa funzionalità è considerata un esempio di pessima
+  implementazione di una interfaccia, richiesta dallo standard POSIX, ma da
+  evitare totalmente, causa la possibilità di creare disservizi generando una
+  gran quantità di processi, tanto che ne è stata richiesta addirittura la
+  rimozione.}
+
+Nel caso di \func{timer\_create} occorrerà passare alla funzione come secondo
+argomento l'indirizzo di una di queste strutture per indicare le modalità con
+cui si vuole essere notificati della scadenza del timer, se non si specifica
+nulla (passando un valore \val{NULL}) verrà inviato il segnale
+\const{SIGALRM} al processo corrente, o per essere più precisi verrà
+utilizzato un valore equivalente all'aver specificato \const{SIGEV\_SIGNAL}
+per \var{sigev\_notify}, \const{SIGALRM} per \var{sigev\_signo} e
+l'identificatore del timer come valore per \var{sigev\_value.sival\_int}.
+
+Il terzo argomento deve essere l'indirizzo di una variabile di tipo
+\type{timer\_t} dove sarà scritto l'identificativo associato al timer appena
+creato, da usare in tutte le successive funzioni di gestione. Una volta creato
+questo identificativo resterà univoco all'interno del processo stesso fintanto
+che il timer non viene cancellato.
+
+Si tenga presente che eventuali POSIX timer creati da un processo non vengono
+ereditati dai processi figli creati con \func{fork} e che vengono cancellati
+nella esecuzione di un programma diverso attraverso una delle funzioni
+\func{exec}. Si tenga presente inoltre che il kernel prealloca l'uso di un
+segnale \textit{real-time} per ciascun timer che viene creato con
+\func{timer\_create}; dato che ciascuno di essi richiede un posto nella coda
+dei segnali \textit{real-time}, il numero massimo di timer utilizzabili da un
+processo è limitato dalle dimensioni di detta coda, ed anche, qualora questo
+sia stato impostato, dal limite \const{RLIMIT\_SIGPENDING}.
+
+Una volta creato il timer \func{timer\_create} ed ottenuto il relativo
+identificatore, si può attivare o disattivare un allarme (in gergo
+\textsl{armare} o \textsl{disarmare} il timer) con la funzione
+\funcd{timer\_settime}, il cui prototipo è:
+\begin{functions}
+  \headdecl{signal.h}
+  \headdecl{time.h}
+
+  \funcdecl{int timer\_settime(timer\_t timerid, int flags, const struct
+    itimerspec *new\_value, struct itimerspec *old\_value)}
+  
+  Arma o disarma il timer POSIX.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore, nel qual caso \var{errno} assumerà uno dei seguenti valori:
+  \begin{errlist}
+  \item[\errcode{EINVAL}] all'interno di \param{new\_value.value} si è
+    specificato un tempo negativo o un numero di nanosecondi maggiore di
+    999999999.
+  \item[\errcode{EFAULT}] si è specificato un indirizzo non valido
+    per \param{new\_value} o \param{old\_value}.
+  \end{errlist}
+}
+\end{functions}
+
+La funzione richiede che si indichi la scadenza del timer con
+l'argomento \param{new\_value}, che deve essere specificato come puntatore ad
+una struttura di tipo \struct{itimerspec}, la cui definizione è riportata in
+fig.~\ref{fig:struct_itimerspec}; se il puntatore \param{old\_value} è diverso
+da \val{NULL} il valore corrente della scadenza verrà restituito in una
+analoga struttura, ovviamente in entrambi i casi le strutture devono essere
+state allocate.
+
+\begin{figure}[!htb]
+  \footnotesize \centering
+  \begin{minipage}[c]{15cm}
+    \includestruct{listati/itimerspec.h}
+  \end{minipage} 
+  \normalsize 
+  \caption{La struttura \structd{itimerspec}, usata per specificare la
+    scadenza di un allarme.}
+  \label{fig:struct_itimerspec}
+\end{figure}
+
+Ciascuno dei due campi di \struct{itimerspec} indica un tempo, da specificare
+con una precisione fino al nanosecondo tramite una struttura \struct{timespec}
+(la cui definizione è riportata fig.~\ref{fig:sys_timespec_struct}). Il campo
+\var{it\_value} indica la prima scadenza dell'allarme. Di default, quando il
+valore di \param{flags} è nullo, questo valore viene considerato come un
+intervallo relativo al tempo corrente,\footnote{il primo allarme scatterà cioè
+  dopo il numero di secondi e nanosecondi indicati da questo campo.} se invece
+si usa per \param{flags} il valore \const{TIMER\_ABSTIME},\footnote{al momento
+  questo è l'unico valore valido per \param{flags}.} \var{it\_value} viene
+considerato come un valore assoluto rispetto al valore usato dall'orologio a
+cui è associato il timer.\footnote{quindi a seconda dei casi lo si potrà
+  indicare o come un tempo assoluto, quando si opera rispetto all'orologio di
+  sistema (nel qual caso il valore deve essere in secondi e nanosecondi dalla
+  \textit{epoch}) o come numero di secondi o nanosecondi rispetto alla
+  partenza di un orologio di CPU, quando si opera su uno di questi.}  Infine
+un valore nullo di \var{it\_value}\footnote{per nullo si intende con valori
+  nulli per entrambi i i campi \var{tv\_sec} e \var{tv\_nsec}.} può essere
+utilizzato, indipendentemente dal tipo di orologio utilizzato, per disarmare
+l'allarme.
+
+Il campo \var{it\_interval} di \struct{itimerspec} viene invece utilizzato per
+impostare un allarme periodico.  Se il suo valore è nullo (se cioè sono nulli
+tutti e due i valori di detta struttura \struct{timespec}) l'allarme scatterà
+una sola volta secondo quando indicato con \var{it\_value}, altrimenti il
+valore specificato verrà preso come l'estensione del periodo di ripetizione
+della generazione dell'allarme, che proseguirà indefinitamente fintanto che
+non si disarmi il timer.
+
+Se il timer era già stato armato la funzione sovrascrive la precedente
+impostazione, se invece si indica come prima scadenza un tempo già passato,
+l'allarme verrà notificato immediatamente e al contempo verrà incrementato il
+contatore dei superamenti. Questo contatore serve a fornire una indicazione al
+programma che riceve l'allarme su un eventuale numero di scadenze che sono
+passate prima della ricezione della notifica dell'allarme. 
+
+É infatti possibile, qualunque sia il meccanismo di notifica scelto, che
+quest'ultima venga ricevuta dopo che il timer è scaduto più di una
+volta.\footnote{specialmente se si imposta un timer con una ripetizione a
+  frequenza elevata.} Nel caso dell'uso di un segnale infatti il sistema mette
+in coda un solo segnale per timer,\footnote{questo indipendentemente che si
+  tratti di un segnale ordinario o \textit{real-time}; per questi ultimi
+  sarebbe anche possibile inviare un segnale per ogni scadenza, questo però
+  non viene fatto per evitare il rischio, tutt'altro che remoto, di riempire
+  la coda.}  e se il sistema è sotto carico o se il segnale è bloccato, prima
+della sua ricezione può passare un intervallo di tempo sufficientemente lungo
+ad avere scadenze multiple, e lo stesso può accadere anche se si usa un
+\textit{thread} di notifica. 
+
+Per questo motivo il gestore del segnale o il \textit{thread} di notifica può
+ottenere una indicazione di quante volte il timer è scaduto dall'invio della
+notifica utilizzando la funzione \funcd{timer\_getoverrun}, il cui prototipo è:
+\begin{functions}
+  \headdecl{time.h}
+
+  \funcdecl{int timer\_getoverrun(timer\_t timerid)}
+  
+  Ottiene il numero di scadenze di un timer POSIX.
+  
+  \bodydesc{La funzione restituisce il numero di scadenze di un timer in caso
+    di successo e $-1$ in caso di errore, nel qual caso \var{errno} assumerà
+    il valore:
+  \begin{errlist}
+  \item[\errcode{EINVAL}] \param{timerid} non indica un timer valido.
+  \end{errlist}
+}
+\end{functions}
+
+La funzione ritorna il numero delle scadenze avvenute, che può anche essere
+nullo se non ve ne sono state. Come estensione specifica di Linux,\footnote{in
+  realtà lo standard POSIX.1-2001 prevede gli \textit{overrun} solo per i
+  segnali e non ne parla affatto in riferimento ai \textit{thread}.}  quando
+si usa un segnale come meccanismo di notifica, si può ottenere direttamente
+questo valore nel campo \var{si\_overrun} della struttura \struct{siginfo\_t}
+(illustrata in fig.~\ref{fig:sig_siginfo_t}) restituita al gestore del segnale
+installato con \func{sigaction}; in questo modo non è più necessario eseguire
+successivamente una chiamata a questa funzione per ottenere il numero delle
+scadenze. Al gestore del segnale viene anche restituito, come ulteriore
+informazione, l'identificativo del timer, in questo caso nel campo
+\var{si\_timerid}.
+
+Qualora si voglia rileggere lo stato corrente di un timer, ed ottenere il
+tempo mancante ad una sua eventuale scadenza, si deve utilizzare la funzione
+\funcd{timer\_gettime}, il cui prototipo è:
+\begin{functions}
+  \headdecl{time.h}
+
+  \funcdecl{int timer\_gettime(timer\_t timerid, int flags, struct
+    itimerspec *curr\_value)}
+  
+  Legge lo stato di un timer POSIX.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore, nel qual caso \var{errno} assumerà uno dei seguenti valori:
+  \begin{errlist}
+  \item[\errcode{EINVAL}] \param{timerid} non indica un timer valido.
+  \item[\errcode{EFAULT}] si è specificato un indirizzo non valido
+    per \param{curr\_value}.
+  \end{errlist}
+}
+\end{functions}
+
+La funzione restituisce nella struttura \struct{itimerspec} puntata
+da \param{curr\_value} il tempo restante alla prossima scadenza nel campo
+\var{it\_value}. Questo tempo viene sempre indicato in forma relativa, anche
+nei casi in cui il timer era stato precedentemente impostato con
+\const{TIMER\_ABSTIME} indicando un tempo assoluto.  Il ritorno di un valore
+nullo nel campo \var{it\_value} significa che il timer è disarmato o è
+definitivamente scaduto. 
+
+Nel campo \var{it\_interval} di \param{curr\_value} viene invece restituito,
+se questo era stato impostato, il periodo di ripetizione del timer.  Anche in
+questo caso il ritorno di un valore nullo significa che il timer non era stato
+impostato per una ripetizione e doveva operare, come suol dirsi, a colpo
+singolo (in gergo \textit{one shot}).
+
+Infine, quando un timer non viene più utilizzato, lo si può cancellare,
+rimuovendolo dal sistema e recuperando le relative risorse, effettuando in
+sostanza l'operazione inversa rispetto a \funcd{timer\_create}. Per questo
+compito lo standard prevede una apposita funzione \funcd{timer\_delete}, il
+cui prototipo è:
+\begin{functions}
+  \headdecl{time.h}
+
+  \funcdecl{int timer\_delete(timer\_t timerid)}
+  
+  Cancella un timer POSIX.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore, nel qual caso \var{errno} assumerà uno dei seguenti valori:
+    \begin{errlist}
+    \item[\errcode{EINVAL}] \param{timerid} non indica un timer valido.
+    \end{errlist}
+}
+\end{functions}
+
+La funzione elimina il timer identificato da \param{timerid}, disarmandolo se
+questo era stato attivato. Nel caso, poco probabile ma comunque possibile, che
+un timer venga cancellato prima della ricezione del segnale pendente per la
+notifica di una scadenza, il comportamento del sistema è indefinito.
+
+\subsection{Ulteriori funzioni di gestione}
+\label{sec:sig_specific_features}
+
+In questo ultimo paragrafo esamineremo le rimanenti funzioni di gestione dei
+segnali non descritte finora, relative agli aspetti meno utilizzati e più
+``\textsl{esoterici}'' della interfaccia.
+
+La prima di queste funzioni è \funcd{sigpending}, anch'essa introdotta dallo
+standard POSIX.1; il suo prototipo è:
+\begin{prototype}{signal.h}
+{int sigpending(sigset\_t *set)} 
+  
+Scrive in \param{set} l'insieme dei segnali pendenti.
+  
+  \bodydesc{La funzione restituisce zero in caso di successo e $-1$ per un
+    errore.}
+\end{prototype}
+
+La funzione permette di ricavare quali sono i segnali pendenti per il processo
+in corso, cioè i segnali che sono stati inviati dal kernel ma non sono stati
+ancora ricevuti dal processo in quanto bloccati. Non esiste una funzione
+equivalente nella vecchia interfaccia, ma essa è tutto sommato poco utile,
+dato che essa può solo assicurare che un segnale è stato inviato, dato che
+escluderne l'avvenuto invio al momento della chiamata non significa nulla
+rispetto a quanto potrebbe essere in un qualunque momento successivo.
+
+Una delle caratteristiche di BSD, disponibile anche in Linux, è la possibilità
+di usare uno \itindex{stack} \textit{stack} alternativo per i segnali; è cioè
+possibile fare usare al sistema un altro \itindex{stack} \textit{stack}
+(invece di quello relativo al processo, vedi sez.~\ref{sec:proc_mem_layout})
+solo durante l'esecuzione di un gestore.  L'uso di uno \textit{stack}
+alternativo è del tutto trasparente ai gestori, occorre però seguire una certa
+procedura:
+\begin{enumerate*}
+\item allocare un'area di memoria di dimensione sufficiente da usare come
+  \textit{stack} alternativo;
+\item usare la funzione \func{sigaltstack} per rendere noto al sistema
+  l'esistenza e la locazione dello \textit{stack} alternativo;
+\item quando si installa un gestore occorre usare \func{sigaction}
+  specificando il flag \const{SA\_ONSTACK} (vedi tab.~\ref{tab:sig_sa_flag})
+  per dire al sistema di usare lo \textit{stack} alternativo durante
+  l'esecuzione del gestore.
+\end{enumerate*}
+
+In genere il primo passo viene effettuato allocando un'opportuna area di
+memoria con \code{malloc}; in \file{signal.h} sono definite due costanti,
+\const{SIGSTKSZ} e \const{MINSIGSTKSZ}, che possono essere utilizzate per
+allocare una quantità di spazio opportuna, in modo da evitare overflow. La
+prima delle due è la dimensione canonica per uno \itindex{stack}
+\textit{stack} di segnali e di norma è sufficiente per tutti gli usi normali.
+
+La seconda è lo spazio che occorre al sistema per essere in grado di lanciare
+il gestore e la dimensione di uno \textit{stack} alternativo deve essere
+sempre maggiore di questo valore. Quando si conosce esattamente quanto è lo
+spazio necessario al gestore gli si può aggiungere questo valore per allocare
+uno \itindex{stack} \textit{stack} di dimensione sufficiente.
 
+Come accennato, per poter essere usato, lo \itindex{stack} \textit{stack} per
+i segnali deve essere indicato al sistema attraverso la funzione
+\funcd{sigaltstack}; il suo prototipo è:
+\begin{prototype}{signal.h}
+{int sigaltstack(const stack\_t *ss, stack\_t *oss)}
+  
+Installa un nuovo \textit{stack} per i segnali.
+  
+  \bodydesc{La funzione restituisce zero in caso di successo e $-1$ per un
+    errore, nel qual caso \var{errno} assumerà i valori:
 
- fig.~\ref{fig:file_sigevent}
+  \begin{errlist}
+  \item[\errcode{ENOMEM}] la dimensione specificata per il nuovo
+    \textit{stack} è minore di \const{MINSIGSTKSZ}.
+  \item[\errcode{EPERM}] uno degli indirizzi non è valido.
+  \item[\errcode{EFAULT}] si è cercato di cambiare lo \textit{stack}
+    alternativo mentre questo è attivo (cioè il processo è in esecuzione su di
+    esso).
+  \item[\errcode{EINVAL}] \param{ss} non è nullo e \var{ss\_flags} contiene un
+  valore diverso da zero che non è \const{SS\_DISABLE}.
+  \end{errlist}}
+\end{prototype}
+
+La funzione prende come argomenti puntatori ad una struttura di tipo
+\var{stack\_t}, definita in fig.~\ref{fig:sig_stack_t}. I due valori
+\param{ss} e \param{oss}, se non nulli, indicano rispettivamente il nuovo
+\itindex{stack} \textit{stack} da installare e quello corrente (che viene
+restituito dalla funzione per un successivo ripristino).
 
 \begin{figure}[!htb]
   \footnotesize \centering
   \begin{minipage}[c]{15cm}
-    \includestruct{listati/sigevent.h}
+    \includestruct{listati/stack_t.h}
   \end{minipage} 
   \normalsize 
-  \caption{La struttura \structd{sigevent}, usata per specificare le modalità
-    di notifica degli eventi relativi alle operazioni di I/O asincrono.}
-  \label{fig:file_sigevent}
+  \caption{La struttura \structd{stack\_t}.} 
+  \label{fig:sig_stack_t}
 \end{figure}
 
+Il campo \var{ss\_sp} di \struct{stack\_t} indica l'indirizzo base dello
+\itindex{stack} \textit{stack}, mentre \var{ss\_size} ne indica la dimensione;
+il campo \var{ss\_flags} invece indica lo stato dello \textit{stack}.
+Nell'indicare un nuovo \textit{stack} occorre inizializzare \var{ss\_sp} e
+\var{ss\_size} rispettivamente al puntatore e alla dimensione della memoria
+allocata, mentre \var{ss\_flags} deve essere nullo.  Se invece si vuole
+disabilitare uno \textit{stack} occorre indicare \const{SS\_DISABLE} come
+valore di \var{ss\_flags} e gli altri valori saranno ignorati.
+
+Se \param{oss} non è nullo verrà restituito dalla funzione indirizzo e
+dimensione dello \itindex{stack} \textit{stack} corrente nei relativi campi,
+mentre \var{ss\_flags} potrà assumere il valore \const{SS\_ONSTACK} se il
+processo è in esecuzione sullo \textit{stack} alternativo (nel qual caso non è
+possibile cambiarlo) e \const{SS\_DISABLE} se questo non è abilitato.
 
+In genere si installa uno \itindex{stack} \textit{stack} alternativo per i
+segnali quando si teme di avere problemi di esaurimento dello \textit{stack}
+standard o di superamento di un limite (vedi
+sez.~\ref{sec:sys_resource_limit}) imposto con chiamate del tipo
+\code{setrlimit(RLIMIT\_STACK, \&rlim)}.  In tal caso infatti si avrebbe un
+segnale di \const{SIGSEGV}, che potrebbe essere gestito soltanto avendo
+abilitato uno \itindex{stack} \textit{stack} alternativo.
 
+Si tenga presente che le funzioni chiamate durante l'esecuzione sullo
+\textit{stack} alternativo continueranno ad usare quest'ultimo, che, al
+contrario di quanto avviene per lo \itindex{stack} \textit{stack} ordinario
+dei processi, non si accresce automaticamente (ed infatti eccederne le
+dimensioni può portare a conseguenze imprevedibili).  Si ricordi infine che
+una chiamata ad una funzione della famiglia \func{exec} cancella ogni
+\textit{stack} alternativo.
 
+Abbiamo visto in fig.~\ref{fig:sig_sleep_incomplete} come si possa usare
+\func{longjmp} per uscire da un gestore rientrando direttamente nel corpo
+del programma; sappiamo però che nell'esecuzione di un gestore il segnale
+che l'ha invocato viene bloccato, e abbiamo detto che possiamo ulteriormente
+modificarlo con \func{sigprocmask}. 
 
-% TODO trattare i Posix timer, e le fuzioni:
-% timer_getoverrun, timer_gettime, timer_settime, timer_create, timer_delete
+Resta quindi il problema di cosa succede alla maschera dei segnali quando si
+esce da un gestore usando questa funzione. Il comportamento dipende
+dall'implementazione; in particolare la semantica usata da BSD prevede che sia
+ripristinata la maschera dei segnali precedente l'invocazione, come per un
+normale ritorno, mentre quella usata da System V no.
 
+Lo standard POSIX.1 non specifica questo comportamento per \func{setjmp} e
+\func{longjmp}, ed il comportamento delle \acr{glibc} dipende da quale delle
+caratteristiche si sono abilitate con le macro viste in
+sez.~\ref{sec:intro_gcc_glibc_std}.
 
-\subsection{Le interfacce per la notifica attraverso i file descriptor}
-\label{sec:sig_signalfd_eventfd}
+Lo standard POSIX però prevede anche la presenza di altre due funzioni
+\funcd{sigsetjmp} e \funcd{siglongjmp}, che permettono di decidere quale dei
+due comportamenti il programma deve assumere; i loro prototipi sono:
+\begin{functions}
+  \headdecl{setjmp.h} 
+  
+  \funcdecl{int sigsetjmp(sigjmp\_buf env, int savesigs)} Salva il contesto
+  dello \textit{stack} per un \index{salto~non-locale} salto non-locale.
  
+  \funcdecl{void siglongjmp(sigjmp\_buf env, int val)} Esegue un salto
+  non-locale su un precedente contesto.
+
+  \bodydesc{Le due funzioni sono identiche alle analoghe \func{setjmp} e
+    \func{longjmp} di sez.~\ref{sec:proc_longjmp}, ma consentono di specificare
+    il comportamento sul ripristino o meno della maschera dei segnali.}
+\end{functions}
 
-% TODO trattare qui eventfd signalfd e timerfd introdotte con il 2.6.22 
-% timerfd è stata tolta nel 2.6.23 e rifatta per bene nel 2.6.25
-% vedi: http://lwn.net/Articles/233462/
-%       http://lwn.net/Articles/245533/
-%       http://lwn.net/Articles/267331/
+Le due funzioni prendono come primo argomento la variabile su cui viene
+salvato il contesto dello \itindex{stack} \textit{stack} per permettere il
+\index{salto~non-locale} salto non-locale; nel caso specifico essa è di tipo
+\type{sigjmp\_buf}, e non \type{jmp\_buf} come per le analoghe di
+sez.~\ref{sec:proc_longjmp} in quanto in questo caso viene salvata anche la
+maschera dei segnali.
+
+Nel caso di \func{sigsetjmp}, se si specifica un valore di \param{savesigs}
+diverso da zero la maschera dei valori sarà salvata in \param{env} e
+ripristinata in un successivo \func{siglongjmp}; quest'ultima funzione, a
+parte l'uso di \type{sigjmp\_buf} per \param{env}, è assolutamente identica a
+\func{longjmp}.
 
 
 
@@ -3113,13 +3409,13 @@ orologio
 % LocalWords:  how oldset BLOCK UNBLOCK SETMASK sigsuspend sigaltstack malloc
 % LocalWords:  SIGSTKSZ MINSIGSTKSZ ss oss ENOMEM flags DISABLE sp setrlimit LB
 % LocalWords:  RLIMIT rlim sigsetjmp siglongjmp sigjmp buf env savesigs jmp ptr
-% LocalWords:  SIGRTMIN SIGRTMAX sigval sigevent sigqueue EAGAIN sysctl safe
+% LocalWords:  SIGRTMIN SIGRTMAX sigval sigevent sigqueue EAGAIN sysctl safe tp
 % LocalWords:  QUEUE thread sigwait sigwaitinfo sigtimedwait info DEF SLB bind
 % LocalWords:  function accept return cfgetispeed cfgetospeed cfsetispeed chdir
 % LocalWords:  cfsetospeed chmod chown gettime close connect creat dup execle
 % LocalWords:  execve fchmod fchown fdatasync fpathconf fstat fsync ftruncate
 % LocalWords:  getegid geteuid getgid getgroups getpeername getpgrp getppid sem
-% LocalWords:  getsockname getsockopt getuid listen lseek lstat mkdir mkfifo
+% LocalWords:  getsockname getsockopt getuid listen lseek lstat mkdir mkfifo tv
 % LocalWords:  pathconf poll posix pselect read readlink recv recvfrom recvmsg
 % LocalWords:  rename rmdir select send sendmsg sendto setgid setpgid setsid
 % LocalWords:  setsockopt setuid shutdown sigpause socketpair stat symlink page
@@ -3135,6 +3431,10 @@ orologio
 % LocalWords:  openat readlinkat renameat symlinkat unlinkat utimensat utimes
 % LocalWords:  LinuxThread NTPL Library clockid evp timerid sigev notify high
 % LocalWords:  resolution CONFIG RES patch REALTIME MONOTONIC RAW NTP CPUTIME
+% LocalWords:  tick calendar The Epoch list getcpuclockid capability CAP getres
+% LocalWords:  ENOSYS pthread ENOENT NULL attribute itimerspec new old ABSTIME
+% LocalWords:  epoch multiplexing overrun res lpthread sec nsec curr one shot
+% LocalWords:  delete
 
 
 %%% Local Variables: