Aggiornamento data copyright
[gapil.git] / ipc.tex
diff --git a/ipc.tex b/ipc.tex
index 04fe2cdf5625d4deb87393086d0f47089f3b1297..491d29d9587f21c3160231b822b2da3ed9481c82 100644 (file)
--- a/ipc.tex
+++ b/ipc.tex
@@ -1,13 +1,14 @@
 %% ipc.tex
 %%
-%% Copyright (C) 2000-2002 Simone Piccardi.  Permission is granted to
+%% Copyright (C) 2000-2011 Simone Piccardi.  Permission is granted to
 %% copy, distribute and/or modify this document under the terms of the GNU Free
 %% Documentation License, Version 1.1 or any later version published by the
-%% Free Software Foundation; with the Invariant Sections being "Prefazione",
+%% Free Software Foundation; with the Invariant Sections being "Un preambolo",
 %% with no Front-Cover Texts, and with no Back-Cover Texts.  A copy of the
 %% license is included in the section entitled "GNU Free Documentation
 %% License".
 %%
+
 \chapter{La comunicazione fra processi}
 \label{cha:IPC}
 
@@ -41,7 +42,7 @@ ne gestiscono l'uso e le varie forme in cui si 
 
 Le \textit{pipe} nascono sostanzialmente con Unix, e sono il primo, e tuttora
 uno dei più usati, meccanismi di comunicazione fra processi. Si tratta in
-sostanza di una una coppia di file descriptor\footnote{si tenga presente che
+sostanza di una coppia di file descriptor\footnote{si tenga presente che
   le pipe sono oggetti creati dal kernel e non risiedono su disco.} connessi
 fra di loro in modo che se quanto scrive su di uno si può rileggere
 dall'altro. Si viene così a costituire un canale di comunicazione tramite i
@@ -65,10 +66,11 @@ La funzione restituisce la coppia di file descriptor nel vettore
 accennato concetto di funzionamento di una pipe è semplice: quello che si
 scrive nel file descriptor aperto in scrittura viene ripresentato tale e quale
 nel file descriptor aperto in lettura. I file descriptor infatti non sono
-connessi a nessun file reale, ma ad un buffer nel kernel, la cui dimensione è
-specificata dal parametro di sistema \const{PIPE\_BUF}, (vedi
-\secref{sec:sys_file_limits}). Lo schema di funzionamento di una pipe è
-illustrato in \figref{fig:ipc_pipe_singular}, in cui sono illustrati i due
+connessi a nessun file reale, ma, come accennato in
+sez.~\ref{sec:file_sendfile_splice}, ad un buffer nel kernel, la cui
+dimensione è specificata dal parametro di sistema \const{PIPE\_BUF}, (vedi
+sez.~\ref{sec:sys_file_limits}). Lo schema di funzionamento di una pipe è
+illustrato in fig.~\ref{fig:ipc_pipe_singular}, in cui sono illustrati i due
 capi della pipe, associati a ciascun file descriptor, con le frecce che
 indicano la direzione del flusso dei dati.
 
@@ -80,12 +82,12 @@ indicano la direzione del flusso dei dati.
 \end{figure}
 
 Chiaramente creare una pipe all'interno di un singolo processo non serve a
-niente; se però ricordiamo quanto esposto in \secref{sec:file_sharing}
+niente; se però ricordiamo quanto esposto in sez.~\ref{sec:file_sharing}
 riguardo al comportamento dei file descriptor nei processi figli, è immediato
 capire come una pipe possa diventare un meccanismo di intercomunicazione. Un
 processo figlio infatti condivide gli stessi file descriptor del padre,
 compresi quelli associati ad una pipe (secondo la situazione illustrata in
-\figref{fig:ipc_pipe_fork}). In questo modo se uno dei processi scrive su un
+fig.~\ref{fig:ipc_pipe_fork}). In questo modo se uno dei processi scrive su un
 capo della pipe, l'altro può leggere.
 
 \begin{figure}[htb]
@@ -98,7 +100,7 @@ capo della pipe, l'altro pu
 
 Tutto ciò ci mostra come sia immediato realizzare un meccanismo di
 comunicazione fra processi attraverso una pipe, utilizzando le proprietà
-ordinarie dei file, ma ci mostra anche qual'è il principale\footnote{Stevens
+ordinarie dei file, ma ci mostra anche qual è il principale\footnote{Stevens
   in \cite{APUE} riporta come limite anche il fatto che la comunicazione è
   unidirezionale, ma in realtà questo è un limite facilmente superabile usando
   una coppia di pipe.} limite nell'uso delle pipe. È necessario infatti che i
@@ -131,18 +133,18 @@ da altri processi.
 Per capire meglio il funzionamento delle pipe faremo un esempio di quello che
 è il loro uso più comune, analogo a quello effettuato della shell, e che
 consiste nell'inviare l'output di un processo (lo standard output) sull'input
-di un'altro. Realizzeremo il programma di esempio nella forma di un
-\textit{CGI}\footnote{Un CGI (\textit{Common Gateway Interface}) è un
+di un altro. Realizzeremo il programma di esempio nella forma di un
+\textit{CGI}\footnote{un CGI (\textit{Common Gateway Interface}) è un
   programma che permette la creazione dinamica di un oggetto da inserire
   all'interno di una pagina HTML.}  per Apache, che genera una immagine JPEG
-di un codice a barre, specificato come parametro di input.
+di un codice a barre, specificato come argomento in ingresso.
 
 Un programma che deve essere eseguito come \textit{CGI} deve rispondere a
 delle caratteristiche specifiche, esso infatti non viene lanciato da una
 shell, ma dallo stesso web server, alla richiesta di una specifica URL, che di
 solito ha la forma:
 \begin{verbatim}
-    http://www.sito.it/cgi-bin/programma?parametro
+    http://www.sito.it/cgi-bin/programma?argomento
 \end{verbatim}
 ed il risultato dell'elaborazione deve essere presentato (con una intestazione
 che ne descrive il mime-type) sullo standard output, in modo che il web-server
@@ -154,38 +156,39 @@ Per realizzare quanto voluto useremo in sequenza i programmi \cmd{barcode} e
 codici a barre corrispondenti ad una qualunque stringa, mentre il secondo
 serve per poter effettuare la conversione della stessa immagine in formato
 JPEG. Usando una pipe potremo inviare l'output del primo sull'input del
-secondo, secondo lo schema mostrato in \figref{fig:ipc_pipe_use}, in cui la
+secondo, secondo lo schema mostrato in fig.~\ref{fig:ipc_pipe_use}, in cui la
 direzione del flusso dei dati è data dalle frecce continue.
 
 \begin{figure}[htb]
   \centering
   \includegraphics[height=5cm]{img/pipeuse}
   \caption{Schema dell'uso di una pipe come mezzo di comunicazione fra
-    due processi attraverso attraverso l'esecuzione una \func{fork} e la
-    chiusura dei capi non utilizzati.}
+    due processi attraverso l'esecuzione una \func{fork} e la chiusura dei
+    capi non utilizzati.}
   \label{fig:ipc_pipe_use}
 \end{figure}
 
 Si potrebbe obiettare che sarebbe molto più semplice salvare il risultato
 intermedio su un file temporaneo. Questo però non tiene conto del fatto che un
 \textit{CGI} deve poter gestire più richieste in concorrenza, e si avrebbe una
-evidente race condition\index{race condition} in caso di accesso simultaneo a
-detto file.\footnote{il problema potrebbe essere superato determinando in
-  anticipo un nome appropriato per il file temporaneo, che verrebbe utilizzato
-  dai vari sotto-processi, e cancellato alla fine della loro esecuzione; ma a
-  questo le cose non sarebbero più tanto semplici.}  L'uso di una pipe invece
-permette di risolvere il problema in maniera semplice ed elegante, oltre ad
-essere molto più efficiente, dato che non si deve scrivere su disco.
+evidente \itindex{race~condition} \textit{race condition} in caso di accesso
+simultaneo a detto file.\footnote{il problema potrebbe essere superato
+  determinando in anticipo un nome appropriato per il file temporaneo, che
+  verrebbe utilizzato dai vari sotto-processi, e cancellato alla fine della
+  loro esecuzione; ma a questo punto le cose non sarebbero più tanto
+  semplici.}  L'uso di una pipe invece permette di risolvere il problema in
+maniera semplice ed elegante, oltre ad essere molto più efficiente, dato che
+non si deve scrivere su disco.
 
 Il programma ci servirà anche come esempio dell'uso delle funzioni di
 duplicazione dei file descriptor che abbiamo trattato in
-\secref{sec:file_dup}, in particolare di \func{dup2}. È attraverso queste
+sez.~\ref{sec:file_dup}, in particolare di \func{dup2}. È attraverso queste
 funzioni infatti che è possibile dirottare gli stream standard dei processi
-(che abbiamo visto in \secref{sec:file_std_descr} e
-\secref{sec:file_std_stream}) sulla pipe. In \figref{fig:ipc_barcodepage_code}
-abbiamo riportato il corpo del programma, il cui codice completo è disponibile
-nel file \file{BarCodePage.c} che si trova nella directory dei sorgenti.
-
+(che abbiamo visto in sez.~\ref{sec:file_std_descr} e
+sez.~\ref{sec:file_std_stream}) sulla pipe. In
+fig.~\ref{fig:ipc_barcodepage_code} abbiamo riportato il corpo del programma,
+il cui codice completo è disponibile nel file \file{BarCodePage.c} che si
+trova nella directory dei sorgenti.
 
 \begin{figure}[!htb]
   \footnotesize \centering
@@ -203,7 +206,7 @@ le due pipe che serviranno per la comunicazione fra i due comandi utilizzati
 per produrre il codice a barre; si ha cura di controllare la riuscita della
 chiamata, inviando in caso di errore un messaggio invece dell'immagine
 richiesta.\footnote{la funzione \func{WriteMess} non è riportata in
-  \secref{fig:ipc_barcodepage_code}; essa si incarica semplicemente di
+  fig.~\ref{fig:ipc_barcodepage_code}; essa si incarica semplicemente di
   formattare l'uscita alla maniera dei CGI, aggiungendo l'opportuno
   \textit{mime type}, e formattando il messaggio in HTML, in modo che
   quest'ultimo possa essere visualizzato correttamente da un browser.}
@@ -300,11 +303,11 @@ programma indicato) in caso si sia indicato \code{"r"}, o in sola scrittura (e
 quindi associato allo standard input) in caso di \code{"w"}.
 
 Lo stream restituito da \func{popen} è identico a tutti gli effetti ai file
-stream visti in \capref{cha:files_std_interface}, anche se è collegato ad una
-pipe e non ad un file, e viene sempre aperto in modalità
-\textit{fully-buffered} (vedi \secref{sec:file_buffering}); l'unica differenza
-con gli usuali stream è che dovrà essere chiuso dalla seconda delle due nuove
-funzioni, \funcd{pclose}, il cui prototipo è:
+stream visti in cap.~\ref{cha:files_std_interface}, anche se è collegato ad
+una pipe e non ad un file, e viene sempre aperto in modalità
+\textit{fully-buffered} (vedi sez.~\ref{sec:file_buffering}); l'unica
+differenza con gli usuali stream è che dovrà essere chiuso dalla seconda delle
+due nuove funzioni, \funcd{pclose}, il cui prototipo è:
 \begin{prototype}{stdio.h}
 {int pclose(FILE *stream)}
 
@@ -320,7 +323,7 @@ attendendo la terminazione del processo ad essa associato.
 \func{popen}.
 
 Per illustrare l'uso di queste due funzioni riprendiamo il problema
-precedente: il programma mostrato in \figref{fig:ipc_barcodepage_code} per
+precedente: il programma mostrato in fig.~\ref{fig:ipc_barcodepage_code} per
 quanto funzionante, è (volutamente) codificato in maniera piuttosto complessa,
 inoltre nella pratica sconta un problema di \cmd{gs} che non è in
 grado\footnote{nella versione GNU Ghostscript 6.53 (2002-02-13).} di
@@ -364,13 +367,13 @@ semplificare notevolmente la stesura del codice.
 Nel nostro caso, dato che ciascun processo deve scrivere il suo output sullo
 standard input del successivo, occorrerà usare \func{popen} aprendo la pipe in
 scrittura. Il codice del nuovo programma è riportato in
-\figref{fig:ipc_barcode_code}.  Come si può notare l'ordine di invocazione dei
-programmi è l'inverso di quello in cui ci si aspetta che vengano
+fig.~\ref{fig:ipc_barcode_code}.  Come si può notare l'ordine di invocazione
+dei programmi è l'inverso di quello in cui ci si aspetta che vengano
 effettivamente eseguiti. Questo non comporta nessun problema dato che la
 lettura su una pipe è bloccante, per cui ciascun processo, per quanto lanciato
 per primo, si bloccherà in attesa di ricevere sullo standard input il
-risultato dell'elaborazione del precedente, benchè quest'ultimo venga
-invocato dopo.
+risultato dell'elaborazione del precedente, benché quest'ultimo venga invocato
+dopo.
 
 \begin{figure}[!htb]
   \footnotesize \centering
@@ -409,24 +412,24 @@ create, tutte le pipe create con \func{pclose}.
 \subsection{Le \textit{pipe} con nome, o \textit{fifo}}
 \label{sec:ipc_named_pipe}
 
-Come accennato in \secref{sec:ipc_pipes} il problema delle \textit{pipe} è che
-esse possono essere utilizzate solo da processi con un progenitore comune o
-nella relazione padre/figlio; per superare questo problema lo standard POSIX.1
-ha definito dei nuovi oggetti, le \textit{fifo}, che hanno le stesse
+Come accennato in sez.~\ref{sec:ipc_pipes} il problema delle \textit{pipe} è
+che esse possono essere utilizzate solo da processi con un progenitore comune
+o nella relazione padre/figlio; per superare questo problema lo standard
+POSIX.1 ha definito dei nuovi oggetti, le \textit{fifo}, che hanno le stesse
 caratteristiche delle pipe, ma che invece di essere strutture interne del
 kernel, visibili solo attraverso un file descriptor, sono accessibili
-attraverso un inode\index{inode} che risiede sul filesystem, così che i
+attraverso un \index{inode} inode che risiede sul filesystem, così che i
 processi le possono usare senza dovere per forza essere in una relazione di
 \textsl{parentela}.
 
 Utilizzando una \textit{fifo} tutti i dati passeranno, come per le pipe,
 attraverso un apposito buffer nel kernel, senza transitare dal filesystem;
-l'inode\index{inode} allocato sul filesystem serve infatti solo a fornire un
+\index{inode} l'inode allocato sul filesystem serve infatti solo a fornire un
 punto di riferimento per i processi, che permetta loro di accedere alla stessa
 fifo; il comportamento delle funzioni di lettura e scrittura è identico a
-quello illustrato per le pipe in \secref{sec:ipc_pipes}.
+quello illustrato per le pipe in sez.~\ref{sec:ipc_pipes}.
 
-Abbiamo già visto in \secref{sec:file_mknod} le funzioni \func{mknod} e
+Abbiamo già visto in sez.~\ref{sec:file_mknod} le funzioni \func{mknod} e
 \func{mkfifo} che permettono di creare una fifo; per utilizzarne una un
 processo non avrà che da aprire il relativo file speciale o in lettura o
 scrittura; nel primo caso sarà collegato al capo di uscita della fifo, e dovrà
@@ -451,8 +454,8 @@ comunque una fifo in scrittura anche se non ci sono ancora processi il
 lettura; è possibile anche usare la fifo all'interno di un solo processo, nel
 qual caso però occorre stare molto attenti alla possibili situazioni di
 stallo.\footnote{se si cerca di leggere da una fifo che non contiene dati si
-  avrà un deadlock\index{deadlock} immediato, dato che il processo si blocca e
-  non potrà quindi mai eseguire le funzioni di scrittura.}
+  avrà un \itindex{deadlock} deadlock immediato, dato che il processo si
+  blocca e non potrà quindi mai eseguire le funzioni di scrittura.}
 
 Per la loro caratteristica di essere accessibili attraverso il filesystem, è
 piuttosto frequente l'utilizzo di una fifo come canale di comunicazione nelle
@@ -460,7 +463,7 @@ situazioni un processo deve ricevere informazioni da altri. In questo caso 
 fondamentale che le operazioni di scrittura siano atomiche; per questo si deve
 sempre tenere presente che questo è vero soltanto fintanto che non si supera
 il limite delle dimensioni di \const{PIPE\_BUF} (si ricordi quanto detto in
-\secref{sec:ipc_pipes}).
+sez.~\ref{sec:ipc_pipes}).
 
 A parte il caso precedente, che resta probabilmente il più comune, Stevens
 riporta in \cite{APUE} altre due casistiche principali per l'uso delle fifo:
@@ -470,7 +473,7 @@ riporta in \cite{APUE} altre due casistiche principali per l'uso delle fifo:
   sull'input di parecchi altri (attraverso l'uso del comando \cmd{tee}).
   
 \item Come canale di comunicazione fra client ed server (il modello
-  \textit{client-server} è illustrato in \secref{sec:net_cliserv}).
+  \textit{client-server} è illustrato in sez.~\ref{sec:net_cliserv}).
 \end{itemize}
 
 Nel primo caso quello che si fa è creare tante fifo, da usare come standard
@@ -489,7 +492,7 @@ la struttura sequenziale delle fifo, i client dovrebbero sapere, prima di
 leggerli, quando i dati inviati sono destinati a loro.
 
 Per risolvere questo problema, si può usare un'architettura come quella
-illustrata in \figref{fig:ipc_fifo_server_arch} in cui i client inviano le
+illustrata in fig.~\ref{fig:ipc_fifo_server_arch} in cui i client inviano le
 richieste al server su una fifo nota mentre le risposte vengono reinviate dal
 server a ciascuno di essi su una fifo temporanea creata per l'occasione.
 
@@ -506,7 +509,7 @@ un server di \textit{fortunes}, che restituisce, alle richieste di un client,
 un detto a caso estratto da un insieme di frasi; sia il numero delle frasi
 dell'insieme, che i file da cui esse vengono lette all'avvio, sono importabili
 da riga di comando. Il corpo principale del server è riportato in
-\figref{fig:ipc_fifo_server}, dove si è tralasciata la parte che tratta la
+fig.~\ref{fig:ipc_fifo_server}, dove si è tralasciata la parte che tratta la
 gestione delle opzioni a riga di comando, che effettua il settaggio delle
 variabili \var{fortunefilename}, che indica il file da cui leggere le frasi,
 ed \var{n}, che indica il numero di frasi tenute in memoria, ad un valore
@@ -528,10 +531,11 @@ Il server richiede (\texttt{\small 12}) che sia stata impostata una dimensione
 dell'insieme delle frasi non nulla, dato che l'inizializzazione del vettore
 \var{fortune} avviene solo quando questa dimensione viene specificata, la
 presenza di un valore nullo provoca l'uscita dal programma attraverso la
-routine (non riportata) che ne stampa le modalità d'uso.  Dopo di che installa
-(\texttt{\small 13--15}) la funzione che gestisce i segnali di interruzione
-(anche questa non è riportata in \figref{fig:ipc_fifo_server}) che si limita a
-rimuovere dal filesystem la fifo usata dal server per comunicare.
+funzione (non riportata) che ne stampa le modalità d'uso.  Dopo di che
+installa (\texttt{\small 13--15}) la funzione che gestisce i segnali di
+interruzione (anche questa non è riportata in fig.~\ref{fig:ipc_fifo_server})
+che si limita a rimuovere dal filesystem la fifo usata dal server per
+comunicare.
 
 Terminata l'inizializzazione (\texttt{\small 16}) si effettua la chiamata alla
 funzione \code{FortuneParse} che legge dal file specificato in
@@ -564,7 +568,7 @@ ricevuta la risposta, uscir
 A questo punto il server resta (se non ci sono altri client che stanno
 effettuando richieste) con la fifo chiusa sul lato in lettura, ed in questo
 stato la funzione \func{read} non si bloccherà in attesa di input, ma
-ritornerà in continuazione, restituendo un end-of-file.\footnote{Si è usata
+ritornerà in continuazione, restituendo un end-of-file.\footnote{si è usata
   questa tecnica per compatibilità, Linux infatti supporta l'apertura delle
   fifo in lettura/scrittura, per cui si sarebbe potuto effettuare una singola
   apertura con \const{O\_RDWR}, la doppia apertura comunque ha il vantaggio
@@ -584,7 +588,7 @@ a \func{read} possono bloccarsi.
 A questo punto si può entrare nel ciclo principale del programma che fornisce
 le risposte ai client (\texttt{\small 34--50}); questo viene eseguito
 indefinitamente (l'uscita del server viene effettuata inviando un segnale, in
-modo da passare attraverso la routine di chiusura che cancella la fifo).
+modo da passare attraverso la funzione di chiusura che cancella la fifo).
 
 Il server è progettato per accettare come richieste dai client delle stringhe
 che contengono il nome della fifo sulla quale deve essere inviata la risposta.
@@ -597,9 +601,9 @@ all'apertura della fifo per la risposta, che poi \texttt{\small 47--48}) vi
 sarà scritta. Infine (\texttt{\small 49}) si chiude la fifo di risposta che
 non serve più.
 
-Il codice del client è invece riportato in \figref{fig:ipc_fifo_client}, anche
-in questo caso si è omessa la gestione delle opzioni e la funzione che stampa
-a video le informazioni di utilizzo ed esce, riportando solo la sezione
+Il codice del client è invece riportato in fig.~\ref{fig:ipc_fifo_client},
+anche in questo caso si è omessa la gestione delle opzioni e la funzione che
+stampa a video le informazioni di utilizzo ed esce, riportando solo la sezione
 principale del programma e le definizioni delle variabili. Il codice completo
 è nel file \file{FortuneClient.c} dei sorgenti allegati.
 
@@ -645,30 +649,32 @@ state raccolte nella libreria \file{libgapil.so}, per poter usare quest'ultima
 occorrerà definire la speciale variabile di ambiente \code{LD\_LIBRARY\_PATH}
 in modo che il linker dinamico possa accedervi.
 
-In generale questa variabile indica il pathname della directory contenente la
-libreria. Nell'ipotesi (che daremo sempre per verificata) che si facciano le
-prove direttamente nella directory dei sorgenti (dove di norma vengono creati
-sia i programmi che la libreria), il comando da dare sarà \code{export
-  LD\_LIBRARY\_PATH=./}; a questo punto potremo lanciare il server, facendogli
-leggere una decina di frasi, con:
-\begin{verbatim}
+In generale questa variabile indica il \itindex{pathname} \textit{pathname}
+della directory contenente la libreria. Nell'ipotesi (che daremo sempre per
+verificata) che si facciano le prove direttamente nella directory dei sorgenti
+(dove di norma vengono creati sia i programmi che la libreria), il comando da
+dare sarà \code{export LD\_LIBRARY\_PATH=./}; a questo punto potremo lanciare
+il server, facendogli leggere una decina di frasi, con:
+\begin{Verbatim}
 [piccardi@gont sources]$ ./fortuned -n10
-\end{verbatim}
+\end{Verbatim}
+%$
 
 Avendo usato \func{daemon} per eseguire il server in background il comando
 ritornerà immediatamente, ma potremo verificare con \cmd{ps} che in effetti il
 programma resta un esecuzione in background, e senza avere associato un
-terminale di controllo (si ricordi quanto detto in \secref{sec:sess_daemon}):
-\begin{verbatim}
+terminale di controllo (si ricordi quanto detto in sez.~\ref{sec:sess_daemon}):
+\begin{Verbatim}
 [piccardi@gont sources]$ ps aux
 ...
 piccardi 27489  0.0  0.0  1204  356 ?        S    01:06   0:00 ./fortuned -n10
 piccardi 27492  3.0  0.1  2492  764 pts/2    R    01:08   0:00 ps aux
-\end{verbatim}%$
+\end{Verbatim}
+%$
 e si potrà verificare anche che in \file{/tmp} è stata creata la fifo di
 ascolto \file{fortune.fifo}. A questo punto potremo interrogare il server con
 il programma client; otterremo così:
-\begin{verbatim}
+\begin{Verbatim}
 [piccardi@gont sources]$ ./fortune
 Linux ext2fs has been stable for a long time, now it's time to break it
         -- Linuxkongreß '95 in Berlin
@@ -687,7 +693,8 @@ Let's call it an accidental feature.
 [piccardi@gont sources]$ ./fortune
 Linux ext2fs has been stable for a long time, now it's time to break it
         -- Linuxkongreß '95 in Berlin
-\end{verbatim}%$
+\end{Verbatim}
+%$
 e ripetendo varie volte il comando otterremo, in ordine casuale, le dieci
 frasi tenute in memoria dal server.
 
@@ -704,10 +711,9 @@ complessa e continua ad avere vari inconvenienti\footnote{lo stesso Stevens,
   fatto una richiesta, ma prima che la risposta sia inviata (cosa che nel
   nostro esempio non è stata fatta).}; in generale infatti l'interfaccia delle
 fifo non è adatta a risolvere questo tipo di problemi, che possono essere
-affrontati in maniera più semplice ed efficace o usando i
-\textit{socket}\index{socket} (che tratteremo in dettaglio a partire da
-\capref{cha:socket_intro}) o ricorrendo a meccanismi di comunicazione diversi,
-come quelli che esamineremo in seguito.
+affrontati in maniera più semplice ed efficace o usando i socket (che
+tratteremo in dettaglio a partire da cap.~\ref{cha:socket_intro}) o ricorrendo
+a meccanismi di comunicazione diversi, come quelli che esamineremo in seguito.
 
 
 
@@ -717,40 +723,39 @@ come quelli che esamineremo in seguito.
 Un meccanismo di comunicazione molto simile alle pipe, ma che non presenta il
 problema della unidirezionalità del flusso dei dati, è quello dei cosiddetti
 \textsl{socket locali} (o \textit{Unix domain socket}). Tratteremo l'argomento
-dei \textit{socket}\index{socket} in \capref{cha:socket_intro},\footnote{si
-  tratta comunque di oggetti di comunicazione che, come le pipe, sono
-  utilizzati attraverso dei file descriptor.} nell'ambito dell'interfaccia
-generale che essi forniscono per la programmazione di rete; e vedremo anche
-(in~\secref{sec:sock_sa_local}) come si possono definire dei file speciali (di
-tipo \textit{socket}, analoghi a quello associati alle fifo) cui si accede
-però attraverso quella medesima interfaccia; vale però la pena esaminare qui
-una modalità di uso dei socket locali\footnote{la funzione \func{socketpair} è
+dei socket in cap.~\ref{cha:socket_intro},\footnote{si tratta comunque di
+  oggetti di comunicazione che, come le pipe, sono utilizzati attraverso dei
+  file descriptor.} nell'ambito dell'interfaccia generale che essi forniscono
+per la programmazione di rete; e vedremo anche
+(in~sez.~\ref{sec:sock_sa_local}) come si possono definire dei file speciali
+(di tipo socket, analoghi a quello associati alle fifo) cui si accede però
+attraverso quella medesima interfaccia; vale però la pena esaminare qui una
+modalità di uso dei socket locali\footnote{la funzione \func{socketpair} è
   stata introdotta in BSD4.4, ma è supportata in genere da qualunque sistema
   che fornisca l'interfaccia dei socket.} che li rende sostanzialmente
 identici ad una pipe bidirezionale.
 
 La funzione \funcd{socketpair} infatti consente di creare una coppia di file
-descriptor connessi fra di loro (tramite un socket\index{socket}, appunto),
-senza dover ricorrere ad un file speciale sul filesystem, i descrittori sono
-del tutto analoghi a quelli che si avrebbero con una chiamata a \func{pipe},
-con la sola differenza è che in questo caso il flusso dei dati può essere
-effettuato in entrambe le direzioni. Il prototipo della funzione è:
+descriptor connessi fra di loro (tramite un socket, appunto), senza dover
+ricorrere ad un file speciale sul filesystem, i descrittori sono del tutto
+analoghi a quelli che si avrebbero con una chiamata a \func{pipe}, con la sola
+differenza è che in questo caso il flusso dei dati può essere effettuato in
+entrambe le direzioni. Il prototipo della funzione è:
 \begin{functions}
   \headdecl{sys/types.h} 
   \headdecl{sys/socket.h} 
   
   \funcdecl{int socketpair(int domain, int type, int protocol, int sv[2])}
   
-  Crea una coppia di socket\index{socket} connessi fra loro.
+  Crea una coppia di socket connessi fra loro.
   
   \bodydesc{La funzione restituisce 0 in caso di successo e -1 in caso di
     errore, nel qual caso \var{errno} assumerà uno dei valori:
   \begin{errlist}
-  \item[\errcode{EAFNOSUPPORT}] I socket\index{socket} locali non sono
-    supportati.
-  \item[\errcode{EPROTONOSUPPORT}] Il protocollo specificato non è supportato.
-  \item[\errcode{EOPNOTSUPP}] Il protocollo specificato non supporta la
-  creazione di coppie di socket\index{socket}.
+  \item[\errcode{EAFNOSUPPORT}] i socket locali non sono supportati.
+  \item[\errcode{EPROTONOSUPPORT}] il protocollo specificato non è supportato.
+  \item[\errcode{EOPNOTSUPP}] il protocollo specificato non supporta la
+  creazione di coppie di socket.
   \end{errlist}
   ed inoltre \errval{EMFILE},  \errval{EFAULT}.
 }
@@ -758,22 +763,23 @@ effettuato in entrambe le direzioni. Il prototipo della funzione 
 
 La funzione restituisce in \param{sv} la coppia di descrittori connessi fra di
 loro: quello che si scrive su uno di essi sarà ripresentato in input
-sull'altro e viceversa. I parametri \param{domain}, \param{type} e
-\param{protocol} derivano dall'interfaccia dei socket\index{socket} (che è
-quella che fornisce il substrato per connettere i due descrittori), ma in
-questo caso i soli valori validi che possono essere specificati sono
-rispettivamente \const{AF\_UNIX}, \const{SOCK\_STREAM} e \val{0}.
+sull'altro e viceversa. Gli argomenti \param{domain}, \param{type} e
+\param{protocol} derivano dall'interfaccia dei socket (vedi
+sez.~\ref{sec:sock_creation}) che è quella che fornisce il substrato per
+connettere i due descrittori, ma in questo caso i soli valori validi che
+possono essere specificati sono rispettivamente \const{AF\_UNIX},
+\const{SOCK\_STREAM} e \val{0}.
 
 L'utilità di chiamare questa funzione per evitare due chiamate a \func{pipe}
-può sembrare limitata; in realtà l'utilizzo di questa funzione (e dei
-socket\index{socket} locali in generale) permette di trasmettere attraverso le
-linea non solo dei dati, ma anche dei file descriptor: si può cioè passare da
-un processo ad un altro un file descriptor, con una sorta di duplicazione
-dello stesso non all'interno di uno stesso processo, ma fra processi distinti
-(torneremo su questa funzionalità in \secref{sec:xxx_fd_passing}).
+può sembrare limitata; in realtà l'utilizzo di questa funzione (e dei socket
+locali in generale) permette di trasmettere attraverso le linea non solo dei
+dati, ma anche dei file descriptor: si può cioè passare da un processo ad un
+altro un file descriptor, con una sorta di duplicazione dello stesso non
+all'interno di uno stesso processo, ma fra processi distinti (torneremo su
+questa funzionalità in sez.~\ref{sec:sock_fd_passing}).
 
 
-\section{La comunicazione fra processi di System V}
+\section{Il sistema di comunicazione fra processi di System V}
 \label{sec:ipc_sysv}
 
 Benché le pipe e le fifo siano ancora ampiamente usate, esse scontano il
@@ -785,7 +791,7 @@ Per questo nello sviluppo di System V vennero introdotti una serie di nuovi
 oggetti per la comunicazione fra processi ed una nuova interfaccia di
 programmazione, che fossero in grado di garantire una maggiore flessibilità.
 In questa sezione esamineremo come Linux supporta quello che viene chiamato il
-\textsl{Sistema di comunicazione inter-processo} di System V, cui da qui in
+\textsl{Sistema di comunicazione fra processi} di System V, cui da qui in
 avanti faremo riferimento come \textit{SysV IPC} (dove IPC è la sigla di
 \textit{Inter-Process Comunication}).
 
@@ -813,7 +819,7 @@ Un'ulteriore caratteristica negativa 
 specificando il relativo \textsl{identificatore}. Questo è un numero
 progressivo (un po' come il \acr{pid} dei processi) che il kernel assegna a
 ciascuno di essi quanto vengono creati (sul procedimento di assegnazione
-torneremo in \secref{sec:ipc_sysv_id_use}). L'identificatore viene restituito
+torneremo in sez.~\ref{sec:ipc_sysv_id_use}). L'identificatore viene restituito
 dalle funzioni che creano l'oggetto, ed è quindi locale al processo che le ha
 eseguite. Dato che l'identificatore viene assegnato dinamicamente dal kernel
 non è possibile prevedere quale sarà, né utilizzare un qualche valore statico,
@@ -828,7 +834,7 @@ tramite la quale 
   si sposta il problema dell'accesso dalla classificazione in base
   all'identificatore alla classificazione in base alla chiave, una delle tante
   complicazioni inutili presenti nel \textit{SysV IPC}.} Oltre la chiave, la
-struttura, la cui definizione è riportata in \figref{fig:ipc_ipc_perm},
+struttura, la cui definizione è riportata in fig.~\ref{fig:ipc_ipc_perm},
 mantiene varie proprietà ed informazioni associate all'oggetto.
 
 \begin{figure}[!htb]
@@ -845,14 +851,14 @@ mantiene varie propriet
 Usando la stessa chiave due processi diversi possono ricavare l'identificatore
 associato ad un oggetto ed accedervi. Il problema che sorge a questo punto è
 come devono fare per accordarsi sull'uso di una stessa chiave. Se i processi
-sono \textsl{parenti} la soluzione è relativamente semplice, in tal caso
+sono \textsl{imparentati} la soluzione è relativamente semplice, in tal caso
 infatti si può usare il valore speciale \texttt{IPC\_PRIVATE} per creare un
 nuovo oggetto nel processo padre, l'identificatore così ottenuto sarà
-disponibile in tutti i figli, e potrà essere passato come parametro attraverso
+disponibile in tutti i figli, e potrà essere passato come argomento attraverso
 una \func{exec}.
 
-Però quando i processi non sono \textsl{parenti} (come capita tutte le volte
-che si ha a che fare con un sistema client-server) tutto questo non è
+Però quando i processi non sono \textsl{imparentati} (come capita tutte le
+volte che si ha a che fare con un sistema client-server) tutto questo non è
 possibile; si potrebbe comunque salvare l'identificatore su un file noto, ma
 questo ovviamente comporta lo svantaggio di doverselo andare a rileggere.  Una
 alternativa più efficace è quella che i programmi usino un valore comune per
@@ -876,22 +882,23 @@ nome di un file ed un numero di versione; il suo prototipo 
 \end{functions}
 
 La funzione determina un valore della chiave sulla base di \param{pathname},
-che deve specificare il pathname di un file effettivamente esistente e di un
-numero di progetto \param{proj\_id)}, che di norma viene specificato come
-carattere, dato che ne vengono utilizzati solo gli 8 bit meno
-significativi.\footnote{nelle libc4 e libc5, come avviene in SunOS,
-  l'argomento \param{proj\_id} è dichiarato tipo \ctyp{char}, le \acr{glibc}
-  usano il prototipo specificato da XPG4, ma vengono lo stesso utilizzati gli
-  8 bit meno significativi.}
+che deve specificare il \itindex{pathname} \textit{pathname} di un file
+effettivamente esistente e di un numero di progetto \param{proj\_id)}, che di
+norma viene specificato come carattere, dato che ne vengono utilizzati solo
+gli 8 bit meno significativi.\footnote{nelle libc4 e libc5, come avviene in
+  SunOS, l'argomento \param{proj\_id} è dichiarato tipo \ctyp{char}, le
+  \acr{glibc} usano il prototipo specificato da XPG4, ma vengono lo stesso
+  utilizzati gli 8 bit meno significativi.}
 
 Il problema è che anche così non c'è la sicurezza che il valore della chiave
 sia univoco, infatti esso è costruito combinando il byte di \param{proj\_id)}
-con i 16 bit meno significativi dell'inode\index{inode} del file
+con i 16 bit meno significativi \index{inode} dell'inode del file
 \param{pathname} (che vengono ottenuti attraverso \func{stat}, da cui derivano
 i possibili errori), e gli 8 bit meno significativi del numero del dispositivo
 su cui è il file.  Diventa perciò relativamente facile ottenere delle
-collisioni, specie se i file sono su dispositivi con lo stesso \textit{minor
-  number}, come \file{/dev/hda1} e \file{/dev/sda1}.
+collisioni, specie se i file sono su dispositivi con lo stesso
+\itindex{minor~number} \textit{minor number}, come \file{/dev/hda1} e
+\file{/dev/sda1}.
 
 In genere quello che si fa è utilizzare un file comune usato dai programmi che
 devono comunicare (ad esempio un header comune, o uno dei programmi che devono
@@ -910,7 +917,7 @@ problema del \textit{SysV IPC}. Non esiste infatti una modalit
 identificare un oggetto, come sarebbe stato se lo si fosse associato ad in
 file, e tutta l'interfaccia è inutilmente complessa.  Per questo ne è stata
 effettuata una revisione completa nello standard POSIX.1b, che tratteremo in
-\secref{sec:ipc_posix}.
+sez.~\ref{sec:ipc_posix}.
 
 
 \subsection{Il controllo di accesso}
@@ -921,7 +928,7 @@ Oltre alle chiavi, abbiamo visto che ad ogni oggetto sono associate in
 (nei campi \var{cuid} e \var{cgid}) e del proprietario (nei campi \var{uid} e
 \var{gid}) dello stesso, e un insieme di permessi (nel campo \var{mode}). In
 questo modo è possibile definire un controllo di accesso sugli oggetti di IPC,
-simile a quello che si ha per i file (vedi \secref{sec:file_perm_overview}).
+simile a quello che si ha per i file (vedi sez.~\ref{sec:file_perm_overview}).
 
 Benché questo controllo di accesso sia molto simile a quello dei file, restano
 delle importanti differenze. La prima è che il permesso di esecuzione non
@@ -929,7 +936,7 @@ esiste (e se specificato viene ignorato), per cui si pu
 permessi di lettura e scrittura (nel caso dei semafori poi quest'ultimo è più
 propriamente un permesso di modifica). I valori di \var{mode} sono gli stessi
 ed hanno lo stesso significato di quelli riportati in
-\secref{tab:file_mode_flags}\footnote{se però si vogliono usare le costanti
+tab.~\ref{tab:file_mode_flags}\footnote{se però si vogliono usare le costanti
   simboliche ivi definite occorrerà includere il file \file{sys/stat.h},
   alcuni sistemi definiscono le costanti \const{MSG\_R} (\texttt{0400}) e
   \const{MSG\_W} (\texttt{0200}) per indicare i permessi base di lettura e
@@ -939,9 +946,9 @@ ed hanno lo stesso significato di quelli riportati in
 il proprietario, il suo gruppo e tutti gli altri.
 
 Quando l'oggetto viene creato i campi \var{cuid} e \var{uid} di
-\struct{ipc\_perm} ed i campi \var{cgid} e \var{gid} vengono settati
-rispettivamente al valore dell'user-ID e del group-ID effettivo del processo che
-ha chiamato la funzione, ma, mentre i campi \var{uid} e \var{gid} possono
+\struct{ipc\_perm} ed i campi \var{cgid} e \var{gid} vengono impostati
+rispettivamente al valore dell'user-ID e del group-ID effettivo del processo
+che ha chiamato la funzione, ma, mentre i campi \var{uid} e \var{gid} possono
 essere cambiati, i campi \var{cuid} e \var{cgid} restano sempre gli stessi.
 
 Il controllo di accesso è effettuato a due livelli. Il primo livello è nelle
@@ -957,32 +964,32 @@ nullo, nel qual caso l'identificatore sar
 Il secondo livello di controllo è quello delle varie funzioni che accedono
 direttamente (in lettura o scrittura) all'oggetto. In tal caso lo schema dei
 controlli è simile a quello dei file, ed avviene secondo questa sequenza:
-\begin{itemize}
+\begin{itemize*}
 \item se il processo ha i privilegi di amministratore l'accesso è sempre
   consentito. 
 \item se l'user-ID effettivo del processo corrisponde o al valore del campo
   \var{cuid} o a quello del campo \var{uid} ed il permesso per il proprietario
   in \var{mode} è appropriato\footnote{per appropriato si intende che è
-    settato il permesso di scrittura per le operazioni di scrittura e quello
+    impostato il permesso di scrittura per le operazioni di scrittura e quello
     di lettura per le operazioni di lettura.} l'accesso è consentito.
 \item se il group-ID effettivo del processo corrisponde o al
   valore del campo \var{cgid} o a quello del campo \var{gid} ed il permesso
   per il gruppo in \var{mode} è appropriato l'accesso è consentito.
 \item se il permesso per gli altri è appropriato l'accesso è consentito.
-\end{itemize}
+\end{itemize*}
 solo se tutti i controlli elencati falliscono l'accesso è negato. Si noti che
 a differenza di quanto avviene per i permessi dei file, fallire in uno dei
 passi elencati non comporta il fallimento dell'accesso. Un'ulteriore
 differenza rispetto a quanto avviene per i file è che per gli oggetti di IPC
-il valore di \var{umask} (si ricordi quanto esposto in
-\secref{sec:file_umask}) non ha alcun significato.
+il valore di \itindex{umask} \textit{umask} (si ricordi quanto esposto in
+sez.~\ref{sec:file_perm_management}) non ha alcun significato.
 
 
 \subsection{Gli identificatori ed il loro utilizzo}
 \label{sec:ipc_sysv_id_use}
 
 L'unico campo di \struct{ipc\_perm} del quale non abbiamo ancora parlato è
-\var{seq}, che in \figref{fig:ipc_ipc_perm} è qualificato con un criptico
+\var{seq}, che in fig.~\ref{fig:ipc_ipc_perm} è qualificato con un criptico
 ``\textsl{numero di sequenza}'', ne parliamo adesso dato che esso è
 strettamente attinente alle modalità con cui il kernel assegna gli
 identificatori degli oggetti del sistema di IPC.
@@ -1014,8 +1021,9 @@ Il sistema dispone sempre di un numero fisso di oggetti di IPC,\footnote{fino
   altri limiti relativi al \textit{SysV IPC}) solo con una ricompilazione del
   kernel, andando a modificarne la definizione nei relativi header file.  A
   partire dal kernel 2.4.x è possibile cambiare questi valori a sistema attivo
-  scrivendo sui file \file{shmmni}, \file{msgmni} e \file{sem} di
-  \file{/proc/sys/kernel} o con l'uso di \func{sysctl}.} e per ciascuno di
+  scrivendo sui file \procrelfile{/proc/sys/kernel}{shmmni},
+  \procrelfile{/proc/sys/kernel}{msgmni} e \procrelfile{/proc/sys/kernel}{sem}
+  di \file{/proc/sys/kernel} o con l'uso di \func{sysctl}.} e per ciascuno di
 essi viene mantenuto in \var{seq} un numero di sequenza progressivo che viene
 incrementato di uno ogni volta che l'oggetto viene cancellato. Quando
 l'oggetto viene creato usando uno spazio che era già stato utilizzato in
   \label{fig:ipc_sysv_idtest}
 \end{figure}
 
-In \figref{fig:ipc_sysv_idtest} è riportato il codice di un semplice programma
-di test che si limita a creare un oggetto (specificato a riga di comando),
-stamparne il numero di identificatore e cancellarlo per un numero specificato
-di volte. Al solito non si è riportato il codice della gestione delle opzioni
-a riga di comando, che permette di specificare quante volte effettuare il
-ciclo \var{n}, e su quale tipo di oggetto eseguirlo.
+In fig.~\ref{fig:ipc_sysv_idtest} è riportato il codice di un semplice
+programma di test che si limita a creare un oggetto (specificato a riga di
+comando), stamparne il numero di identificatore e cancellarlo per un numero
+specificato di volte. Al solito non si è riportato il codice della gestione
+delle opzioni a riga di comando, che permette di specificare quante volte
+effettuare il ciclo \var{n}, e su quale tipo di oggetto eseguirlo.
 
 La figura non riporta il codice di selezione delle opzioni, che permette di
 inizializzare i valori delle variabili \var{type} al tipo di oggetto voluto, e
@@ -1052,25 +1060,27 @@ inizializzare i valori delle variabili \var{type} al tipo di oggetto voluto, e
 stampa, cancellazione. I valori di default sono per l'uso delle code di
 messaggi e un ciclo di 5 volte. Se si lancia il comando si otterrà qualcosa
 del tipo:
-\begin{verbatim}
+\begin{Verbatim}
 piccardi@gont sources]$ ./ipctestid
 Identifier Value 0 
 Identifier Value 32768 
 Identifier Value 65536 
 Identifier Value 98304 
 Identifier Value 131072 
-\end{verbatim}%$
+\end{Verbatim}
+%$
 il che ci mostra che abbiamo un kernel della serie 2.4.x nel quale non avevamo
 ancora usato nessuna coda di messaggi. Se ripetiamo il comando otterremo
 ancora:
-\begin{verbatim}
+\begin{Verbatim}
 [piccardi@gont sources]$ ./ipctestid
 Identifier Value 163840 
 Identifier Value 196608 
 Identifier Value 229376 
 Identifier Value 262144 
 Identifier Value 294912 
-\end{verbatim}%$
+\end{Verbatim}
+%$
 che ci mostra come il valore di \var{seq} sia in effetti una quantità
 mantenuta staticamente all'interno del sistema.
 
@@ -1098,15 +1108,15 @@ di messaggi esistente (o di crearne una se questa non esiste) 
   \bodydesc{La funzione restituisce l'identificatore (un intero positivo) o -1
     in caso di errore, nel qual caso \var{errno} assumerà uno dei valori:
   \begin{errlist}
-  \item[\errcode{EACCES}] Il processo chiamante non ha i privilegi per accedere
+  \item[\errcode{EACCES}] il processo chiamante non ha i privilegi per accedere
   alla coda richiesta.  
-  \item[\errcode{EEXIST}] Si è richiesta la creazione di una coda che già
+  \item[\errcode{EEXIST}] si è richiesta la creazione di una coda che già
   esiste, ma erano specificati sia \const{IPC\_CREAT} che \const{IPC\_EXCL}. 
-  \item[\errcode{EIDRM}] La coda richiesta è marcata per essere cancellata.
-  \item[\errcode{ENOENT}] Si è cercato di ottenere l'identificatore di una coda
+  \item[\errcode{EIDRM}] la coda richiesta è marcata per essere cancellata.
+  \item[\errcode{ENOENT}] si è cercato di ottenere l'identificatore di una coda
     di messaggi specificando una chiave che non esiste e \const{IPC\_CREAT}
     non era specificato.
-  \item[\errcode{ENOSPC}] Si è cercato di creare una coda di messaggi quando è
+  \item[\errcode{ENOSPC}] si è cercato di creare una coda di messaggi quando è
     stato superato il limite massimo di code (\const{MSGMNI}).
   \end{errlist}
   ed inoltre \errval{ENOMEM}.
@@ -1133,7 +1143,7 @@ Se invece si vuole creare una nuova coda di messaggi \param{flag} non pu
 essere nullo e deve essere fornito come maschera binaria, impostando il bit
 corrispondente al valore \const{IPC\_CREAT}. In questo caso i nove bit meno
 significativi di \param{flag} saranno usati come permessi per il nuovo
-oggetto, secondo quanto illustrato in \secref{sec:ipc_sysv_access_control}.
+oggetto, secondo quanto illustrato in sez.~\ref{sec:ipc_sysv_access_control}.
 Se si imposta anche il bit corrispondente a \const{IPC\_EXCL} la funzione avrà
 successo solo se l'oggetto non esiste già, fallendo con un errore di
 \errcode{EEXIST} altrimenti.
@@ -1157,7 +1167,7 @@ coda.
     \hline
     \hline
     \const{MSGMNI}&   16& \file{msgmni} & Numero massimo di code di
-                                          messaggi. \\
+                                          messaggi.\\
     \const{MSGMAX}& 8192& \file{msgmax} & Dimensione massima di un singolo
                                           messaggio.\\
     \const{MSGMNB}&16384& \file{msgmnb} & Dimensione massima del contenuto di 
@@ -1170,34 +1180,36 @@ coda.
 
 Le code di messaggi sono caratterizzate da tre limiti fondamentali, definiti
 negli header e corrispondenti alle prime tre costanti riportate in
-\tabref{tab:ipc_msg_limits}, come accennato però in Linux è possibile
+tab.~\ref{tab:ipc_msg_limits}, come accennato però in Linux è possibile
 modificare questi limiti attraverso l'uso di \func{sysctl} o scrivendo nei
-file \file{msgmax}, \file{msgmnb} e \file{msgmni} di \file{/proc/sys/kernel/}.
-
+file \procrelfile{/proc/sys/kernel}{msgmax},
+\procrelfile{/proc/sys/kernel}{msgmnb} e
+\procrelfile{/proc/sys/kernel}{msgmni} di \file{/proc/sys/kernel/}.
 
 \begin{figure}[htb]
-  \centering \includegraphics[width=15cm]{img/mqstruct}
+  \centering \includegraphics[width=13cm]{img/mqstruct}
   \caption{Schema della struttura di una coda messaggi.}
   \label{fig:ipc_mq_schema}
 \end{figure}
 
 
-Una coda di messaggi è costituita da una \textit{linked list};\footnote{una
-  \textit{linked list} è una tipica struttura di dati, organizzati in una
-  lista in cui ciascun elemento contiene un puntatore al successivo. In questo
-  modo la struttura è veloce nell'estrazione ed immissione dei dati dalle
-  estremità dalla lista (basta aggiungere un elemento in testa o in coda ed
-  aggiornare un puntatore), e relativamente veloce da attraversare in ordine
-  sequenziale (seguendo i puntatori), è invece relativamente lenta
-  nell'accesso casuale e nella ricerca.}  i nuovi messaggi vengono inseriti in
-coda alla lista e vengono letti dalla cima, in \figref{fig:ipc_mq_schema} si è
-riportato lo schema con cui queste strutture vengono mantenute dal
-kernel.\footnote{lo schema illustrato in \figref{fig:ipc_mq_schema} è in
-  realtà una semplificazione di quello usato effettivamente fino ai kernel
-  della serie 2.2.x, nei kernel della serie 2.4.x la gestione delle code di
-  messaggi è stata modificata ed è effettuata in maniera diversa; abbiamo
-  mantenuto lo schema precedente in quanto illustra comunque in maniera più
-  che adeguata i principi di funzionamento delle code di messaggi.}
+Una coda di messaggi è costituita da una \itindex{linked~list} \textit{linked
+  list};\footnote{una \itindex{linked~list} \textit{linked list} è una tipica
+  struttura di dati, organizzati in una lista in cui ciascun elemento contiene
+  un puntatore al successivo. In questo modo la struttura è veloce
+  nell'estrazione ed immissione dei dati dalle estremità dalla lista (basta
+  aggiungere un elemento in testa o in coda ed aggiornare un puntatore), e
+  relativamente veloce da attraversare in ordine sequenziale (seguendo i
+  puntatori), è invece relativamente lenta nell'accesso casuale e nella
+  ricerca.}  i nuovi messaggi vengono inseriti in coda alla lista e vengono
+letti dalla cima, in fig.~\ref{fig:ipc_mq_schema} si è riportato lo schema con
+cui queste strutture vengono mantenute dal kernel.\footnote{lo schema
+  illustrato in fig.~\ref{fig:ipc_mq_schema} è in realtà una semplificazione
+  di quello usato effettivamente fino ai kernel della serie 2.2.x, nei kernel
+  della serie 2.4.x la gestione delle code di messaggi è stata modificata ed è
+  effettuata in maniera diversa; abbiamo mantenuto lo schema precedente in
+  quanto illustra comunque in maniera più che adeguata i principi di
+  funzionamento delle code di messaggi.}
 
 \begin{figure}[!htb]
   \footnotesize \centering
@@ -1211,22 +1223,22 @@ kernel.\footnote{lo schema illustrato in \figref{fig:ipc_mq_schema} 
 \end{figure}
 
 A ciascuna coda è associata una struttura \struct{msgid\_ds}, la cui
-definizione, è riportata in \secref{fig:ipc_msqid_ds}. In questa struttura il
+definizione, è riportata in fig.~\ref{fig:ipc_msqid_ds}. In questa struttura il
 kernel mantiene le principali informazioni riguardo lo stato corrente della
 coda.\footnote{come accennato questo vale fino ai kernel della serie 2.2.x,
   essa viene usata nei kernel della serie 2.4.x solo per compatibilità in
   quanto è quella restituita dalle funzioni dell'interfaccia.  Si noti come ci
   sia una differenza con i campi mostrati nello schema di
-  \figref{fig:ipc_mq_schema} che sono presi dalla definizione di
+  fig.~\ref{fig:ipc_mq_schema} che sono presi dalla definizione di
   \file{linux/msg.h}, e fanno riferimento alla definizione della omonima
-  struttura usata nel kernel.} In \figref{fig:ipc_msqid_ds} sono elencati i
+  struttura usata nel kernel.} In fig.~\ref{fig:ipc_msqid_ds} sono elencati i
 campi significativi definiti in \file{sys/msg.h}, a cui si sono aggiunti gli
 ultimi tre campi che sono previsti dalla implementazione originale di System
 V, ma non dallo standard Unix98.
 
 Quando si crea una nuova coda con \func{msgget} questa struttura viene
 inizializzata, in particolare il campo \var{msg\_perm} viene inizializzato
-come illustrato in \secref{sec:ipc_sysv_access_control}, per quanto riguarda
+come illustrato in sez.~\ref{sec:ipc_sysv_access_control}, per quanto riguarda
 gli altri campi invece:
 \begin{itemize*}
 \item il campo \var{msg\_qnum}, che esprime il numero di messaggi presenti
@@ -1262,13 +1274,13 @@ prototipo 
   
   Esegue l'operazione specificata da \param{cmd} sulla coda \param{msqid}.
   
-  \bodydesc{La funzione restituisce 0 in caso di successo o -1 in caso di
+  \bodydesc{La funzione restituisce 0 in caso di successo o $-1$ in caso di
     errore, nel qual caso \var{errno} assumerà uno dei valori:
   \begin{errlist}
-  \item[\errcode{EACCES}] Si è richiesto \const{IPC\_STAT} ma processo
+  \item[\errcode{EACCES}] si è richiesto \const{IPC\_STAT} ma processo
     chiamante non ha i privilegi di lettura sulla coda.
-  \item[\errcode{EIDRM}] La coda richiesta è stata cancellata.
-  \item[\errcode{EPERM}] Si è richiesto \const{IPC\_SET} o \const{IPC\_RMID} ma
+  \item[\errcode{EIDRM}] la coda richiesta è stata cancellata.
+  \item[\errcode{EPERM}] si è richiesto \const{IPC\_SET} o \const{IPC\_RMID} ma
     il processo non ha i privilegi, o si è richiesto di aumentare il valore di
     \var{msg\_qbytes} oltre il limite \const{MSGMNB} senza essere
     amministratore.
@@ -1289,7 +1301,7 @@ eseguire; i valori possibili sono:
 \item[\const{IPC\_RMID}] Rimuove la coda, cancellando tutti i dati, con
   effetto immediato. Tutti i processi che cercheranno di accedere alla coda
   riceveranno un errore di \errcode{EIDRM}, e tutti processi in attesa su
-  funzioni di di lettura o di scrittura sulla coda saranno svegliati ricevendo
+  funzioni di lettura o di scrittura sulla coda saranno svegliati ricevendo
   il medesimo errore. Questo comando può essere eseguito solo da un processo
   con user-ID effettivo corrispondente al creatore o al proprietario della
   coda, o all'amministratore.
@@ -1317,32 +1329,30 @@ messaggio su una coda si utilizza la funzione \funcd{msgsnd}; il suo prototipo
 
   Invia un messaggio sulla coda \param{msqid}.
   
-  \bodydesc{La funzione restituisce 0, e -1 in caso di errore, nel qual caso
+  \bodydesc{La funzione restituisce 0, e $-1$ in caso di errore, nel qual caso
     \var{errno} assumerà uno dei valori:
   \begin{errlist}
-  \item[\errcode{EACCES}] Non si hanno i privilegi di accesso sulla coda.
-  \item[\errcode{EIDRM}] La coda è stata cancellata.
-  \item[\errcode{EAGAIN}] Il messaggio non può essere inviato perché si è
+  \item[\errcode{EACCES}] non si hanno i privilegi di accesso sulla coda.
+  \item[\errcode{EIDRM}] la coda è stata cancellata.
+  \item[\errcode{EAGAIN}] il messaggio non può essere inviato perché si è
   superato il limite \var{msg\_qbytes} sul numero massimo di byte presenti
   sulla coda, e si è richiesto \const{IPC\_NOWAIT} in \param{flag}.
-  \item[\errcode{EINTR}] La funzione è stata interrotta da un segnale.
-  \item[\errcode{EINVAL}] Si è specificato un \param{msgid} invalido, o un
+  \item[\errcode{EINVAL}] si è specificato un \param{msgid} invalido, o un
     valore non positivo per \param{mtype}, o un valore di \param{msgsz}
     maggiore di \const{MSGMAX}.
   \end{errlist}
-  ed inoltre \errval{EFAULT} ed \errval{ENOMEM}.
-}
+  ed inoltre \errval{EFAULT}, \errval{EINTR} ed \errval{ENOMEM}.  }
 \end{functions}
 
 La funzione inserisce il messaggio sulla coda specificata da \param{msqid}; il
 messaggio ha lunghezza specificata da \param{msgsz} ed è passato attraverso il
 l'argomento \param{msgp}.  Quest'ultimo deve venire passato sempre come
 puntatore ad una struttura \struct{msgbuf} analoga a quella riportata in
-\figref{fig:ipc_msbuf} che è quella che deve contenere effettivamente il
+fig.~\ref{fig:ipc_msbuf} che è quella che deve contenere effettivamente il
 messaggio.  La dimensione massima per il testo di un messaggio non può
 comunque superare il limite \const{MSGMAX}.
 
-La struttura di \figref{fig:ipc_msbuf} è comunque solo un modello, tanto che
+La struttura di fig.~\ref{fig:ipc_msbuf} è comunque solo un modello, tanto che
 la definizione contenuta in \file{sys/msg.h} usa esplicitamente per il secondo
 campo il valore \code{mtext[1]}, che non è di nessuna utilità ai fini pratici.
 La sola cosa che conta è che la struttura abbia come primo membro un campo
@@ -1352,7 +1362,7 @@ messaggio e deve essere sempre specificato come intero positivo di tipo
 dimensione, e serve a contenere il testo del messaggio.
 
 In generale pertanto per inviare un messaggio con \func{msgsnd} si usa
-ridefinire una struttura simile a quella di \figref{fig:ipc_msbuf}, adattando
+ridefinire una struttura simile a quella di fig.~\ref{fig:ipc_msbuf}, adattando
 alle proprie esigenze il campo \var{mtype}, (o ridefinendo come si vuole il
 corpo del messaggio, anche con più campi o con strutture più complesse) avendo
 però la cura di mantenere nel primo campo un valore di tipo \ctyp{long} che ne
@@ -1362,7 +1372,7 @@ Si tenga presente che la lunghezza che deve essere indicata in questo
 argomento è solo quella del messaggio, non quella di tutta la struttura, se
 cioè \var{message} è una propria struttura che si passa alla funzione,
 \param{msgsz} dovrà essere uguale a \code{sizeof(message)-sizeof(long)}, (se
-consideriamo il caso dell'esempio in \figref{fig:ipc_msbuf}, \param{msgsz}
+consideriamo il caso dell'esempio in fig.~\ref{fig:ipc_msbuf}, \param{msgsz}
 dovrà essere pari a \const{LENGTH}).
 
 \begin{figure}[!htb]
@@ -1378,7 +1388,7 @@ dovr
 
 Per capire meglio il funzionamento della funzione riprendiamo in
 considerazione la struttura della coda illustrata in
-\figref{fig:ipc_mq_schema}. Alla chiamata di \func{msgsnd} il nuovo messaggio
+fig.~\ref{fig:ipc_mq_schema}. Alla chiamata di \func{msgsnd} il nuovo messaggio
 sarà aggiunto in fondo alla lista inserendo una nuova struttura \struct{msg},
 il puntatore \var{msg\_last} di \struct{msqid\_ds} verrà aggiornato, come pure
 il puntatore al messaggio successivo per quello che era il precedente ultimo
@@ -1428,13 +1438,13 @@ La funzione che viene utilizzata per estrarre un messaggio da una coda 
     successo, e -1 in caso di errore, nel qual caso \var{errno} assumerà uno
     dei valori:
   \begin{errlist}
-  \item[\errcode{EACCES}] Non si hanno i privilegi di accesso sulla coda.
-  \item[\errcode{EIDRM}] La coda è stata cancellata.
-  \item[\errcode{E2BIG}] Il testo del messaggio è più lungo di \param{msgsz} e
+  \item[\errcode{EACCES}] non si hanno i privilegi di accesso sulla coda.
+  \item[\errcode{EIDRM}] la coda è stata cancellata.
+  \item[\errcode{E2BIG}] il testo del messaggio è più lungo di \param{msgsz} e
     non si è specificato \const{MSG\_NOERROR} in \param{msgflg}.
-  \item[\errcode{EINTR}] La funzione è stata interrotta da un segnale mentre
+  \item[\errcode{EINTR}] la funzione è stata interrotta da un segnale mentre
     era in attesa di ricevere un messaggio.
-  \item[\errcode{EINVAL}] Si è specificato un \param{msgid} invalido o un
+  \item[\errcode{EINVAL}] si è specificato un \param{msgid} invalido o un
     valore di \param{msgsz} negativo.
   \end{errlist}
   ed inoltre \errval{EFAULT}.
@@ -1443,10 +1453,10 @@ La funzione che viene utilizzata per estrarre un messaggio da una coda 
 
 La funzione legge un messaggio dalla coda specificata, scrivendolo sulla
 struttura puntata da \param{msgp}, che dovrà avere un formato analogo a quello
-di \figref{fig:ipc_msbuf}.  Una volta estratto, il messaggio sarà rimosso dalla
-coda.  L'argomento \param{msgsz} indica la lunghezza massima del testo del
-messaggio (equivalente al valore del parametro \const{LENGTH} nell'esempio di
-\figref{fig:ipc_msbuf}).
+di fig.~\ref{fig:ipc_msbuf}.  Una volta estratto, il messaggio sarà rimosso
+dalla coda.  L'argomento \param{msgsz} indica la lunghezza massima del testo
+del messaggio (equivalente al valore del parametro \const{LENGTH} nell'esempio
+di fig.~\ref{fig:ipc_msbuf}).
 
 Se il testo del messaggio ha lunghezza inferiore a \param{msgsz} esso viene
 rimosso dalla coda; in caso contrario, se \param{msgflg} è impostato a
@@ -1456,13 +1466,13 @@ un errore di \errcode{E2BIG}.
 
 L'argomento \param{msgtyp} permette di restringere la ricerca ad un
 sottoinsieme dei messaggi presenti sulla coda; la ricerca infatti è fatta con
-una scansione della struttura mostrata in \figref{fig:ipc_mq_schema},
+una scansione della struttura mostrata in fig.~\ref{fig:ipc_mq_schema},
 restituendo il primo messaggio incontrato che corrisponde ai criteri
 specificati (che quindi, visto come i messaggi vengono sempre inseriti dalla
 coda, è quello meno recente); in particolare:
 \begin{itemize}
 \item se \param{msgtyp} è 0 viene estratto il messaggio in cima alla coda, cioè
-  quello fra i presenti che è stato inserito inserito per primo. 
+  quello fra i presenti che è stato inserito per primo. 
 \item se \param{msgtyp} è positivo viene estratto il primo messaggio il cui
   tipo (il valore del campo \var{mtype}) corrisponde al valore di
   \param{msgtyp}.
@@ -1505,16 +1515,16 @@ tutte le risorse occupate vengono rilasciate quanto l'ultimo processo che le
 utilizzava termina. Questo comporta che in caso di errori si può saturare il
 sistema, e che devono comunque essere esplicitamente previste delle funzioni
 di rimozione in caso di interruzioni o uscite dal programma (come vedremo in
-\figref{fig:ipc_mq_fortune_server}).
+fig.~\ref{fig:ipc_mq_fortune_server}).
 
 L'altro problema è non facendo uso di file descriptor le tecniche di
-\textit{I/O multiplexing} descritte in \secref{sec:file_multiplexing} non
+\textit{I/O multiplexing} descritte in sez.~\ref{sec:file_multiplexing} non
 possono essere utilizzate, e non si ha a disposizione niente di analogo alle
 funzioni \func{select} e \func{poll}. Questo rende molto scomodo usare più di
 una di queste strutture alla volta; ad esempio non si può scrivere un server
 che aspetti un messaggio su più di una coda senza fare ricorso ad una tecnica
-di \textit{polling}\index{polling} che esegua un ciclo di attesa su ciascuna
-di esse.
+di \itindex{polling} \textit{polling} che esegua un ciclo di attesa su
+ciascuna di esse.
 
 Come esempio dell'uso delle code di messaggi possiamo riscrivere il nostro
 server di \textit{fortunes} usando queste al posto delle fifo. In questo caso
@@ -1532,7 +1542,7 @@ in maniera indipendente con client diversi.
   \label{fig:ipc_mq_fortune_server}
 \end{figure}
 
-In \figref{fig:ipc_mq_fortune_server} si è riportato un estratto delle parti
+In fig.~\ref{fig:ipc_mq_fortune_server} si è riportato un estratto delle parti
 principali del codice del nuovo server (il codice completo è nel file
 \file{MQFortuneServer.c} nei sorgenti allegati). Il programma è basato su un
 uso accorto della caratteristica di poter associate un ``tipo'' ai messaggi
@@ -1606,13 +1616,13 @@ gestore \code{HandSIGTERM}, che semplicemente si limita a cancellare la coda
   \label{fig:ipc_mq_fortune_client}
 \end{figure}
 
-In \figref{fig:ipc_mq_fortune_client} si è riportato un estratto il codice del
-programma client.  Al solito il codice completo è con i sorgenti allegati, nel
-file \file{MQFortuneClient.c}.  Come sempre si sono rimosse le parti relative
-alla gestione delle opzioni, ed in questo caso, anche la dichiarazione delle
-variabili, che, per la parte relative alle strutture usate per la
-comunicazione tramite le code, sono le stesse viste in
-\figref{fig:ipc_mq_fortune_server}.
+In fig.~\ref{fig:ipc_mq_fortune_client} si è riportato un estratto il codice
+del programma client.  Al solito il codice completo è con i sorgenti allegati,
+nel file \file{MQFortuneClient.c}.  Come sempre si sono rimosse le parti
+relative alla gestione delle opzioni, ed in questo caso, anche la
+dichiarazione delle variabili, che, per la parte relative alle strutture usate
+per la comunicazione tramite le code, sono le stesse viste in
+fig.~\ref{fig:ipc_mq_fortune_server}.
 
 Il client in questo caso è molto semplice; la prima parte del programma
 (\texttt{\small 4--9}) si occupa di accedere alla coda di messaggi, ed è
@@ -1634,7 +1644,7 @@ passo (\texttt{\small 17}) prima di uscire 
 messaggio ricevuto.
  
 Proviamo allora il nostro nuovo sistema, al solito occorre definire
-\code{LD\_LIBRAY\_PATH} per accedere alla libreria \file{libgapil.so}, dopo di
+\code{LD\_LIBRARY\_PATH} per accedere alla libreria \file{libgapil.so}, dopo di
 che, in maniera del tutto analoga a quanto fatto con il programma che usa le
 fifo, potremo far partire il server con:
 \begin{verbatim}
@@ -1676,7 +1686,7 @@ viene interrotto dopo l'invio del messaggio di richiesta e prima della lettura
 della risposta, quest'ultima resta nella coda (così come per le fifo si aveva
 il problema delle fifo che restavano nel filesystem). In questo caso però il
 problemi sono maggiori, sia perché è molto più facile esaurire la memoria
-dedicata ad una coda di messaggi che gli inode\index{inode} di un filesystem,
+dedicata ad una coda di messaggi che gli \index{inode} inode di un filesystem,
 sia perché, con il riutilizzo dei \acr{pid} da parte dei processi, un client
 eseguito in un momento successivo potrebbe ricevere un messaggio non
 indirizzato a lui.
@@ -1689,8 +1699,8 @@ indirizzato a lui.
 I semafori non sono meccanismi di intercomunicazione diretta come quelli
 (pipe, fifo e code di messaggi) visti finora, e non consentono di scambiare
 dati fra processi, ma servono piuttosto come meccanismi di sincronizzazione o
-di protezione per le \textsl{sezioni critiche}\index{sezioni critiche} del
-codice (si ricordi quanto detto in \secref{sec:proc_race_cond}). 
+di protezione per le \index{sezione~critica} \textsl{sezioni critiche} del
+codice (si ricordi quanto detto in sez.~\ref{sec:proc_race_cond}).
 
 Un semaforo è uno speciale contatore, mantenuto nel kernel, che permette, a
 seconda del suo valore, di consentire o meno la prosecuzione dell'esecuzione
@@ -1720,7 +1730,7 @@ pertanto una realizzazione di un oggetto di questo tipo 
 demandata al kernel. La forma più semplice di semaforo è quella del
 \textsl{semaforo binario}, o \textit{mutex}, in cui un valore diverso da zero
 (normalmente 1) indica la libertà di accesso, e un valore nullo l'occupazione
-della risorsa; in generale però si possono usare semafori con valori interi,
+della risorsa. In generale però si possono usare semafori con valori interi,
 utilizzando il valore del contatore come indicatore del ``numero di risorse''
 ancora disponibili.
 
@@ -1741,15 +1751,15 @@ permette di creare o ottenere l'identificatore di un insieme di semafori 
   \bodydesc{La funzione restituisce l'identificatore (un intero positivo) o -1
     in caso di errore, nel qual caso \var{errno} assumerà i valori:
     \begin{errlist}
-    \item[\errcode{ENOSPC}] Si è cercato di creare una insieme di semafori
+    \item[\errcode{ENOSPC}] si è cercato di creare una insieme di semafori
       quando è stato superato o il limite per il numero totale di semafori
       (\const{SEMMNS}) o quello per il numero totale degli insiemi
       (\const{SEMMNI}) nel sistema.
-    \item[\errcode{EINVAL}] L'argomento \param{nsems} è minore di zero o
+    \item[\errcode{EINVAL}] l'argomento \param{nsems} è minore di zero o
       maggiore del limite sul numero di semafori per ciascun insieme
       (\const{SEMMSL}), o se l'insieme già esiste, maggiore del numero di
       semafori che contiene.
-    \item[\errcode{ENOMEM}] Il sistema non ha abbastanza memoria per poter
+    \item[\errcode{ENOMEM}] il sistema non ha abbastanza memoria per poter
       contenere le strutture per un nuovo insieme di semafori.
     \end{errlist}
     ed inoltre \errval{EACCES}, \errval{ENOENT}, \errval{EEXIST},
@@ -1759,7 +1769,7 @@ permette di creare o ottenere l'identificatore di un insieme di semafori 
 La funzione è del tutto analoga a \func{msgget}, solo che in questo caso
 restituisce l'identificatore di un insieme di semafori, in particolare è
 identico l'uso degli argomenti \param{key} e \param{flag}, per cui non
-ripeteremo quanto detto al proposito in \secref{sec:ipc_sysv_mq}. L'argomento
+ripeteremo quanto detto al proposito in sez.~\ref{sec:ipc_sysv_mq}. L'argomento
 \param{nsems} permette di specificare quanti semafori deve contenere l'insieme
 quando se ne richieda la creazione, e deve essere nullo quando si effettua una
 richiesta dell'identificatore di un insieme già esistente.
@@ -1784,7 +1794,6 @@ del sistema. Come vedremo esistono delle modalit
 diventa necessario indicare esplicitamente che si vuole il ripristino del
 semaforo all'uscita del processo.
 
-
 \begin{figure}[!htb]
   \footnotesize \centering
   \begin{minipage}[c]{15cm}
@@ -1797,14 +1806,15 @@ semaforo all'uscita del processo.
 \end{figure}
 
 A ciascun insieme di semafori è associata una struttura \struct{semid\_ds},
-riportata in \figref{fig:ipc_semid_ds}.\footnote{non si sono riportati i campi
-  ad uso interno del kernel, che vedremo in \figref{fig:ipc_sem_schema}, che
-  dipendono dall'implementazione.} Come nel caso delle code di messaggi quando
-si crea un nuovo insieme di semafori con \func{semget} questa struttura viene
-inizializzata, in particolare il campo \var{sem\_perm} viene inizializzato
-come illustrato in \secref{sec:ipc_sysv_access_control} (si ricordi che in
-questo caso il permesso di scrittura è in realtà permesso di alterare il
-semaforo), per quanto riguarda gli altri campi invece:
+riportata in fig.~\ref{fig:ipc_semid_ds}.\footnote{non si sono riportati i
+  campi ad uso interno del kernel, che vedremo in
+  fig.~\ref{fig:ipc_sem_schema}, che dipendono dall'implementazione.} Come nel
+caso delle code di messaggi quando si crea un nuovo insieme di semafori con
+\func{semget} questa struttura viene inizializzata, in particolare il campo
+\var{sem\_perm} viene inizializzato come illustrato in
+sez.~\ref{sec:ipc_sysv_access_control} (si ricordi che in questo caso il
+permesso di scrittura è in realtà permesso di alterare il semaforo), per
+quanto riguarda gli altri campi invece:
 \begin{itemize*}
 \item il campo \var{sem\_nsems}, che esprime il numero di semafori
   nell'insieme, viene inizializzato al valore di \param{nsems}.
@@ -1814,7 +1824,6 @@ semaforo), per quanto riguarda gli altri campi invece:
   effettuata, viene inizializzato a zero.
 \end{itemize*}
 
-
 Ciascun semaforo dell'insieme è realizzato come una struttura di tipo
 \struct{sem} che ne contiene i dati essenziali, la sua definizione\footnote{si
   è riportata la definizione originaria del kernel 1.0, che contiene la prima
@@ -1822,10 +1831,10 @@ Ciascun semaforo dell'insieme 
   ormai è ridotta ai soli due primi membri, e gli altri vengono calcolati
   dinamicamente. La si è utilizzata a scopo di esempio, perché indica tutti i
   valori associati ad un semaforo, restituiti dalle funzioni di controllo, e
-  citati dalle pagine di manuale.} è riportata in \figref{fig:ipc_sem}. Questa
-struttura, non è accessibile in user space, ma i valori in essa specificati
-possono essere letti in maniera indiretta, attraverso l'uso delle funzioni di
-controllo.
+  citati dalle pagine di manuale.} è riportata in fig.~\ref{fig:ipc_sem}.
+Questa struttura, non è accessibile in user space, ma i valori in essa
+specificati possono essere letti in maniera indiretta, attraverso l'uso delle
+funzioni di controllo.
 
 \begin{figure}[!htb]
   \footnotesize \centering
@@ -1838,7 +1847,7 @@ controllo.
   \label{fig:ipc_sem}
 \end{figure}
 
-I dati mantenuti nella struttura, ed elencati in \figref{fig:ipc_sem},
+I dati mantenuti nella struttura, ed elencati in fig.~\ref{fig:ipc_sem},
 indicano rispettivamente:
 \begin{description*}
 \item[\var{semval}] il valore numerico del semaforo.
@@ -1857,16 +1866,16 @@ indicano rispettivamente:
     \textbf{Costante} & \textbf{Valore} & \textbf{Significato} \\
     \hline
     \hline
-    \const{SEMMNI}&          128 & Numero massimo di insiemi di semafori. \\
+    \const{SEMMNI}&          128 & Numero massimo di insiemi di semafori.\\
     \const{SEMMSL}&          250 & Numero massimo di semafori per insieme.\\
     \const{SEMMNS}&\const{SEMMNI}*\const{SEMMSL}& Numero massimo di semafori
-                                   nel sistema .\\
+                                   nel sistema.\\
     \const{SEMVMX}&        32767 & Massimo valore per un semaforo.\\
     \const{SEMOPM}&           32 & Massimo numero di operazioni per chiamata a
                                    \func{semop}. \\
     \const{SEMMNU}&\const{SEMMNS}& Massimo numero di strutture di ripristino.\\
     \const{SEMUME}&\const{SEMOPM}& Massimo numero di voci di ripristino.\\
-    \const{SEMAEM}&\const{SEMVMX}& valore massimo per l'aggiustamento
+    \const{SEMAEM}&\const{SEMVMX}& Valore massimo per l'aggiustamento
                                    all'uscita. \\
     \hline
   \end{tabular}
@@ -1877,9 +1886,9 @@ indicano rispettivamente:
 
 Come per le code di messaggi anche per gli insiemi di semafori esistono una
 serie di limiti, i cui valori sono associati ad altrettante costanti, che si
-sono riportate in \tabref{tab:ipc_sem_limits}. Alcuni di questi limiti sono al
-solito accessibili e modificabili attraverso \func{sysctl} o scrivendo
-direttamente nel file \file{/proc/sys/kernel/sem}.
+sono riportate in tab.~\ref{tab:ipc_sem_limits}. Alcuni di questi limiti sono
+al solito accessibili e modificabili attraverso \func{sysctl} o scrivendo
+direttamente nel file \procfile{/proc/sys/kernel/sem}.
 
 La funzione che permette di effettuare le varie operazioni di controllo sui
 semafori (fra le quali, come accennato, è impropriamente compresa anche la
@@ -1899,12 +1908,12 @@ loro inizializzazione) 
     quattro. In caso di errore restituisce -1, ed \var{errno} assumerà uno dei
     valori:
     \begin{errlist}
-    \item[\errcode{EACCES}] Il processo non ha i privilegi per eseguire
+    \item[\errcode{EACCES}] il processo non ha i privilegi per eseguire
       l'operazione richiesta.
-    \item[\errcode{EIDRM}] L'insieme di semafori è stato cancellato.
-    \item[\errcode{EPERM}] Si è richiesto \const{IPC\_SET} o \const{IPC\_RMID}
+    \item[\errcode{EIDRM}] l'insieme di semafori è stato cancellato.
+    \item[\errcode{EPERM}] si è richiesto \const{IPC\_SET} o \const{IPC\_RMID}
       ma il processo non ha privilegi sufficienti ad eseguire l'operazione.
-    \item[\errcode{ERANGE}] Si è richiesto \const{SETALL} \const{SETVAL} ma il
+    \item[\errcode{ERANGE}] si è richiesto \const{SETALL} \const{SETVAL} ma il
       valore a cui si vuole impostare il semaforo è minore di zero o maggiore
       di \const{SEMVMX}.
   \end{errlist}
@@ -1912,7 +1921,7 @@ loro inizializzazione) 
 }
 \end{functions}
 
-La funzione può avere tre o quattro parametri, a seconda dell'operazione
+La funzione può avere tre o quattro argomenti, a seconda dell'operazione
 specificata con \param{cmd}, ed opera o sull'intero insieme specificato da
 \param{semid} o sul singolo semaforo di un insieme, specificato da
 \param{semnum}. 
@@ -1933,10 +1942,10 @@ Qualora la funzione operi con quattro argomenti \param{arg} 
 generico, che conterrà un dato diverso a seconda dell'azione richiesta; per
 unificare l'argomento esso deve essere passato come una \struct{semun}, la cui
 definizione, con i possibili valori che può assumere, è riportata in
-\figref{fig:ipc_semun}.
+fig.~\ref{fig:ipc_semun}.
 
 Come già accennato sia il comportamento della funzione che il numero di
-parametri con cui deve essere invocata, dipendono dal valore dell'argomento
+argomenti con cui deve essere invocata dipendono dal valore dell'argomento
 \param{cmd}, che specifica l'azione da intraprendere; i valori validi (che
 cioè non causano un errore di \errcode{EINVAL}) per questo argomento sono i
 seguenti:
@@ -2005,10 +2014,10 @@ tutti i semafori il cui valore viene modificato.
     \textbf{Operazione}  & \textbf{Valore restituito} \\
     \hline
     \hline
-    \const{GETNCNT}& valore di \var{semncnt}.\\
-    \const{GETPID} & valore di \var{sempid}.\\
-    \const{GETVAL} & valore di \var{semval}.\\
-    \const{GETZCNT}& valore di \var{semzcnt}.\\
+    \const{GETNCNT}& Valore di \var{semncnt}.\\
+    \const{GETPID} & Valore di \var{sempid}.\\
+    \const{GETVAL} & Valore di \var{semval}.\\
+    \const{GETZCNT}& Valore di \var{semzcnt}.\\
     \hline
   \end{tabular}
   \caption{Valori di ritorno della funzione \func{semctl}.} 
@@ -2018,7 +2027,7 @@ tutti i semafori il cui valore viene modificato.
 Il valore di ritorno della funzione in caso di successo dipende
 dall'operazione richiesta; per tutte le operazioni che richiedono quattro
 argomenti esso è sempre nullo, per le altre operazioni, elencate in
-\tabref{tab:ipc_semctl_returns} viene invece restituito il valore richiesto,
+tab.~\ref{tab:ipc_semctl_returns} viene invece restituito il valore richiesto,
 corrispondente al campo della struttura \struct{sem} indicato nella seconda
 colonna della tabella.
 
@@ -2037,18 +2046,18 @@ vengono effettuate con la funzione \funcd{semop}, il cui prototipo 
   \bodydesc{La funzione restituisce 0 in caso di successo e -1 in caso di
     errore, nel qual caso \var{errno} assumerà uno dei valori:
     \begin{errlist}
-    \item[\errcode{EACCES}] Il processo non ha i privilegi per eseguire
+    \item[\errcode{EACCES}] il processo non ha i privilegi per eseguire
       l'operazione richiesta.
-    \item[\errcode{EIDRM}] L'insieme di semafori è stato cancellato.
-    \item[\errcode{ENOMEM}] Si è richiesto un \const{SEM\_UNDO} ma il sistema
+    \item[\errcode{EIDRM}] l'insieme di semafori è stato cancellato.
+    \item[\errcode{ENOMEM}] si è richiesto un \const{SEM\_UNDO} ma il sistema
       non ha le risorse per allocare la struttura di ripristino.
-    \item[\errcode{EAGAIN}] Un'operazione comporterebbe il blocco del processo,
+    \item[\errcode{EAGAIN}] un'operazione comporterebbe il blocco del processo,
       ma si è specificato \const{IPC\_NOWAIT} in \var{sem\_flg}.
-    \item[\errcode{EINTR}] La funzione, bloccata in attesa dell'esecuzione
+    \item[\errcode{EINTR}] la funzione, bloccata in attesa dell'esecuzione
       dell'operazione, viene interrotta da un segnale.
-    \item[\errcode{E2BIG}] L'argomento \param{nsops} è maggiore del numero
+    \item[\errcode{E2BIG}] l'argomento \param{nsops} è maggiore del numero
       massimo di operazioni \const{SEMOPM}.
-    \item[\errcode{ERANGE}] Per alcune operazioni il valore risultante del
+    \item[\errcode{ERANGE}] per alcune operazioni il valore risultante del
       semaforo viene a superare il limite massimo \const{SEMVMX}.
   \end{errlist}
   ed inoltre \errval{EFAULT} ed \errval{EINVAL}.
@@ -2076,7 +2085,7 @@ effettivamente eseguite se e soltanto se 
 
 Il contenuto di ciascuna operazione deve essere specificato attraverso una
 opportuna struttura \struct{sembuf} (la cui definizione è riportata in
-\figref{fig:ipc_sembuf}) che il programma chiamante deve avere cura di
+fig.~\ref{fig:ipc_sembuf}) che il programma chiamante deve avere cura di
 allocare in un opportuno vettore. La struttura permette di indicare il
 semaforo su cui operare, il tipo di operazione, ed un flag di controllo.
 Il campo \var{sem\_num} serve per indicare a quale semaforo dell'insieme fa
@@ -2167,7 +2176,7 @@ una \func{exec} (altrimenti non si avrebbe ripristino).
 
 Tutto questo però ha un problema di fondo. Per capire di cosa si tratta
 occorre fare riferimento all'implementazione usata in Linux, che è riportata
-in maniera semplificata nello schema di \figref{fig:ipc_sem_schema}.  Si è
+in maniera semplificata nello schema di fig.~\ref{fig:ipc_sem_schema}.  Si è
 presa come riferimento l'architettura usata fino al kernel 2.2.x che è più
 semplice (ed illustrata in dettaglio in \cite{tlk}); nel kernel 2.4.x la
 struttura del \textit{SysV IPC} è stata modificata, ma le definizioni relative
@@ -2175,7 +2184,7 @@ a queste strutture restano per compatibilit
   vecchie versioni delle librerie del C, come le libc5.}
 
 \begin{figure}[htb]
-  \centering \includegraphics[width=15cm]{img/semtruct}
+  \centering \includegraphics[width=13cm]{img/semtruct}
   \caption{Schema della struttura di un insieme di semafori.}
   \label{fig:ipc_sem_schema}
 \end{figure}
@@ -2187,11 +2196,13 @@ possono avere successo; se una di esse comporta il blocco del processo il
 kernel crea una struttura \struct{sem\_queue} che viene aggiunta in fondo alla
 coda di attesa associata a ciascun insieme di semafori\footnote{che viene
   referenziata tramite i campi \var{sem\_pending} e \var{sem\_pending\_last}
-  di \struct{semid\_ds}.}. Nella struttura viene memorizzato il riferimento
-alle operazioni richieste (nel campo \var{sops}, che è un puntatore ad una
-struttura \struct{sembuf}) e al processo corrente (nel campo \var{sleeper}) poi
-quest'ultimo viene messo stato di attesa e viene invocato lo
-scheduler\index{scheduler} per passare all'esecuzione di un altro processo.
+  di \struct{semid\_ds}.}. 
+
+Nella struttura viene memorizzato il riferimento alle operazioni richieste
+(nel campo \var{sops}, che è un puntatore ad una struttura \struct{sembuf}) e
+al processo corrente (nel campo \var{sleeper}) poi quest'ultimo viene messo
+stato di attesa e viene invocato lo \itindex{scheduler} scheduler per passare
+all'esecuzione di un altro processo.
 
 Se invece tutte le operazioni possono avere successo queste vengono eseguite
 immediatamente, dopo di che il kernel esegue una scansione della coda di
@@ -2200,13 +2211,12 @@ operazioni sospese in precedenza pu
 struttura \struct{sem\_queue} viene rimossa e lo stato del processo associato
 all'operazione (\var{sleeper}) viene riportato a \textit{running}; il tutto
 viene ripetuto fin quando non ci sono più operazioni eseguibili o si è
-svuotata la coda.
-
-Per gestire il meccanismo del ripristino tutte le volte che per un'operazione
-si è specificato il flag \const{SEM\_UNDO} viene mantenuta per ciascun insieme
-di semafori una apposita struttura \struct{sem\_undo} che contiene (nel vettore
-puntato dal campo \var{semadj}) un valore di aggiustamento per ogni semaforo
-cui viene sommato l'opposto del valore usato per l'operazione. 
+svuotata la coda.  Per gestire il meccanismo del ripristino tutte le volte che
+per un'operazione si è specificato il flag \const{SEM\_UNDO} viene mantenuta
+per ciascun insieme di semafori una apposita struttura \struct{sem\_undo} che
+contiene (nel vettore puntato dal campo \var{semadj}) un valore di
+aggiustamento per ogni semaforo cui viene sommato l'opposto del valore usato
+per l'operazione.
 
 Queste strutture sono mantenute in due liste,\footnote{rispettivamente
   attraverso i due campi \var{id\_next} e \var{proc\_next}.} una associata
@@ -2216,25 +2226,26 @@ operazione con \func{semctl}; l'altra associata al processo che ha eseguito
 l'operazione;\footnote{attraverso il campo \var{semundo} di
   \struct{task\_struct}, come mostrato in \ref{fig:ipc_sem_schema}.} quando un
 processo termina, la lista ad esso associata viene scandita e le operazioni
-applicate al semaforo.
-
-Siccome un processo può accumulare delle richieste di ripristino per semafori
-differenti chiamate attraverso diverse chiamate a \func{semop}, si pone il
-problema di come eseguire il ripristino dei semafori all'uscita del processo,
-ed in particolare se questo può essere fatto atomicamente. Il punto è cosa
-succede quando una delle operazioni previste per il ripristino non può essere
-eseguita immediatamente perché ad esempio il semaforo è occupato; in tal caso
-infatti, se si pone il processo in stato di \textit{sleep} aspettando la
-disponibilità del semaforo (come faceva l'implementazione originaria) si perde
-l'atomicità dell'operazione. La scelta fatta dal kernel è pertanto quella di
-effettuare subito le operazioni che non prevedono un blocco del processo e di
-ignorare silenziosamente le altre; questo però comporta il fatto che il
-ripristino non è comunque garantito in tutte le occasioni.
+applicate al semaforo.  Siccome un processo può accumulare delle richieste di
+ripristino per semafori differenti chiamate attraverso diverse chiamate a
+\func{semop}, si pone il problema di come eseguire il ripristino dei semafori
+all'uscita del processo, ed in particolare se questo può essere fatto
+atomicamente.
+
+Il punto è cosa succede quando una delle operazioni previste per il ripristino
+non può essere eseguita immediatamente perché ad esempio il semaforo è
+occupato; in tal caso infatti, se si pone il processo in stato di
+\textit{sleep} aspettando la disponibilità del semaforo (come faceva
+l'implementazione originaria) si perde l'atomicità dell'operazione. La scelta
+fatta dal kernel è pertanto quella di effettuare subito le operazioni che non
+prevedono un blocco del processo e di ignorare silenziosamente le altre;
+questo però comporta il fatto che il ripristino non è comunque garantito in
+tutte le occasioni.
 
 Come esempio di uso dell'interfaccia dei semafori vediamo come implementare
 con essa dei semplici \textit{mutex} (cioè semafori binari), tutto il codice
 in questione, contenuto nel file \file{Mutex.c} allegato ai sorgenti, è
-riportato in \figref{fig:ipc_mutex_create}. Utilizzeremo l'interfaccia per
+riportato in fig.~\ref{fig:ipc_mutex_create}. Utilizzeremo l'interfaccia per
 creare un insieme contenente un singolo semaforo, per il quale poi useremo un
 valore unitario per segnalare la disponibilità della risorsa, ed un valore
 nullo per segnalarne l'indisponibilità. 
@@ -2306,9 +2317,9 @@ non avrebbe pi
 considerata libera).  Infine si tenga presente che usare \func{MutexRead} per
 controllare il valore dei mutex prima di proseguire in una operazione di
 sblocco non servirebbe comunque, dato che l'operazione non sarebbe atomica.
-Vedremo in \secref{sec:ipc_lock_file} come sia possibile ottenere
+Vedremo in sez.~\ref{sec:ipc_lock_file} come sia possibile ottenere
 un'interfaccia analoga a quella appena illustrata, senza incorrere in questi
-problemi, usando il file locking\index{file!locking}.
+problemi, usando il \index{file!locking} \textit{file locking}.
 
 
 \subsection{Memoria condivisa}
@@ -2329,14 +2340,14 @@ ed il suo prototipo 
   \bodydesc{La funzione restituisce l'identificatore (un intero positivo) o -1
     in caso di errore, nel qual caso \var{errno} assumerà i valori:
     \begin{errlist}
-    \item[\errcode{ENOSPC}] Si è superato il limite (\const{SHMMNI}) sul numero
+    \item[\errcode{ENOSPC}] si è superato il limite (\const{SHMMNI}) sul numero
       di segmenti di memoria nel sistema, o cercato di allocare un segmento le
       cui dimensioni fanno superare il limite di sistema (\const{SHMALL}) per
       la memoria ad essi riservata.
-    \item[\errcode{EINVAL}] Si è richiesta una dimensione per un nuovo segmento
+    \item[\errcode{EINVAL}] si è richiesta una dimensione per un nuovo segmento
       maggiore di \const{SHMMAX} o minore di \const{SHMMIN}, o se il segmento
       già esiste \param{size} è maggiore delle sue dimensioni.
-    \item[\errcode{ENOMEM}] Il sistema non ha abbastanza memoria per poter
+    \item[\errcode{ENOMEM}] il sistema non ha abbastanza memoria per poter
       contenere le strutture per un nuovo segmento di memoria condivisa.
     \end{errlist}
     ed inoltre \errval{EACCES}, \errval{ENOENT}, \errval{EEXIST},
@@ -2345,7 +2356,7 @@ ed il suo prototipo 
 
 La funzione, come \func{semget}, è del tutto analoga a \func{msgget}, ed
 identico è l'uso degli argomenti \param{key} e \param{flag} per cui non
-ripeteremo quanto detto al proposito in \secref{sec:ipc_sysv_mq}. L'argomento
+ripeteremo quanto detto al proposito in sez.~\ref{sec:ipc_sysv_mq}. L'argomento
 \param{size} specifica invece la dimensione, in byte, del segmento, che viene
 comunque arrotondata al multiplo superiore di \const{PAGE\_SIZE}.
 
@@ -2379,11 +2390,11 @@ norma, significa insieme a dei semafori.
 \end{figure}
 
 A ciascun segmento di memoria condivisa è associata una struttura
-\struct{shmid\_ds}, riportata in \figref{fig:ipc_shmid_ds}.  Come nel caso
+\struct{shmid\_ds}, riportata in fig.~\ref{fig:ipc_shmid_ds}.  Come nel caso
 delle code di messaggi quando si crea un nuovo segmento di memoria condivisa
 con \func{shmget} questa struttura viene inizializzata, in particolare il
 campo \var{shm\_perm} viene inizializzato come illustrato in
-\secref{sec:ipc_sysv_access_control}, e valgono le considerazioni ivi fatte
+sez.~\ref{sec:ipc_sysv_access_control}, e valgono le considerazioni ivi fatte
 relativamente ai permessi di accesso; per quanto riguarda gli altri campi
 invece:
 \begin{itemize}
@@ -2408,7 +2419,7 @@ di questi limiti sono al solito accessibili e modificabili attraverso
 \func{sysctl} o scrivendo direttamente nei rispettivi file di
 \file{/proc/sys/kernel/}. 
 
-In \tabref{tab:ipc_shm_limits} si sono riportate le
+In tab.~\ref{tab:ipc_shm_limits} si sono riportate le
 costanti simboliche associate a ciascuno di essi, il loro significato, i
 valori preimpostati, e, quando presente, il file in \file{/proc/sys/kernel/}
 che permettono di cambiarne il valore. 
@@ -2423,23 +2434,25 @@ che permettono di cambiarne il valore.
     & \textbf{Significato} \\
     \hline
     \hline
-    \const{SHMALL}& 0x200000&\file{shmall}& Numero massimo di pagine che 
-                                       possono essere usate per i segmenti di
-                                       memoria condivisa. \\
-    \const{SHMMAX}&0x2000000&\file{shmmax}& Dimensione massima di un segmento 
-                                            di memoria condivisa.\\
-    \const{SHMMNI}&     4096&\file{msgmni}& Numero massimo di segmenti di 
-                                            memoria condivisa presenti nel
-                                            kernel.\\ 
+    \const{SHMALL}& 0x200000&\procrelfile{/proc/sys/kernel}{shmall}
+                            & Numero massimo di pagine che 
+                              possono essere usate per i segmenti di
+                              memoria condivisa.\\
+    \const{SHMMAX}&0x2000000&\procrelfile{/proc/sys/kernel}{shmmax} 
+                            & Dimensione massima di un segmento di memoria
+                              condivisa.\\ 
+    \const{SHMMNI}&     4096&\procrelfile{/proc/sys/kernel}{msgmni}
+                            & Numero massimo di segmenti di memoria condivisa
+                              presenti nel kernel.\\ 
     \const{SHMMIN}&        1& ---         & Dimensione minima di un segmento di
-                                            memoria condivisa. \\
+                                            memoria condivisa.\\
     \const{SHMLBA}&\const{PAGE\_SIZE}&--- & Limite inferiore per le dimensioni
                                             minime di un segmento (deve essere
                                             allineato alle dimensioni di una
-                                            pagina di memoria). \\
+                                            pagina di memoria).\\
     \const{SHMSEG}&   ---   &     ---     & Numero massimo di segmenti di
-                                            memoria condivisa 
-                                            per ciascun processo.\\
+                                            memoria condivisa per ciascun
+                                            processo.\\
 
 
     \hline
@@ -2463,18 +2476,18 @@ un segmento di memoria condivisa 
   \bodydesc{La funzione restituisce 0 in caso di successo e -1 in caso di
     errore, nel qual caso \var{errno} assumerà i valori:
     \begin{errlist}
-    \item[\errcode{EACCES}] Si è richiesto \const{IPC\_STAT} ma i permessi non
+    \item[\errcode{EACCES}] si è richiesto \const{IPC\_STAT} ma i permessi non
       consentono l'accesso in lettura al segmento.
-    \item[\errcode{EINVAL}] O \param{shmid} non è un identificatore valido o
+    \item[\errcode{EINVAL}] o \param{shmid} non è un identificatore valido o
       \param{cmd} non è un comando valido.
-    \item[\errcode{EIDRM}] L'argomento \param{shmid} fa riferimento ad un
+    \item[\errcode{EIDRM}] l'argomento \param{shmid} fa riferimento ad un
       segmento che è stato cancellato.
-    \item[\errcode{EPERM}] Si è specificato un comando con \const{IPC\_SET} o
+    \item[\errcode{EPERM}] si è specificato un comando con \const{IPC\_SET} o
       \const{IPC\_RMID} senza i permessi necessari.
-    \item[\errcode{EOVERFLOW}] Si è tentato il comando \const{IPC\_STAT} ma il
+    \item[\errcode{EOVERFLOW}] si è tentato il comando \const{IPC\_STAT} ma il
       valore del group-ID o dell'user-ID è troppo grande per essere
-      memorizzato nella struttura puntata dal \param{buf}.  
-    \item[\errcode{EFAULT}] L'indirizzo specificato con \param{buf} non è
+      memorizzato nella struttura puntata da \param{buf}.
+    \item[\errcode{EFAULT}] l'indirizzo specificato con \param{buf} non è
       valido.
     \end{errlist}
 }
@@ -2498,19 +2511,20 @@ corrispondente comportamento della funzione, sono i seguenti:
   \var{shm\_perm.uid} e \var{shm\_perm.gid} occorre essere il proprietario o
   il creatore del segmento, oppure l'amministratore. Compiuta l'operazione
   aggiorna anche il valore del campo \var{shm\_ctime}.
-\item[\const{SHM\_LOCK}] Abilita il  
-  \textit{memory locking}\index{memory locking}\footnote{impedisce cioè che la
-    memoria usata per il segmento venga salvata su disco dal meccanismo della
-    memoria virtuale\index{memoria virtuale}; si ricordi quanto trattato in
-    \secref{sec:proc_mem_lock}.} sul segmento di memoria condivisa. Solo
+\item[\const{SHM\_LOCK}] Abilita il \itindex{memory~locking} \textit{memory
+    locking}\footnote{impedisce cioè che la memoria usata per il segmento
+    venga salvata su disco dal meccanismo della \index{memoria~virtuale}
+    memoria virtuale; si ricordi quanto trattato in
+    sez.~\ref{sec:proc_mem_lock}.} sul segmento di memoria condivisa. Solo
+  l'amministratore può utilizzare questo comando.
+\item[\const{SHM\_UNLOCK}] Disabilita il \itindex{memory~locking}
+  \textit{memory locking} sul segmento di memoria condivisa.  Solo
   l'amministratore può utilizzare questo comando.
-\item[\const{SHM\_UNLOCK}] Disabilita il \textit{memory locking} sul segmento
-  di memoria condivisa. Solo l'amministratore può utilizzare questo comando.
 \end{basedescript}
 i primi tre comandi sono gli stessi già visti anche per le code di messaggi e
 gli insiemi di semafori, gli ultimi due sono delle estensioni specifiche
 previste da Linux, che permettono di abilitare e disabilitare il meccanismo
-della memoria virtuale\index{memoria virtuale} per il segmento.
+della \index{memoria~virtuale} memoria virtuale per il segmento.
 
 L'argomento \param{buf} viene utilizzato solo con i comandi \const{IPC\_STAT}
 e \const{IPC\_SET} nel qual caso esso dovrà puntare ad una struttura
@@ -2534,9 +2548,9 @@ il suo prototipo 
     successo, e -1 in caso di errore, nel qual caso \var{errno} assumerà i
     valori:
     \begin{errlist}
-    \item[\errcode{EACCES}] Il processo non ha i privilegi per accedere al
+    \item[\errcode{EACCES}] il processo non ha i privilegi per accedere al
       segmento nella modalità richiesta.
-    \item[\errcode{EINVAL}] Si è specificato un identificatore invalido per
+    \item[\errcode{EINVAL}] si è specificato un identificatore invalido per
       \param{shmid}, o un indirizzo non allineato sul confine di una pagina
       per \param{shmaddr}.
     \end{errlist}
@@ -2546,12 +2560,12 @@ il suo prototipo 
 La funzione inserisce un segmento di memoria condivisa all'interno dello
 spazio di indirizzi del processo, in modo che questo possa accedervi
 direttamente, la situazione dopo l'esecuzione di \func{shmat} è illustrata in
-\figref{fig:ipc_shmem_layout} (per la comprensione del resto dello schema si
-ricordi quanto illustrato al proposito in \secref{sec:proc_mem_layout}). In
+fig.~\ref{fig:ipc_shmem_layout} (per la comprensione del resto dello schema si
+ricordi quanto illustrato al proposito in sez.~\ref{sec:proc_mem_layout}). In
 particolare l'indirizzo finale del segmento dati (quello impostato da
-\func{brk}, vedi \secref{sec:proc_mem_sbrk}) non viene influenzato. Si tenga
-presente infine che la funzione ha successo anche se il segmento è stato
-marcato per la cancellazione.
+\func{brk}, vedi sez.~\ref{sec:proc_mem_alloc}) non viene influenzato.
+Si tenga presente infine che la funzione ha successo anche se il segmento è
+stato marcato per la cancellazione.
 
 \begin{figure}[htb]
   \centering
@@ -2561,9 +2575,9 @@ marcato per la cancellazione.
   \label{fig:ipc_shmem_layout}
 \end{figure}
 
-L'argomento \param{shmaddr} specifica a quale indirizzo\footnote{Lo standard
+L'argomento \param{shmaddr} specifica a quale indirizzo\footnote{lo standard
   SVID prevede che l'argomento \param{shmaddr} sia di tipo \ctyp{char *}, così
-  come il valore di ritorno della funzione. In Linux è stato così con le
+  come il valore di ritorno della funzione; in Linux è stato così con le
   \acr{libc4} e le \acr{libc5}, con il passaggio alle \acr{glibc} il tipo di
   \param{shmaddr} è divenuto un \ctyp{const void *} e quello del valore di
   ritorno un \ctyp{void *}.} deve essere associato il segmento, se il valore
@@ -2593,12 +2607,12 @@ indirizzo come arrotondamento, in Linux 
 
 L'uso di \const{SHM\_RDONLY} permette di agganciare il segmento in sola
 lettura (si ricordi che anche le pagine di memoria hanno dei permessi), in tal
-caso un tentativo di scrivere sul segmento comporterà una violazione di
-accesso con l'emissione di un segnale di \const{SIGSEGV}. Il comportamento
-usuale di \func{shmat} è quello di agganciare il segmento con l'accesso in
-lettura e scrittura (ed il processo deve aver questi permessi in
-\var{shm\_perm}), non è prevista la possibilità di agganciare un segmento in
-sola scrittura.
+caso un tentativo di scrivere sul segmento comporterà una
+\itindex{segment~violation} violazione di accesso con l'emissione di un
+segnale di \const{SIGSEGV}. Il comportamento usuale di \func{shmat} è quello
+di agganciare il segmento con l'accesso in lettura e scrittura (ed il processo
+deve aver questi permessi in \var{shm\_perm}), non è prevista la possibilità
+di agganciare un segmento in sola scrittura.
 
 In caso di successo la funzione aggiorna anche i seguenti campi di
 \struct{shmid\_ds}:
@@ -2611,7 +2625,7 @@ In caso di successo la funzione aggiorna anche i seguenti campi di
   aumentato di uno.
 \end{itemize*} 
 
-Come accennato in \secref{sec:proc_fork} un segmento di memoria condivisa
+Come accennato in sez.~\ref{sec:proc_fork} un segmento di memoria condivisa
 agganciato ad un processo viene ereditato da un figlio attraverso una
 \func{fork}, dato che quest'ultimo riceve una copia dello spazio degli
 indirizzi del padre. Invece, dato che attraverso una \func{exec} viene
@@ -2632,7 +2646,7 @@ dell'interfaccia, \funcd{shmdt}, il cui prototipo 
   
   \bodydesc{La funzione restituisce 0 in caso di successo, e -1 in caso di
     errore, la funzione fallisce solo quando non c'è un segmento agganciato
-    all'indirizzo \func{shmaddr}, con \var{errno} che assume il valore
+    all'indirizzo \param{shmaddr}, con \var{errno} che assume il valore
     \errval{EINVAL}.}
 \end{functions}
 
@@ -2668,7 +2682,7 @@ viene tolta dallo spazio di indirizzi del processo.
 Come esempio di uso di queste funzioni vediamo come implementare una serie di
 funzioni di libreria che ne semplifichino l'uso, automatizzando le operazioni
 più comuni; il codice, contenuto nel file \file{SharedMem.c}, è riportato in
-\figref{fig:ipc_sysv_shm_func}.
+fig.~\ref{fig:ipc_sysv_shm_func}.
 
 La prima funzione (\texttt{\small 3--16}) è \func{ShmCreate} che, data una
 chiave, crea il segmento di memoria condivisa restituendo il puntatore allo
@@ -2698,7 +2712,7 @@ chiave ed il puntatore associati al segmento di memoria condivisa, prima lo
 sgancia dal processo e poi lo rimuove. Il primo passo (\texttt{\small 37}) è
 la chiamata a \func{shmdt} per sganciare il segmento, restituendo
 (\texttt{\small 38--39}) un valore -1 in caso di errore. Il passo successivo
-(\texttt{\small 41}) è utilizzare \func{shmget} per ottenre l'identificatore
+(\texttt{\small 41}) è utilizzare \func{shmget} per ottenere l'identificatore
 associato al segmento data la chiave \var{key}. Al solito si restituisce un
 valore di -1 (\texttt{\small 42--45}) in caso di errore, mentre se tutto va
 bene si conclude restituendo un valore nullo.
@@ -2710,7 +2724,7 @@ accessi.  Per questo motivo, quando la comunicazione fra processi 
 sequenziale, altri meccanismi come le pipe, le fifo o i socket, che non
 necessitano di sincronizzazione esplicita, sono da preferire. Essa diventa
 l'unico meccanismo possibile quando la comunicazione non è
-sequenziale\footnote{come accennato in \secref{sec:ipc_sysv_mq} per la
+sequenziale\footnote{come accennato in sez.~\ref{sec:ipc_sysv_mq} per la
   comunicazione non sequenziale si possono usare le code di messaggi,
   attraverso l'uso del campo \var{mtype}, ma solo se quest'ultima può essere
   effettuata in forma di messaggio.} o quando non può avvenire secondo una
@@ -2734,7 +2748,7 @@ directory, link simbolici, file normali, ecc.) che saranno salvati in un
 segmento di memoria condivisa cui altri processi potranno accedere per
 ricavare la parte di informazione che interessa.
 
-In \figref{fig:ipc_dirmonitor_main} si è riportata la sezione principale del
+In fig.~\ref{fig:ipc_dirmonitor_main} si è riportata la sezione principale del
 corpo del programma server, insieme alle definizioni delle altre funzioni
 usate nel programma e delle variabili globali, omettendo tutto quello che
 riguarda la gestione delle opzioni e la stampa delle istruzioni di uso a
@@ -2761,17 +2775,17 @@ Il programma, dopo la sezione, omessa, relativa alla gestione delle opzioni da
 riga di comando (che si limitano alla eventuale stampa di un messaggio di
 aiuto a video ed all'impostazione della durata dell'intervallo con cui viene
 ripetuto il calcolo delle proprietà della directory) controlla (\texttt{\small
-  20--23}) che sia stato specificato il parametro necessario contenente il
-nome della directory da tenere sotto controllo, senza il quale esce
-immediatamente con un messaggio di errore.
+  20--23}) che sia stato specificato l'argomento necessario contenente il nome
+della directory da tenere sotto controllo, senza il quale esce immediatamente
+con un messaggio di errore.
 
-Poi, per verificare che il parametro specifichi effettivamente una directory,
+Poi, per verificare che l'argomento specifichi effettivamente una directory,
 si esegue (\texttt{\small 24--26}) su di esso una \func{chdir}, uscendo
 immediatamente in caso di errore.  Questa funzione serve anche per impostare
 la directory di lavoro del programma nella directory da tenere sotto
 controllo, in vista del successivo uso della funzione
 \func{daemon}.\footnote{si noti come si è potuta fare questa scelta,
-  nonostante le indicazioni illustrate in \secref{sec:sess_daemon}, per il
+  nonostante le indicazioni illustrate in sez.~\ref{sec:sess_daemon}, per il
   particolare scopo del programma, che necessita comunque di restare
   all'interno di una directory.} Infine (\texttt{\small 27--29}) si installano
 i gestori per i vari segnali di terminazione che, avendo a che fare con un
@@ -2792,8 +2806,8 @@ abbia successo. Con l'indirizzo \var{shmptr} cos
 accedere alla memoria condivisa, che, per come abbiamo lo abbiamo definito,
 sarà vista nella forma data da \struct{DirProp}. Infine (\texttt{\small
   36--39}) utilizzando sempre la stessa chiave, si crea, tramite le funzioni
-di interfaccia già descritte in \secref{sec:ipc_sysv_sem}, anche un mutex, che
-utilizzeremo per regolare l'accesso alla memoria condivisa.
+di interfaccia già descritte in sez.~\ref{sec:ipc_sysv_sem}, anche un mutex,
+che utilizzeremo per regolare l'accesso alla memoria condivisa.
 
 \begin{figure}[!htb]
   \footnotesize \centering
@@ -2825,13 +2839,13 @@ l'opzione \code{-p} con una \func{sleep}.
 
 Si noti come per il calcolo dei valori da mantenere nella memoria condivisa si
 sia usata ancora una volta la funzione \func{DirScan}, già utilizzata (e
-descritta in dettaglio) in \secref{sec:file_dir_read}, che ci permette di
+descritta in dettaglio) in sez.~\ref{sec:file_dir_read}, che ci permette di
 effettuare la scansione delle voci della directory, chiamando per ciascuna di
 esse la funzione \func{ComputeValues}, che esegue tutti i calcoli necessari.
 
-Il codice di quest'ultima è riportato in \figref{fig:ipc_dirmonitor_sub}. Come
-si vede la funzione (\texttt{\small 2--16}) è molto semplice e si limita a
-chiamare (\texttt{\small 5}) la funzione \func{stat} sul file indicato da
+Il codice di quest'ultima è riportato in fig.~\ref{fig:ipc_dirmonitor_sub}.
+Come si vede la funzione (\texttt{\small 2--16}) è molto semplice e si limita
+chiamare (\texttt{\small 5}) la funzione \func{stat} sul file indicato da
 ciascuna voce, per ottenerne i dati, che poi utilizza per incrementare i vari
 contatori nella memoria condivisa, cui accede grazie alla variabile globale
 \var{shmptr}.
@@ -2842,14 +2856,14 @@ effettuare nessun controllo e si pu
 condivisa usando \var{shmptr} per riempire i campi della struttura
 \struct{DirProp}; così prima (\texttt{\small 6--7}) si sommano le dimensioni
 dei file ed il loro numero, poi, utilizzando le macro di
-\tabref{tab:file_type_macro}, si contano (\texttt{\small 8--14}) quanti ce ne
-sono per ciascun tipo.
-
-In \figref{fig:ipc_dirmonitor_sub} è riportato anche il codice (\texttt{\small
-  17--23}) del gestore dei segnali di terminazione, usato per chiudere il
-programma. Esso, oltre a provocare l'uscita del programma, si incarica anche
-di cancellare tutti gli oggetti di intercomunicazione non più necessari.  Per
-questo anzitutto (\texttt{\small 19}) acquisisce il mutex con
+tab.~\ref{tab:file_type_macro}, si contano (\texttt{\small 8--14}) quanti ce
+ne sono per ciascun tipo.
+
+In fig.~\ref{fig:ipc_dirmonitor_sub} è riportato anche il codice
+(\texttt{\small 17--23}) del gestore dei segnali di terminazione, usato per
+chiudere il programma. Esso, oltre a provocare l'uscita del programma, si
+incarica anche di cancellare tutti gli oggetti di intercomunicazione non più
+necessari.  Per questo anzitutto (\texttt{\small 19}) acquisisce il mutex con
 \func{MutexLock}, per evitare di operare mentre un client sta ancora leggendo
 i dati, dopo di che (\texttt{\small 20}) distacca e rimuove il segmento di
 memoria condivisa usando \func{ShmRemove}.  Infine (\texttt{\small 21})
@@ -2867,7 +2881,7 @@ rimuove il mutex con \func{MutexRemove} ed esce (\texttt{\small 22}).
 \end{figure}
 
 Il codice del client usato per leggere le informazioni mantenute nella memoria
-condivisa è riportato in \figref{fig:ipc_dirmonitor_client}. Al solito si è
+condivisa è riportato in fig.~\ref{fig:ipc_dirmonitor_client}. Al solito si è
 omessa la sezione di gestione delle opzioni e la funzione che stampa a video
 le istruzioni; il codice completo è nei sorgenti allegati, nel file
 \file{ReadMonitor.c}.
@@ -2890,13 +2904,14 @@ il mutex, prima di uscire.
 Verifichiamo allora il funzionamento dei nostri programmi; al solito, usando
 le funzioni di libreria occorre definire opportunamente
 \code{LD\_LIBRARY\_PATH}; poi si potrà lanciare il server con:
-\begin{verbatim}
+\begin{Verbatim}
 [piccardi@gont sources]$ ./dirmonitor ./
-\end{verbatim}%$
+\end{Verbatim}
+%$
 ed avendo usato \func{daemon} il comando ritornerà immediatamente. Una volta
 che il server è in esecuzione, possiamo passare ad invocare il client per
 verificarne i risultati, in tal caso otterremo:
-\begin{verbatim}
+\begin{Verbatim}
 [piccardi@gont sources]$ ./readmon 
 Ci sono 68 file dati
 Ci sono 3 directory
@@ -2906,12 +2921,13 @@ Ci sono 0 socket
 Ci sono 0 device a caratteri
 Ci sono 0 device a blocchi
 Totale  71 file, per 489831 byte
-\end{verbatim}%$
+\end{Verbatim}
+%$
 ed un rapido calcolo (ad esempio con \code{ls -a | wc} per contare i file) ci
 permette di verificare che il totale dei file è giusto. Un controllo con
 \cmd{ipcs} ci permette inoltre di verificare la presenza di un segmento di
 memoria condivisa e di un semaforo:
-\begin{verbatim}
+\begin{Verbatim}
 [piccardi@gont sources]$ ipcs
 ------ Shared Memory Segments --------
 key        shmid      owner      perms      bytes      nattch     status      
@@ -2923,12 +2939,13 @@ key        semid      owner      perms      nsems
 
 ------ Message Queues --------
 key        msqid      owner      perms      used-bytes   messages    
-\end{verbatim}%$
+\end{Verbatim}
+%$
 
 Se a questo punto aggiungiamo un file, ad esempio con \code{touch prova},
 potremo verificare che, passati nel peggiore dei casi almeno 10 secondi (o
 l'eventuale altro intervallo impostato per la rilettura dei dati) avremo:
-\begin{verbatim}
+\begin{Verbatim}
 [piccardi@gont sources]$ ./readmon 
 Ci sono 69 file dati
 Ci sono 3 directory
@@ -2938,18 +2955,20 @@ Ci sono 0 socket
 Ci sono 0 device a caratteri
 Ci sono 0 device a blocchi
 Totale  72 file, per 489887 byte
-\end{verbatim}%$
+\end{Verbatim}
+%$
 
 A questo punto possiamo far uscire il server inviandogli un segnale di
 \const{SIGTERM} con il comando \code{killall dirmonitor}, a questo punto
 ripetendo la lettura, otterremo un errore:
-\begin{verbatim}
+\begin{Verbatim}
 [piccardi@gont sources]$ ./readmon 
 Cannot find shared memory: No such file or directory
-\end{verbatim}%$
+\end{Verbatim}
+%$
 e inoltre potremo anche verificare che anche gli oggetti di intercomunicazione
 visti in precedenza sono stati regolarmente  cancellati:
-\begin{verbatim}
+\begin{Verbatim}
 [piccardi@gont sources]$ ipcs
 ------ Shared Memory Segments --------
 key        shmid      owner      perms      bytes      nattch     status      
@@ -2959,14 +2978,14 @@ key        semid      owner      perms      nsems
 
 ------ Message Queues --------
 key        msqid      owner      perms      used-bytes   messages    
-\end{verbatim}%$
-
+\end{Verbatim}
+%$
 
 
 %% Per capire meglio il funzionamento delle funzioni facciamo ancora una volta
 %% riferimento alle strutture con cui il kernel implementa i segmenti di memoria
 %% condivisa; uno schema semplificato della struttura è illustrato in
-%% \figref{fig:ipc_shm_struct}. 
+%% fig.~\ref{fig:ipc_shm_struct}. 
 
 %% \begin{figure}[htb]
 %%   \centering
@@ -2982,7 +3001,7 @@ key        msqid      owner      perms      used-bytes   messages
 \section{Tecniche alternative}
 \label{sec:ipc_alternatives}
 
-Come abbiamo detto in \secref{sec:ipc_sysv_generic}, e ripreso nella
+Come abbiamo detto in sez.~\ref{sec:ipc_sysv_generic}, e ripreso nella
 descrizione dei singoli oggetti che ne fan parte, il \textit{SysV IPC}
 presenta numerosi problemi; in \cite{APUE}\footnote{in particolare nel
   capitolo 14.}  Stevens ne effettua una accurata analisi (alcuni dei concetti
@@ -2996,24 +3015,25 @@ alternative, che vogliamo riprendere in questa sezione.
 Le code di messaggi sono probabilmente il meno usato degli oggetti del
 \textit{SysV IPC}; esse infatti nacquero principalmente come meccanismo di
 comunicazione bidirezionale quando ancora le pipe erano unidirezionali; con la
-disponibilità di \func{socketpair} (vedi \secref{sec:ipc_socketpair}) o
+disponibilità di \func{socketpair} (vedi sez.~\ref{sec:ipc_socketpair}) o
 utilizzando una coppia di pipe, si può ottenere questo risultato senza
 incorrere nelle complicazioni introdotte dal \textit{SysV IPC}.
 
 In realtà, grazie alla presenza del campo \var{mtype}, le code di messaggi
 hanno delle caratteristiche ulteriori, consentendo una classificazione dei
 messaggi ed un accesso non rigidamente sequenziale; due caratteristiche che
-sono impossibili da ottenere con le pipe e i socket\index{socket} di
-\func{socketpair}.  A queste esigenze però si può comunque ovviare in maniera
-diversa con un uso combinato della memoria condivisa e dei meccanismi di
-sincronizzazione, per cui alla fine l'uso delle code di messaggi classiche è
-relativamente poco diffuso.
+sono impossibili da ottenere con le pipe e i socket di \func{socketpair}.  A
+queste esigenze però si può comunque ovviare in maniera diversa con un uso
+combinato della memoria condivisa e dei meccanismi di sincronizzazione, per
+cui alla fine l'uso delle code di messaggi classiche è relativamente poco
+diffuso.
 
 \subsection{I \textsl{file di lock}}
 \label{sec:ipc_file_lock}
 
 \index{file!di lock|(}
-Come illustrato in \secref{sec:ipc_sysv_sem} i semafori del \textit{SysV IPC}
+
+Come illustrato in sez.~\ref{sec:ipc_sysv_sem} i semafori del \textit{SysV IPC}
 presentano una interfaccia inutilmente complessa e con alcuni difetti
 strutturali, per questo quando si ha una semplice esigenza di sincronizzazione
 per la quale basterebbe un semaforo binario (quello che abbiamo definito come
@@ -3025,20 +3045,20 @@ La prima possibilit
 dei \textsl{file di lock} (per i quali esiste anche una opportuna directory,
 \file{/var/lock}, nel filesystem standard). Per questo si usa la
 caratteristica della funzione \func{open} (illustrata in
-\secref{sec:file_open}) che prevede\footnote{questo è quanto dettato dallo
+sez.~\ref{sec:file_open}) che prevede\footnote{questo è quanto dettato dallo
   standard POSIX.1, ciò non toglie che in alcune implementazioni questa
   tecnica possa non funzionare; in particolare per Linux, nel caso di NFS, si
-  è comunque soggetti alla possibilità di una race   
-  condition\index{race condition}.} che essa ritorni un errore quando usata
-con i flag di \const{O\_CREAT} e \const{O\_EXCL}. In tal modo la creazione di
-un \textsl{file di lock} può essere eseguita atomicamente, il processo che
-crea il file con successo si può considerare come titolare del lock (e della
+  è comunque soggetti alla possibilità di una \itindex{race~condition}
+  \textit{race condition}.} che essa ritorni un errore quando usata con i
+flag di \const{O\_CREAT} e \const{O\_EXCL}. In tal modo la creazione di un
+\textsl{file di lock} può essere eseguita atomicamente, il processo che crea
+il file con successo si può considerare come titolare del lock (e della
 risorsa ad esso associata) mentre il rilascio si può eseguire con una chiamata
 ad \func{unlink}.
 
 Un esempio dell'uso di questa funzione è mostrato dalle funzioni
-\func{LockFile} ed \func{UnlockFile} riportate in \figref{fig:ipc_file_lock}
-(sono contenute in \file{LockFile.c}, un'altro dei sorgenti allegati alla
+\func{LockFile} ed \func{UnlockFile} riportate in fig.~\ref{fig:ipc_file_lock}
+(sono contenute in \file{LockFile.c}, un altro dei sorgenti allegati alla
 guida) che permettono rispettivamente di creare e rimuovere un \textsl{file di
   lock}. Come si può notare entrambe le funzioni sono elementari; la prima
 (\texttt{\small 4--10}) si limita ad aprire il file di lock (\texttt{\small
@@ -3057,48 +3077,50 @@ cancella con \func{unlink}.
 \end{figure}
 
 Uno dei limiti di questa tecnica è che, come abbiamo già accennato in
-\secref{sec:file_open}, questo comportamento di \func{open} può non funzionare
-(la funzione viene eseguita, ma non è garantita l'atomicità dell'operazione)
-se il filesystem su cui si va ad operare è su NFS; in tal caso si può adottare
-una tecnica alternativa che prevede l'uso della \func{link} per creare come
-\textsl{file di lock} un hard link ad un file esistente; se il link esiste già
-e la funzione fallisce, significa che la risorsa è bloccata e potrà essere
-sbloccata solo con un \func{unlink}, altrimenti il link è creato ed il lock
-acquisito; il controllo e l'eventuale acquisizione sono atomici; la soluzione
-funziona anche su NFS, ma ha un'altro difetto è che è quello di poterla usare
-solo se si opera all'interno di uno stesso filesystem.
-
-Un generale comunque l'uso di un \textsl{file di lock} presenta parecchi
-problemi, che non lo rendono una alternativa praticabile per la
+sez.~\ref{sec:file_open}, questo comportamento di \func{open} può non
+funzionare (la funzione viene eseguita, ma non è garantita l'atomicità
+dell'operazione) se il filesystem su cui si va ad operare è su NFS; in tal
+caso si può adottare una tecnica alternativa che prevede l'uso della
+\func{link} per creare come \textsl{file di lock} un hard link ad un file
+esistente; se il link esiste già e la funzione fallisce, significa che la
+risorsa è bloccata e potrà essere sbloccata solo con un \func{unlink},
+altrimenti il link è creato ed il lock acquisito; il controllo e l'eventuale
+acquisizione sono atomici; la soluzione funziona anche su NFS, ma ha un altro
+difetto è che è quello di poterla usare solo se si opera all'interno di uno
+stesso filesystem.
+
+In generale comunque l'uso di un \textsl{file di lock} presenta parecchi
+problemi che non lo rendono una alternativa praticabile per la
 sincronizzazione: anzitutto in caso di terminazione imprevista del processo,
 si lascia allocata la risorsa (il \textsl{file di lock}) e questa deve essere
 sempre cancellata esplicitamente.  Inoltre il controllo della disponibilità
-può essere eseguito solo con una tecnica di \textit{polling}\index{polling},
-ed è quindi molto inefficiente.
+può essere eseguito solo con una tecnica di \itindex{polling}
+\textit{polling}, ed è quindi molto inefficiente.
 
 La tecnica dei file di lock ha comunque una sua utilità, e può essere usata
 con successo quando l'esigenza è solo quella di segnalare l'occupazione di una
 risorsa, senza necessità di attendere che questa si liberi; ad esempio la si
 usa spesso per evitare interferenze sull'uso delle porte seriali da parte di
 più programmi: qualora si trovi un file di lock il programma che cerca di
-accedere alla seriale si limita a segnalare che la risorsa non è
-disponibile.\index{file!di lock|)}
+accedere alla seriale si limita a segnalare che la risorsa non è disponibile.
+
+\index{file!di lock|)}
 
 
 \subsection{La sincronizzazione con il \textit{file locking}}
 \label{sec:ipc_lock_file}
 
-Dato che i file di lock\index{file!di lock} presentano gli inconvenienti
+Dato che i \index{file!di lock} file di lock presentano gli inconvenienti
 illustrati in precedenza, la tecnica alternativa di sincronizzazione più
-comune è quella di fare ricorso al \textit{file locking}\index{file!locking}
-(trattato in \secref{sec:file_locking}) usando \func{fcntl} su un file creato
-per l'occasione per ottenere un write lock. In questo modo potremo usare il
-lock come un \textit{mutex}: per bloccare la risorsa basterà acquisire il
-lock, per sbloccarla basterà rilasciare il lock. Una richiesta fatta con un
-write lock metterà automaticamente il processo in stato di attesa, senza
-necessità di ricorrere al \textit{polling}\index{polling} per determinare la
-disponibilità della risorsa, e al rilascio della stessa da parte del processo
-che la occupava si otterrà il nuovo lock atomicamente.
+comune è quella di fare ricorso al \index{file!locking} \textit{file locking}
+(trattato in sez.~\ref{sec:file_locking}) usando \func{fcntl} su un file
+creato per l'occasione per ottenere un write lock. In questo modo potremo
+usare il lock come un \textit{mutex}: per bloccare la risorsa basterà
+acquisire il lock, per sbloccarla basterà rilasciare il lock. Una richiesta
+fatta con un write lock metterà automaticamente il processo in stato di
+attesa, senza necessità di ricorrere al \itindex{polling} \textit{polling} per
+determinare la disponibilità della risorsa, e al rilascio della stessa da
+parte del processo che la occupava si otterrà il nuovo lock atomicamente.
 
 Questo approccio presenta il notevole vantaggio che alla terminazione di un
 processo tutti i lock acquisiti vengono rilasciati automaticamente (alla
@@ -3114,30 +3136,31 @@ leggermente pi
   \end{minipage} 
   \normalsize 
   \caption{Il codice delle funzioni che permettono per la gestione dei 
-    \textit{mutex} con il file locking\index{file!locking}.}
+    \textit{mutex} con il \index{file!locking} \textit{file locking}.}
   \label{fig:ipc_flock_mutex}
 \end{figure}
 
 Il codice delle varie funzioni usate per implementare un mutex utilizzando il
-file locking\index{file!locking} è riportato in \figref{fig:ipc_flock_mutex};
-si è mantenuta volutamente una struttura analoga alle precedenti funzioni che
-usano i semafori, anche se le due interfacce non possono essere completamente
-equivalenti, specie per quanto riguarda la rimozione del mutex.
+\textit{file locking} \index{file!locking} è riportato in
+fig.~\ref{fig:ipc_flock_mutex}; si è mantenuta volutamente una struttura
+analoga alle precedenti funzioni che usano i semafori, anche se le due
+interfacce non possono essere completamente equivalenti, specie per quanto
+riguarda la rimozione del mutex.
 
 La prima funzione (\texttt{\small 1--5}) è \func{CreateMutex}, e serve a
 creare il mutex; la funzione è estremamente semplice, e si limita
 (\texttt{\small 4}) a creare, con una opportuna chiamata ad \func{open}, il
-file che sarà usato per il successivo file locking, assicurandosi che non
-esista già (nel qual caso segnala un errore); poi restituisce il file
+file che sarà usato per il successivo \textit{file locking}, assicurandosi che
+non esista già (nel qual caso segnala un errore); poi restituisce il file
 descriptor che sarà usato dalle altre funzioni per acquisire e rilasciare il
 mutex.
 
 La seconda funzione (\texttt{\small 6--10}) è \func{FindMutex}, che, come la
 precedente, è stata definita per mantenere una analogia con la corrispondente
 funzione basata sui semafori. Anch'essa si limita (\texttt{\small 9}) ad
-aprire il file da usare per il file locking, solo che in questo caso le
-opzioni di \func{open} sono tali che il file in questione deve esistere di
-già.
+aprire il file da usare per il \index{file!locking} \textit{file locking},
+solo che in questo caso le opzioni di \func{open} sono tali che il file in
+questione deve esistere di già.
 
 La terza funzione (\texttt{\small 11--22}) è \func{LockMutex} e serve per
 acquisire il mutex. La funzione definisce (\texttt{\small 14}) e inizializza
@@ -3146,15 +3169,16 @@ write lock sul file, che poi (\texttt{\small 21}) viene richiesto con
 \func{fcntl}, restituendo il valore di ritorno di quest'ultima. Se il file è
 libero il lock viene acquisito e la funzione ritorna immediatamente;
 altrimenti \func{fcntl} si bloccherà (si noti che la si è chiamata con
-\func{F\_SETLKW}) fino al rilascio del lock.
+\const{F\_SETLKW}) fino al rilascio del lock.
 
 La quarta funzione (\texttt{\small 24--34}) è \func{UnlockMutex} e serve a
 rilasciare il mutex. La funzione è analoga alla precedente, solo che in questo
 caso si inizializza (\texttt{\small 28--31}) la struttura \var{lock} per il
 rilascio del lock, che viene effettuato (\texttt{\small 33}) con la opportuna
-chiamata a \func{fcntl}. Avendo usato il file locking in semantica POSIX (si
-riveda quanto detto \secref{sec:file_posix_lock}) solo il processo che ha
-precedentemente eseguito il lock può sbloccare il mutex.
+chiamata a \func{fcntl}. Avendo usato il \index{file!locking} \textit{file
+  locking} in semantica POSIX (si riveda quanto detto
+sez.~\ref{sec:file_posix_lock}) solo il processo che ha precedentemente
+eseguito il lock può sbloccare il mutex.
 
 La quinta funzione (\texttt{\small 36--39}) è \func{RemoveMutex} e serve a
 cancellare il mutex. Anche questa funzione è stata definita per mantenere una
@@ -3183,8 +3207,8 @@ successo, ad indicare che il mutex 
 
 Basandosi sulla semantica dei file lock POSIX valgono tutte le considerazioni
 relative al comportamento di questi ultimi fatte in
-\secref{sec:file_posix_lock}; questo significa ad esempio che, al contrario di
-quanto avveniva con l'interfaccia basata sui semafori, chiamate multiple a
+sez.~\ref{sec:file_posix_lock}; questo significa ad esempio che, al contrario
+di quanto avveniva con l'interfaccia basata sui semafori, chiamate multiple a
 \func{UnlockMutex} o \func{LockMutex} non si cumulano e non danno perciò
 nessun inconveniente.
 
@@ -3192,13 +3216,14 @@ nessun inconveniente.
 \subsection{Il \textit{memory mapping} anonimo}
 \label{sec:ipc_mmap_anonymous}
 
+\itindbeg{memory~mapping}
 Abbiamo già visto che quando i processi sono \textsl{correlati}\footnote{se
   cioè hanno almeno un progenitore comune.} l'uso delle pipe può costituire
 una valida alternativa alle code di messaggi; nella stessa situazione si può
 evitare l'uso di una memoria condivisa facendo ricorso al cosiddetto
 \textit{memory mapping} anonimo.
 
-In \secref{sec:file_memory_map} abbiamo visto come sia possibile mappare il
+In sez.~\ref{sec:file_memory_map} abbiamo visto come sia possibile mappare il
 contenuto di un file nella memoria di un processo, e che, quando viene usato
 il flag \const{MAP\_SHARED}, le modifiche effettuate al contenuto del file
 vengono viste da tutti i processi che lo hanno mappato. Utilizzare questa
@@ -3219,15 +3244,16 @@ il \textit{memory mapping} anonimo.\footnote{nei sistemi derivati da SysV una
   restano in memoria e possono essere riletti secondo le stesse modalità usate
   nel \textit{memory mapping} anonimo.} Vedremo come utilizzare questa tecnica
 più avanti, quando realizzeremo una nuova versione del monitor visto in
-\secref{sec:ipc_sysv_shm} che possa restituisca i risultati via rete.
+sez.~\ref{sec:ipc_sysv_shm} che possa restituisca i risultati via rete.
+\itindend{memory~mapping}
 
+% TODO fare esempio di mmap anonima
 
-
-\section{La comunicazione fra processi di POSIX}
+\section{Il sistema di comunicazione fra processi di POSIX}
 \label{sec:ipc_posix}
 
 Per superare i numerosi problemi del \textit{SysV IPC}, evidenziati per i suoi
-aspetti generali in coda a \secref{sec:ipc_sysv_generic} e per i singoli
+aspetti generali in coda a sez.~\ref{sec:ipc_sysv_generic} e per i singoli
 oggetti nei paragrafi successivi, lo standard POSIX.1b ha introdotto dei nuovi
 meccanismi di comunicazione, che vanno sotto il nome di POSIX IPC, definendo
 una interfaccia completamente nuova, che tratteremo in questa sezione.
@@ -3236,103 +3262,100 @@ una interfaccia completamente nuova, che tratteremo in questa sezione.
 \subsection{Considerazioni generali}
 \label{sec:ipc_posix_generic}
 
-In Linux non tutti gli oggetti del POSIX IPC sono pienamente supportati nel
-kernel ufficiale; solo la memoria condivisa è presente con l'interfaccia
-completa, ma solo a partire dal kernel 2.4.x, i semafori sono forniti dalle
-\acr{glibc} nella sezione che implementa i thread POSIX, le code di messaggi
-non hanno alcun tipo di supporto ufficiale.  Per queste ultime esistono
-tuttavia dei patch e una libreria aggiuntiva.
+Oggi Linux supporta tutti gli oggetti definito nello standard POSIX per l'IPC,
+ma a lungo non è stato così; la memoria condivisa è presente a partire dal
+kernel 2.4.x, i semafori sono forniti dalle \acr{glibc} nella sezione che
+implementa i \itindex{thread} \textit{thread} POSIX di nuova generazione che
+richiedono il kernel 2.6, le code di messaggi sono supportate a partire dal
+kernel 2.6.6.
 
 La caratteristica fondamentale dell'interfaccia POSIX è l'abbandono dell'uso
 degli identificatori e delle chiavi visti nel SysV IPC, per passare ai
-\textit{Posix IPC names}\index{Posix IPC names}, che sono sostanzialmente
+\itindex{POSIX~IPC~names} \textit{POSIX IPC names}, che sono sostanzialmente
 equivalenti ai nomi dei file. Tutte le funzioni che creano un oggetto di IPC
-Posix prendono come primo argomento una stringa che indica uno di questi nomi;
+POSIX prendono come primo argomento una stringa che indica uno di questi nomi;
 lo standard è molto generico riguardo l'implementazione, ed i nomi stessi
 possono avere o meno una corrispondenza sul filesystem; tutto quello che è
 richiesto è che:
-\begin{itemize}
+\begin{itemize*}
 \item i nomi devono essere conformi alle regole che caratterizzano i
-  \textit{pathname}, in particolare non essere più lunghi di \const{PATH\_MAX}
-  byte e terminati da un carattere nullo.
+  \itindex{pathname} \textit{pathname}, in particolare non essere più lunghi di
+  \const{PATH\_MAX} byte e terminati da un carattere nullo.
 \item se il nome inizia per una \texttt{/} chiamate differenti allo stesso
   nome fanno riferimento allo stesso oggetto, altrimenti l'interpretazione del
   nome dipende dall'implementazione.
 \item l'interpretazione di ulteriori \texttt{/} presenti nel nome dipende
   dall'implementazione.
-\end{itemize}
+\end{itemize*}
 
 Data la assoluta genericità delle specifiche, il comportamento delle funzioni
-è pertanto subordinato in maniera quasi completa alla relativa
+è subordinato in maniera quasi completa alla relativa
 implementazione.\footnote{tanto che Stevens in \cite{UNP2} cita questo caso
   come un esempio della maniera standard usata dallo standard POSIX per
   consentire implementazioni non standardizzabili.} Nel caso di Linux, sia per
-quanto riguarda la memoria condivisa, che per quanto riguarda le code di
-messaggi, tutto viene creato usando come radici delle opportune directory
-(rispettivamente \file{/dev/shm} e \file{/dev/mqueue}, per i dettagli si
-faccia riferimento a \secref{sec:ipc_posix_shm} e \secref{sec:ipc_posix_mq})
-ed i nomi specificati nelle relative funzioni sono considerati come un
-pathname assoluto (comprendente eventuali sottodirectory) rispetto a queste
-radici. 
+quanto riguarda la memoria condivisa ed i semafori, che per quanto riguarda le
+code di messaggi, tutto viene creato usando come radici delle opportune
+directory (rispettivamente \file{/dev/shm} e \file{/dev/mqueue}, per i
+dettagli si faccia riferimento a sez.~\ref{sec:ipc_posix_shm},
+sez.~\ref{sec:ipc_posix_sem} e sez.~\ref{sec:ipc_posix_mq}) ed i nomi
+specificati nelle relative funzioni sono considerati come un
+\itindsub{pathname}{assoluto} \textit{pathname} assoluto (comprendente
+eventuali sottodirectory) rispetto a queste radici.
 
 Il vantaggio degli oggetti di IPC POSIX è comunque che essi vengono inseriti
 nell'albero dei file, e possono essere maneggiati con le usuali funzioni e
-comandi di accesso ai file,\footnote{questo è ancora più vero nel caso di
-  Linux, che usa una implementazione che lo consente, non è detto che
-  altrettanto valga per altri kernel. In particolare sia la memoria condivisa
-  che per le code di messaggi, come si può facilmente evincere con uno
-  \cmd{strace}, le system call utilizzate sono le stesse, in quanto esse sono
-  realizzate con dei file in speciali filesystem.}  che funzionano come su dei
-file normali.
+comandi di accesso ai file,\footnote{questo è vero nel caso di Linux, che usa
+  una implementazione che lo consente, non è detto che altrettanto valga per
+  altri kernel; in particolare, come si può facilmente verificare con uno
+  \cmd{strace}, sia per la memoria condivisa che per le code di messaggi le
+  system call utilizzate da Linux sono le stesse di quelle dei file, essendo
+  detti oggetti realizzati come tali in appositi filesystem.}  che funzionano
+come su dei file normali.
 
 In particolare i permessi associati agli oggetti di IPC POSIX sono identici ai
-permessi dei file, e il controllo di accesso segue esattamente la stessa
-semantica (quella illustrata in \secref{sec:file_access_control}), invece di
+permessi dei file, ed il controllo di accesso segue esattamente la stessa
+semantica (quella illustrata in sez.~\ref{sec:file_access_control}), e non
 quella particolare (si ricordi quanto visto in
-\secref{sec:ipc_sysv_access_control}) usata per gli oggetti del SysV IPC. Per
-quanto riguarda l'attribuzione dell'utente e del gruppo proprietari
-dell'oggetto alla creazione di quest'ultimo essa viene effettuata secondo la
-semantica SysV (essi corrispondono cioè a userid e groupid effettivi del
-processo che esegue la creazione).
-
+sez.~\ref{sec:ipc_sysv_access_control}) che viene usata per gli oggetti del
+SysV IPC.  Per quanto riguarda l'attribuzione dell'utente e del gruppo
+proprietari dell'oggetto alla creazione di quest'ultimo essa viene effettuata
+secondo la semantica SysV: corrispondono cioè a user-ID e group-ID effettivi
+del processo che esegue la creazione.
 
 
 \subsection{Code di messaggi}
 \label{sec:ipc_posix_mq}
 
-Le code di messaggi non sono ancora supportate nel kernel ufficiale, esiste
-però una implementazione sperimentale di Michal Wronski e Krzysztof
-Benedyczak,\footnote{i patch al kernel e la relativa libreria possono essere
-  trovati su \href{http://www.mat.uni.torun.pl/~wrona/posix_ipc}
-  {http://www.mat.uni.torun.pl/\tild{}wrona/posix\_ipc}, questi sono stati
-  inseriti nel kernel ufficiale a partire dalla versione 2.6.6-rc1.}.  In
+Le code di messaggi POSIX sono supportate da Linux a partire dalla versione
+2.6.6-rc1 del kernel,\footnote{l'implementazione è dovuta a Michal Wronski e
+  Krzysztof Benedyczak, e le relative informazioni si possono trovare su
+  \href{http://www.geocities.com/wronski12/posix_ipc/index.html}
+  {\textsf{http://www.geocities.com/wronski12/posix\_ipc/index.html}}.} In
 generale, come le corrispettive del SysV IPC, le code di messaggi sono poco
-usate, dato che i socket\index{socket}, nei casi in cui sono sufficienti, sono
-più comodi, e che in casi più complessi la comunicazione può essere gestita
-direttamente con mutex e memoria condivisa con tutta la flessibilità che
-occorre.
-
-Per poter utilizzare le code di messaggi, oltre ad utilizzare un kernel cui
-siano stati opportunamente applicati i relativi patch, occorre utilizzare la
-libreria \file{mqueue}\footnote{i programmi che usano le code di messaggi cioè
-  devono essere compilati aggiungendo l'opzione \code{-lmqueue} al comando
-  \cmd{gcc}, dato che le funzioni non fanno parte della libreria standard, in
-  corrispondenza all'inclusione del supporto nel kernel ufficiale, anche le
-  relative funzioni sono state inserite nelle \acr{glibc} a partire dalla
-  versione 2.3.4.}  che contiene le funzioni dell'interfaccia
+usate, dato che i socket, nei casi in cui sono sufficienti, sono più comodi, e
+che in casi più complessi la comunicazione può essere gestita direttamente con
+mutex (o semafori) e memoria condivisa con tutta la flessibilità che occorre.
+
+Per poter utilizzare le code di messaggi, oltre ad utilizzare un kernel
+superiore al 2.6.6 (o precedente, se sono stati opportunamente applicati i
+relativi patch) occorre utilizzare la libreria \file{libmqueue}\footnote{i
+  programmi che usano le code di messaggi cioè devono essere compilati
+  aggiungendo l'opzione \code{-lmqueue} al comando \cmd{gcc}; in
+  corrispondenza all'inclusione del supporto nel kernel ufficiale anche
+  \file{libmqueue} è stata inserita nelle \acr{glibc}, a partire dalla
+  versione 2.3.4 delle medesime.} che contiene le funzioni dell'interfaccia
 POSIX.\footnote{in realtà l'implementazione è realizzata tramite delle
-  speciali chiamate ad \func{ioctl} sui file del filesystem speciale su cui
+  opportune chiamate ad \func{ioctl} sui file del filesystem speciale su cui
   vengono mantenuti questi oggetti di IPC.}
 
-
 La libreria inoltre richiede la presenza dell'apposito filesystem di tipo
 \texttt{mqueue} montato su \file{/dev/mqueue}; questo può essere fatto
-aggiungendo ad \file{/etc/fstab} una riga come:
+aggiungendo ad \conffile{/etc/fstab} una riga come:
 \begin{verbatim}
 mqueue   /dev/mqueue       mqueue    defaults        0      0
 \end{verbatim}
 ed esso sarà utilizzato come radice sulla quale vengono risolti i nomi delle
-code di messaggi che iniziano con una \texttt{/}. Le opzioni di mount
+code di messaggi che iniziano con una ``\texttt{/}''. Le opzioni di mount
 accettate sono \texttt{uid}, \texttt{gid} e \texttt{mode} che permettono
 rispettivamente di impostare l'utente, il gruppo ed i permessi associati al
 filesystem.
@@ -3351,37 +3374,42 @@ di messaggi POSIX 
   Apre una coda di messaggi POSIX impostandone le caratteristiche.
   
   \bodydesc{La funzione restituisce il descrittore associato alla coda in caso
-    di successo e -1 in caso di errore; nel quel caso \var{errno} assumerà i
+    di successo e -1 per un errore; nel quel caso \var{errno} assumerà i
     valori:
     \begin{errlist}
-    \item[\errcode{EACCESS}] Il processo non ha i privilegi per accedere al
+    \item[\errcode{EACCES}] il processo non ha i privilegi per accedere al
       alla memoria secondo quanto specificato da \param{oflag}.
-    \item[\errcode{EEXIST}] Si è specificato \const{O\_CREAT} e
+    \item[\errcode{EEXIST}] si è specificato \const{O\_CREAT} e
       \const{O\_EXCL} ma la coda già esiste.
-    \item[\errcode{EINTR}] La funzione è stata interrotta da un segnale.
-    \item[\errcode{EINVAL}] Il file non supporta la funzione, o si è
+    \item[\errcode{EINVAL}] il file non supporta la funzione, o si è
       specificato \const{O\_CREAT} con una valore non nullo di \param{attr} e
       valori non validi di \var{mq\_maxmsg} e \var{mq\_msgsize}.
-    \item[\errcode{ENOENT}] Non si è specificato \const{O\_CREAT} ma la coda
+    \item[\errcode{ENOENT}] non si è specificato \const{O\_CREAT} ma la coda
       non esiste.
     \end{errlist}
     ed inoltre \errval{ENOMEM}, \errval{ENOSPC}, \errval{EFAULT},
-    \errval{EMFILE} ed \errval{ENFILE}.}
+    \errval{EMFILE}, \errval{EINTR} ed \errval{ENFILE}.
+}
 \end{functions}
 
 La funzione apre la coda di messaggi identificata dall'argomento \param{name}
 restituendo il descrittore ad essa associato, del tutto analogo ad un file
 descriptor, con l'unica differenza che lo standard prevede un apposito tipo
-\type{mqd\_t}.\footnote{nella implementazione citata questo è definito come
-  \ctyp{int}.} Se la coda esiste già il descrittore farà riferimento allo
-stesso oggetto, consentendo così la comunicazione fra due processi diversi.
+\type{mqd\_t}.\footnote{nel caso di Linux si tratta in effetti proprio di un
+  normale file descriptor; pertanto, anche se questo comportamento non è
+  portabile, lo si può tenere sotto osservazione con le funzioni dell'I/O
+  multiplexing (vedi sez.~\ref{sec:file_multiplexing}) come possibile
+  alternativa all'uso dell'interfaccia di notifica di \func{mq\_notify} (che
+  vedremo a breve).} Se la coda esiste già il descrittore farà riferimento
+allo stesso oggetto, consentendo così la comunicazione fra due processi
+diversi.
 
 La funzione è del tutto analoga ad \func{open} ed analoghi sono i valori che
 possono essere specificati per \param{oflag}, che deve essere specificato come
 maschera binaria; i valori possibili per i vari bit sono quelli visti in
-\tabref{tab:file_open_flags} dei quali però \func{mq\_open} riconosce solo i
+tab.~\ref{tab:file_open_flags} dei quali però \func{mq\_open} riconosce solo i
 seguenti:
-\begin{basedescript}{\desclabelwidth{2cm}\desclabelstyle{\nextlinelabel}}
+\begin{basedescript}{\desclabelwidth{2.2cm}\desclabelstyle{\nextlinelabel}}
 \item[\const{O\_RDONLY}] Apre la coda solo per la ricezione di messaggi. Il
   processo potrà usare il descrittore con \func{mq\_receive} ma non con
   \func{mq\_send}.
@@ -3409,13 +3437,14 @@ per i file normali.
 
 Se la coda non esiste e la si vuole creare si deve specificare
 \const{O\_CREAT}, in tal caso occorre anche specificare i permessi di
-creazione con l'argomento \param{mode}; i valori di quest'ultimo sono identici
-a quelli usati per \func{open}, anche se per le code di messaggi han senso
-solo i permessi di lettura e scrittura. Oltre ai permessi di creazione possono
-essere specificati anche gli attributi specifici della coda tramite
-l'argomento \param{attr}; quest'ultimo è un puntatore ad una apposita
-struttura \struct{mq\_attr}, la cui definizione è riportata in
-\figref{fig:ipc_mq_attr}.
+creazione con l'argomento \param{mode};\footnote{fino al 2.6.14 per un bug i
+  valori della \textit{umask} del processo non venivano applicati a questi
+  permessi.} i valori di quest'ultimo sono identici a quelli usati per
+\func{open}, anche se per le code di messaggi han senso solo i permessi di
+lettura e scrittura. Oltre ai permessi di creazione possono essere specificati
+anche gli attributi specifici della coda tramite l'argomento \param{attr};
+quest'ultimo è un puntatore ad una apposita struttura \struct{mq\_attr}, la
+cui definizione è riportata in fig.~\ref{fig:ipc_mq_attr}.
 
 \begin{figure}[!htb]
   \footnotesize \centering
@@ -3428,14 +3457,14 @@ struttura \struct{mq\_attr}, la cui definizione 
   \label{fig:ipc_mq_attr}
 \end{figure}
 
-Per ls creazione della coda i campi della struttura che devono essere
-specificati sono \var{mq\_msgsize} e \var{mq\_maxmsg}, che indicano
-rispettivamente la dimensione massima di un messaggio ed il numero massimo di
-messaggi che essa può contenere. Il valore dovrà essere positivo e minore dei
-rispettivi limiti di sistema \const{MQ\_MAXMSG} e \const{MQ\_MSGSIZE},
-altrimenti la funzione fallirà con un errore di \errcode{EINVAL}.  Qualora si
-specifichi per \param{attr} un puntatore nullo gli attributi della coda
-saranno impostati ai valori predefiniti.
+Per la creazione della coda i campi della struttura che devono essere
+specificati sono \var{mq\_maxmsg} e \var{mq\_msgsize}, che indicano
+rispettivamente il numero massimo di messaggi che può contenere e la
+dimensione massima di un messaggio. Il valore dovrà essere positivo e minore
+dei rispettivi limiti di sistema \const{MQ\_MAXMSG} e \const{MQ\_MSGSIZE},
+altrimenti la funzione fallirà con un errore di \errcode{EINVAL}.
+Se \param{attr} è un puntatore nullo gli attributi della coda saranno
+impostati ai valori predefiniti.
 
 Quando l'accesso alla coda non è più necessario si può chiudere il relativo
 descrittore con la funzione \funcd{mq\_close}, il cui prototipo è:
@@ -3444,8 +3473,8 @@ descrittore con la funzione \funcd{mq\_close}, il cui prototipo 
 
 Chiude la coda \param{mqdes}.
   
-\bodydesc{La funzione restituisce 0 in caso di successo e -1 in caso di
-  errore; nel quel caso \var{errno} assumerà i valori \errval{EBADF} o
+\bodydesc{La funzione restituisce 0 in caso di successo e -1 per un errore;
+  nel quel caso \var{errno} assumerà i valori \errval{EBADF} o
   \errval{EINTR}.}
 \end{prototype}
 
@@ -3474,7 +3503,7 @@ Rimuove una coda di messaggi.
 
 Anche in questo caso il comportamento della funzione è analogo a quello di
 \func{unlink} per i file,\footnote{di nuovo l'implementazione di Linux usa
-  direttamente \func{unlink}.} la funzione rimove la coda \param{name}, così
+  direttamente \func{unlink}.} la funzione rimuove la coda \param{name}, così
 che una successiva chiamata a \func{mq\_open} fallisce o crea una coda
 diversa. 
 
@@ -3485,15 +3514,13 @@ coda rester
 di essa.  Allo stesso modo una coda ed i suoi contenuti resteranno disponibili
 all'interno del sistema anche quando quest'ultima non è aperta da nessun
 processo (questa è una delle differenze più rilevanti nei confronti di pipe e
-fifo).
+fifo).  La sola differenza fra code di messaggi POSIX e file normali è che,
+essendo il filesystem delle code di messaggi virtuale e basato su oggetti
+interni al kernel, il suo contenuto viene perduto con il riavvio del sistema.
 
-La sola differenza fra code di messaggi POSIX e file normali è che, essendo il
-filesystem delle code di messaggi virtuale e basato su oggetti interni al
-kernel, il suo contenuto viene perduto con il riavvio del sistema.
-
-Come accennato in precedenza ad ogni coda di messaggi è associata una
-struttura \struct{mq\_attr}, che può essere letta e modificata attraverso le
-due funzioni \funcd{mq\_getattr} e \funcd{mq\_setattr}, i cui prototipi sono:
+Come accennato ad ogni coda di messaggi è associata una struttura
+\struct{mq\_attr}, che può essere letta e modificata attraverso le due
+funzioni \funcd{mq\_getattr} e \funcd{mq\_setattr}, i cui prototipi sono:
 \begin{functions}
   \headdecl{mqueue.h} 
   
@@ -3542,22 +3569,20 @@ Per inserire messaggi su di una coda sono previste due funzioni,
   \param{abs\_timeout}.
 
   
-  \bodydesc{Le funzioni restituiscono 0 in caso di successo e -1 in caso di
+  \bodydesc{Le funzioni restituiscono 0 in caso di successo e $-1$ per un
     errore; nel quel caso \var{errno} assumerà i valori:
     \begin{errlist}
-    \item[\errcode{EAGAIN}] Si è aperta la coda con \const{O\_NONBLOCK}, e la
+    \item[\errcode{EAGAIN}] si è aperta la coda con \const{O\_NONBLOCK}, e la
       coda è piena.
-    \item[\errcode{EMSGSIZE}] La lunghezza del messaggio \param{msg\_len}
+    \item[\errcode{EMSGSIZE}] la lunghezza del messaggio \param{msg\_len}
       eccede il limite impostato per la coda.
-    \item[\errcode{ENOMEM}] Il kernel non ha memoria sufficiente. Questo
-      errore può avvenire quando l'inserimento del messaggio
-    \item[\errcode{EINVAL}] Si è specificato un valore nullo per
+    \item[\errcode{EINVAL}] si è specificato un valore nullo per
       \param{msg\_len}, o un valore di \param{msg\_prio} fuori dai limiti, o
       un valore non valido per \param{abs\_timeout}.
-    \item[\errcode{ETIMEDOUT}] L'inserimento del messaggio non è stato
+    \item[\errcode{ETIMEDOUT}] l'inserimento del messaggio non è stato
       effettuato entro il tempo stabilito.
     \end{errlist}    
-    ed inoltre \errval{EBADF} ed \errval{EINTR}.}
+    ed inoltre \errval{EBADF}, \errval{ENOMEM} ed \errval{EINTR}.}
 \end{functions}
 
 Entrambe le funzioni richiedono un puntatore al testo del messaggio
@@ -3573,11 +3598,16 @@ valore della priorit
 \const{MQ\_PRIO\_MAX}, che nel caso è pari a 32768.
 
 Qualora la coda sia piena, entrambe le funzioni si bloccano, a meno che non
-sia stata selezionata in fase di apertura la modalità non bloccante, nel qual
-caso entrambe ritornano \errcode{EAGAIN}. La sola differenza fra le due
-funzioni è che la seconda, passato il tempo massimo impostato con l'argomento
-\param{abs\_timeout}, ritorna comunque con un errore di \errcode{ETIMEDOUT}.
-
+sia stata selezionata in fase di apertura la modalità non
+bloccante,\footnote{o si sia impostato il flag \const{O\_NONBLOCK} sul file
+  descriptor della coda.} nel qual caso entrambe ritornano \errcode{EAGAIN}.
+La sola differenza fra le due funzioni è che la seconda, passato il tempo
+massimo impostato con l'argomento \param{abs\_timeout},\footnote{deve essere
+  specificato un tempo assoluto tramite una struttura \struct{timespec} (vedi
+  fig.~\ref{fig:sys_timespec_struct}) indicato in numero di secondi e
+  nanosecondi a partire dal 1 gennaio 1970.} ritorna comunque con un errore di
+\errcode{ETIMEDOUT}, se invece il tempo è già scaduto al momento della
+chiamata e la coda è vuota la funzione ritorna immediatamente.
 
 Come per l'inserimento, anche per l'estrazione dei messaggi da una coda sono
 previste due funzioni, \funcd{mq\_receive} e \funcd{mq\_timedreceive}, i cui
@@ -3598,13 +3628,13 @@ prototipi sono:
     di successo e -1 in caso di errore; nel quel caso \var{errno} assumerà i
     valori:
     \begin{errlist}
-    \item[\errcode{EAGAIN}] Si è aperta la coda con \const{O\_NONBLOCK}, e la
+    \item[\errcode{EAGAIN}] si è aperta la coda con \const{O\_NONBLOCK}, e la
       coda è vuota.
-    \item[\errcode{EMSGSIZE}] La lunghezza del messaggio sulla coda eccede il
+    \item[\errcode{EMSGSIZE}] la lunghezza del messaggio sulla coda eccede il
       valore \param{msg\_len} specificato per la ricezione.
-    \item[\errcode{EINVAL}] Si è specificato un valore nullo per
+    \item[\errcode{EINVAL}] si è specificato un valore nullo per
       \param{msg\_ptr}, o un valore non valido per \param{abs\_timeout}.
-    \item[\errcode{ETIMEDOUT}] La ricezione del messaggio non è stata
+    \item[\errcode{ETIMEDOUT}] la ricezione del messaggio non è stata
       effettuata entro il tempo stabilito.
     \end{errlist}    
     ed inoltre \errval{EBADF}, \errval{EINTR}, \errval{ENOMEM}, o
@@ -3614,7 +3644,11 @@ prototipi sono:
 La funzione estrae dalla coda il messaggio a priorità più alta, o il più
 vecchio fra quelli della stessa priorità. Una volta ricevuto il messaggio
 viene tolto dalla coda e la sua dimensione viene restituita come valore di
-ritorno.
+ritorno.\footnote{si tenga presente che 0 è una dimensione valida e che la
+  condizione di errore è restituita dal valore -1; Stevens in \cite{UNP2} fa
+  notare che questo è uno dei casi in cui vale ciò che lo standard
+  \textsl{non} dice, una dimensione nulla infatti, pur non essendo citata, non
+  viene proibita.}
 
 Se la dimensione specificata da \param{msg\_len} non è sufficiente a contenere
 il messaggio, entrambe le funzioni, al contrario di quanto avveniva nelle code
@@ -3633,8 +3667,9 @@ Qualora non interessi usare la priorit
 Si noti che con le code di messaggi POSIX non si ha la possibilità di
 selezionare quale messaggio estrarre con delle condizioni sulla priorità, a
 differenza di quanto avveniva con le code di messaggi di SysV che permettono
-invece la selezione in base al valore del campo \var{mtype}. Qualora non
-interessi usare la priorità dei messaggi si
+invece la selezione in base al valore del campo \var{mtype}. 
+
+% TODO inserire i dati di /proc/sys/fs/mqueue 
 
 Qualora la coda sia vuota entrambe le funzioni si bloccano, a meno che non si
 sia selezionata la modalità non bloccante; in tal caso entrambe ritornano
@@ -3663,8 +3698,8 @@ Attiva il meccanismo di notifica per la coda \param{mqdes}.
 \bodydesc{La funzione restituisce 0 in caso di successo e -1 in caso di
   errore; nel quel caso \var{errno} assumerà i valori: 
     \begin{errlist}
-    \item[\errcode{EBUSY}] C'è già un processo registrato per la notifica.
-    \item[\errcode{EBADF}] Il descrittore non fa riferimento ad una coda di
+    \item[\errcode{EBUSY}] c'è già un processo registrato per la notifica.
+    \item[\errcode{EBADF}] il descrittore non fa riferimento ad una coda di
       messaggi.
     \end{errlist}}
 \end{prototype}
@@ -3677,32 +3712,36 @@ processo alla volta per ciascuna coda.
 
 Il comportamento di \func{mq\_notify} dipende dal valore dell'argomento
 \param{notification}, che è un puntatore ad una apposita struttura
-\struct{sigevent}, (definita in \figref{fig:file_sigevent}) introdotta dallo
-standard POSIX.1b per gestire la notifica di eventi; per altri dettagli si può
-vedere quanto detto in \secref{sec:file_asyncronous_io} a proposito dell'uso
-della stessa struttura per l'invio dei segnali usati per l'I/O asincrono.
+\struct{sigevent}, (definita in fig.~\ref{fig:struct_sigevent}) introdotta
+dallo standard POSIX.1b per gestire la notifica di eventi; per altri dettagli
+si può vedere quanto detto in sez.~\ref{sec:sig_timer_adv} a proposito
+dell'uso della stessa struttura per la notifica delle scadenze dei
+\textit{timer}.
 
 Attraverso questa struttura si possono impostare le modalità con cui viene
-effettuata la notifica; in particolare il campo \var{sigev\_notify} deve
-essere posto a \const{SIGEV\_SIGNAL}\footnote{il meccanismo di notifica basato
-  sui thread, specificato tramite il valore \const{SIGEV\_THREAD}, non è
-  implementato.} ed il campo \var{sigev\_signo} deve indicare il valore del
-segnale che sarà inviato al processo. Inoltre il campo \var{sigev\_value} è il
-puntatore ad una struttura \struct{sigval\_t} (definita in
-\figref{fig:sig_sigval}) che permette di restituire al gestore del segnale un
-valore numerico o un indirizzo,\footnote{per il suo uso si riveda la
-  trattazione fatta in \secref{sec:sig_real_time} a proposito dei segnali
-  real-time.} posto che questo sia installato nella forma estesa vista in
-\secref{sec:sig_sigaction}.
+effettuata la notifica nel campo \var{sigev\_notify}, che può assumere i
+valori di tab.~\ref{tab:sigevent_sigev_notify}.\footnote{la pagina di manuale
+  riporta soltanto i primi tre (inizialmente era possibile solo
+  \const{SIGEV\_SIGNAL}).} Il metodo consigliato è quello di usare
+\const{SIGEV\_SIGNAL} usando il campo \var{sigev\_signo} per indicare il quale
+segnale deve essere inviato al processo. Inoltre il campo \var{sigev\_value} è
+un puntatore ad una struttura \struct{sigval\_t} (definita in
+fig.~\ref{fig:sig_sigval}) che permette di restituire al gestore del segnale
+un valore numerico o un indirizzo,\footnote{per il suo uso si riveda la
+  trattazione fatta in sez.~\ref{sec:sig_real_time} a proposito dei segnali
+  \textit{real-time}.} posto che questo sia installato nella forma estesa
+vista in sez.~\ref{sec:sig_sigaction}.
 
 La funzione registra il processo chiamante per la notifica se
 \param{notification} punta ad una struttura \struct{sigevent} opportunamente
 inizializzata, o cancella una precedente registrazione se è \val{NULL}. Dato
 che un solo processo alla volta può essere registrato, la funzione fallisce
-con \errcode{EBUSY} se c'è un altro processo già registrato.  Si tenga
-presente inoltre che alla chiusura del descrittore associato alla coda (e
-quindi anche all'uscita del processo) ogni eventuale registrazione di notifica
-presente viene cancellata.
+con \errcode{EBUSY} se c'è un altro processo già registrato.\footnote{questo
+  significa anche che se si registra una notifica con \const{SIGEV\_NONE} il
+  processo non la riceverà, ma impedirà anche che altri possano registrarsi
+  per poterlo fare.}  Si tenga presente inoltre che alla chiusura del
+descrittore associato alla coda (e quindi anche all'uscita del processo) ogni
+eventuale registrazione di notifica presente viene cancellata.
 
 La notifica del segnale avviene all'arrivo di un messaggio in una coda vuota
 (cioè solo se sulla coda non ci sono messaggi) e se non c'è nessun processo
@@ -3719,77 +3758,43 @@ registrazione chiamando nuovamente \func{mq\_notify} all'interno del gestore
 del segnale di notifica. A differenza della situazione simile che si aveva con
 i segnali non affidabili,\footnote{l'argomento è stato affrontato in
   \ref{sec:sig_semantics}.} questa caratteristica non configura una
-race-condition perché l'invio di un segnale avviene solo se la coda è vuota;
-pertanto se si vuole evitare di correre il rischio di perdere eventuali
-ulteriori segnali inviati nel lasso di tempo che occorre per ripetere la
-richiesta di notifica basta avere cura di eseguire questa operazione prima di
-estrarre i messaggi presenti dalla coda.
+\itindex{race~condition} \textit{race condition} perché l'invio di un segnale
+avviene solo se la coda è vuota; pertanto se si vuole evitare di correre il
+rischio di perdere eventuali ulteriori segnali inviati nel lasso di tempo che
+occorre per ripetere la richiesta di notifica basta avere cura di eseguire
+questa operazione prima di estrarre i messaggi presenti dalla coda.
 
 L'invio del segnale di notifica avvalora alcuni campi di informazione
 restituiti al gestore attraverso la struttura \struct{siginfo\_t} (definita in
-\figref{fig:sig_siginfo_t}). In particolare \var{si\_pid} viene impostato al
+fig.~\ref{fig:sig_siginfo_t}). In particolare \var{si\_pid} viene impostato al
 valore del \acr{pid} del processo che ha emesso il segnale, \var{si\_uid}
 all'userid effettivo, \var{si\_code} a \const{SI\_MESGQ}, e \var{si\_errno} a
 0. Questo ci dice che, se si effettua la ricezione dei messaggi usando
 esclusivamente il meccanismo di notifica, è possibile ottenere le informazioni
 sul processo che ha inserito un messaggio usando un gestore per il segnale in
-forma estesa\footnote{di nuovo si faccia riferimento a quanto detto al
-  proposito in \secref{sec:sig_sigaction} e \secref{sec:sig_real_time}.}
-
-
-
-\subsection{Semafori}
-\label{sec:ipc_posix_sem}
-
-Dei semafori POSIX esistono sostanzialmente due implementazioni; una è fatta a
-livello di libreria ed è fornita dalla libreria dei thread; questa però li
-implementa solo a livello di thread e non di processi.\footnote{questo
-  significa che i semafori sono visibili solo all'interno dei thread creati da
-  un singolo processo, e non possono essere usati come meccanismo di
-  sincronizzazione fra processi diversi.} Esiste però anche una libreria
-realizzata da Konstantin Knizhnik, che reimplementa l'interfaccia POSIX usando
-i semafori di SysV IPC, e che non vale comunque la pena di usare visto che i
-problemi sottolineati in \secref{sec:ipc_sysv_sem} rimangono, anche se
-mascherati.
-
-In realtà a partire dal kernel 2.5.7 è stato introdotto un meccanismo di
-sincronizzazione completamente nuovo, basato sui cosiddetti
-\textit{futex}\footnote{la sigla sta per \textit{faxt user mode mutex}.}, con
-il quale dovrebbe essere possibile implementare una versione nativa dei
-semafori; esso è già stato usato con successo per reimplementare in maniera
-più efficiente tutte le direttive di sincronizzazione previste per i thread
-POSIX. L'interfaccia corrente è stata stabilizzata a partire dal kernel
-2.5.40.
-
+forma estesa.\footnote{di nuovo si faccia riferimento a quanto detto al
+  proposito in sez.~\ref{sec:sig_sigaction} e sez.~\ref{sec:sig_real_time}.}
 
 
 
 \subsection{Memoria condivisa}
 \label{sec:ipc_posix_shm}
 
-La memoria condivisa è l'unico degli oggetti di IPC POSIX già presente nel
-kernel ufficiale; in realtà il supporto a questo tipo di oggetti è realizzato
-attraverso il filesystem \texttt{tmpfs}, uno speciale filesystem che mantiene
-tutti i suoi contenuti in memoria,\footnote{il filesystem \texttt{tmpfs} è
-  diverso da un normale RAM disk, anch'esso disponibile attraverso il
-  filesystem \texttt{ramfs}, proprio perché realizza una interfaccia
-  utilizzabile anche per la memoria condivisa; esso infatti non ha dimensione
-  fissa, ed usa direttamente la cache interna del kernel (che viene usata
-  anche per la shared memory in stile SysV). In più i suoi contenuti, essendo
-  trattati direttamente dalla memoria virtuale\index{memoria virtuale} possono
-  essere salvati sullo swap automaticamente.} che viene attivato abilitando
-l'opzione \texttt{CONFIG\_TMPFS} in fase di compilazione del kernel.
-
-
-Per potere utilizzare l'interfaccia POSIX per le code di messaggi le
+La memoria condivisa è stato il primo degli oggetti di IPC POSIX inserito nel
+kernel ufficiale; il supporto a questo tipo di oggetti è realizzato attraverso
+il filesystem \texttt{tmpfs}, uno speciale filesystem che mantiene tutti i
+suoi contenuti in memoria, che viene attivato abilitando l'opzione
+\texttt{CONFIG\_TMPFS} in fase di compilazione del kernel.
+
+Per potere utilizzare l'interfaccia POSIX per la memoria condivisa le
 \acr{glibc}\footnote{le funzioni sono state introdotte con le glibc-2.2.}
 richiedono di compilare i programmi con l'opzione \code{-lrt}; inoltre è
 necessario che in \file{/dev/shm} sia montato un filesystem \texttt{tmpfs};
-questo di norma viene eseguita aggiungendo una riga tipo:
+questo di norma viene fatto aggiungendo una riga del tipo di:
 \begin{verbatim}
 tmpfs   /dev/shm        tmpfs   defaults        0      0
 \end{verbatim}
-ad \file{/etc/fstab}. In realtà si può montare un filesystem \texttt{tmpfs}
+ad \conffile{/etc/fstab}. In realtà si può montare un filesystem \texttt{tmpfs}
 dove si vuole, per usarlo come RAM disk, con un comando del tipo:
 \begin{verbatim}
 mount -t tmpfs -o size=128M,nr_inodes=10k,mode=700 tmpfs /mytmpfs
@@ -3804,31 +3809,36 @@ questo caso 
 La funzione che permette di aprire un segmento di memoria condivisa POSIX, ed
 eventualmente di crearlo se non esiste ancora, è \funcd{shm\_open}; il suo
 prototipo è:
-\begin{prototype}{mqueue.h}
-{int shm\_open(const char *name, int oflag, mode\_t mode)}
+\begin{functions}
+  \headdecl{sys/mman.h} 
+  \headdecl{sys/stat.h} 
+  \headdecl{fcntl.h} 
+
+  \funcdecl{int shm\_open(const char *name, int oflag, mode\_t mode)} 
 
-Apre un segmento di memoria condivisa.
+  Apre un segmento di memoria condivisa.
   
-\bodydesc{La funzione restituisce un file descriptor positivo in caso di
-  successo e -1 in caso di errore; nel quel caso \var{errno} assumerà gli
-  stessi valori riportati da \func{open}.}
-\end{prototype}
+  \bodydesc{La funzione restituisce un file descriptor positivo in caso di
+    successo e -1 in caso di errore; nel quel caso \var{errno} assumerà gli
+    stessi valori riportati da \func{open}.}
+\end{functions}
 
 La funzione apre un segmento di memoria condivisa identificato dal nome
-\param{name}. Come già spiegato in \secref{sec:ipc_posix_generic} questo nome
-può essere specificato in forma standard solo facendolo iniziare per \file{/}
-e senza ulteriori \file{/}, Linux supporta comunque nomi generici, che
-verranno intepretati prendendo come radice \file{/dev/shm}.\footnote{occorre
-  pertanto evitare di specificare qualcosa del tipo \file{/dev/shm/nome}
-  all'interno di \param{name}, perché questo comporta, da parte delle routine
-  di libereria, il tentativo di accedere a \file{/dev/shm/dev/shm/nome}.}
+\param{name}. Come già spiegato in sez.~\ref{sec:ipc_posix_generic} questo
+nome può essere specificato in forma standard solo facendolo iniziare per
+``\file{/}'' e senza ulteriori ``\file{/}''. Linux supporta comunque nomi
+generici, che verranno interpretati prendendo come radice
+\file{/dev/shm}.\footnote{occorre pertanto evitare di specificare qualcosa del
+  tipo \file{/dev/shm/nome} all'interno di \param{name}, perché questo
+  comporta, da parte delle funzioni di libreria, il tentativo di accedere a
+  \file{/dev/shm/dev/shm/nome}.}
 
 La funzione è del tutto analoga ad \func{open} ed analoghi sono i valori che
 possono essere specificati per \param{oflag}, che deve essere specificato come
 maschera binaria comprendente almeno uno dei due valori \const{O\_RDONLY} e
 \const{O\_RDWR}; i valori possibili per i vari bit sono quelli visti in
-\tabref{tab:file_open_flags} dei quali però \func{shm\_open} riconosce solo i
-seguenti:
+tab.~\ref{tab:file_open_flags} dei quali però \func{shm\_open} riconosce solo
+seguenti:
 \begin{basedescript}{\desclabelwidth{2.0cm}\desclabelstyle{\nextlinelabel}}
 \item[\const{O\_RDONLY}] Apre il file descriptor associato al segmento di
   memoria condivisa per l'accesso in sola lettura.
@@ -3849,26 +3859,25 @@ In caso di successo la funzione restituisce un file descriptor associato al
 segmento di memoria condiviso con le stesse modalità di
 \func{open}\footnote{in realtà, come accennato, \func{shm\_open} è un semplice
   wrapper per \func{open}, usare direttamente quest'ultima avrebbe lo stesso
-  effetto.}  viste in \secref{sec:file_open}; in particolare viene impostato
+  effetto.}  viste in sez.~\ref{sec:file_open}; in particolare viene impostato
 il flag \const{FD\_CLOEXEC}.  Chiamate effettuate da diversi processi usando
 lo stesso nome, restituiranno file descriptor associati allo stesso segmento
-(così come, nel caso di file di dati, essi sono associati allo stesso inode).
-In questo modo è possibile effettuare una chiamata ad \func{mmap} sul file
-descriptor restituito da \func{shm\_open} ed i processi vedranno lo stesso
-segmento di memoria condivisa.
+(così come, nel caso di file di dati, essi sono associati allo stesso
+\index{inode} inode).  In questo modo è possibile effettuare una chiamata ad
+\func{mmap} sul file descriptor restituito da \func{shm\_open} ed i processi
+vedranno lo stesso segmento di memoria condivisa.
 
 Quando il nome non esiste il segmento può essere creato specificando
 \const{O\_CREAT}; in tal caso il segmento avrà (così come i nuovi file)
 lunghezza nulla. Dato che un segmento di lunghezza nulla è di scarsa utilità,
 per impostarne la dimensione si deve usare \func{ftruncate} (vedi
-\secref{sec:file_file_size}), prima di mapparlo in memoria con \func{mmap}. Si
-tenga presente che una volta chiamata \func{mmap} si può chiudere il file
+sez.~\ref{sec:file_file_size}), prima di mapparlo in memoria con \func{mmap}.
+Si tenga presente che una volta chiamata \func{mmap} si può chiudere il file
 descriptor (con \func{close}), senza che la mappatura ne risenta.
 
-
 Come per i file, quando si vuole effettivamente rimuovere segmento di memoria
 condivisa, occorre usare la funzione \funcd{shm\_unlink}, il cui prototipo è:
-\begin{prototype}{mqueue.h}
+\begin{prototype}{sys/mman.h}
 {int shm\_unlink(const char *name)}
 
 Rimuove un segmento di memoria condivisa.
@@ -3901,8 +3910,8 @@ descriptor che fa riferimento ad un segmento distinto da eventuali precedenti.
 
 Come esempio per l'uso di queste funzioni vediamo come è possibile riscrivere
 una interfaccia semplificata analoga a quella vista in
-\secref{fig:ipc_sysv_shm_func} per la memoria condivisa in stile SysV. Il
-codice, riportato in \figref{fig:ipc_posix_shmmem}, è sempre contenuto nel
+fig.~\ref{fig:ipc_sysv_shm_func} per la memoria condivisa in stile SysV. Il
+codice, riportato in fig.~\ref{fig:ipc_posix_shmmem}, è sempre contenuto nel
 file \file{SharedMem.c} dei sorgenti allegati.
 
 La prima funzione (\texttt{\small 1--24}) è \func{CreateShm} che, dato un nome
@@ -3938,8 +3947,683 @@ cancellare un segmento di memoria condivisa. Dato che al contrario di quanto
 avveniva con i segmenti del SysV IPC gli oggetti allocati nel kernel vengono
 rilasciati automaticamente quando nessuna li usa più, tutto quello che c'è da
 fare (\texttt{\small 44}) in questo caso è chiamare \func{shm\_unlink},
-retituendo al chiamante il valore di ritorno.
+restituendo al chiamante il valore di ritorno.
+
+
+
+
+\subsection{Semafori}
+\label{sec:ipc_posix_sem}
+
+Fino alla serie 2.4.x del kernel esisteva solo una implementazione parziale
+dei semafori POSIX che li realizzava solo a livello di \itindex{thread}
+\textit{thread} e non di processi,\footnote{questo significava che i semafori
+  erano visibili solo all'interno dei \itindex{thread} \textit{thread} creati
+  da un singolo processo, e non potevano essere usati come meccanismo di
+  sincronizzazione fra processi diversi.} fornita attraverso la sezione delle
+estensioni \textit{real-time} delle \acr{glibc}.\footnote{quelle che si
+  accedono collegandosi alla libreria \texttt{librt}.} Esisteva inoltre una
+libreria che realizzava (parzialmente) l'interfaccia POSIX usando le funzioni
+dei semafori di SysV IPC (mantenendo così tutti i problemi sottolineati in
+sez.~\ref{sec:ipc_sysv_sem}).
+
+A partire dal kernel 2.5.7 è stato introdotto un meccanismo di
+sincronizzazione completamente nuovo, basato sui cosiddetti
+\textit{futex},\footnote{la sigla sta per \textit{fast user mode mutex}.} con
+il quale è stato possibile implementare una versione nativa dei semafori
+POSIX.  Grazie a questo con i kernel della serie 2.6 e le nuove versioni delle
+\acr{glibc} che usano questa nuova infrastruttura per quella che viene quella
+che viene chiamata \textit{New Posix Thread Library}, sono state implementate
+anche tutte le funzioni dell'interfaccia dei semafori POSIX.
+
+Anche in questo caso è necessario appoggiarsi alla libreria per le estensioni
+\textit{real-time} \texttt{librt}, questo significa che se si vuole utilizzare
+questa interfaccia, oltre ad utilizzare gli opportuni file di definizione,
+occorrerà compilare i programmi con l'opzione \texttt{-lrt}. 
+
+La funzione che permette di creare un nuovo semaforo POSIX, creando il
+relativo file, o di accedere ad uno esistente, è \funcd{sem\_open}, questa
+prevede due forme diverse a seconda che sia utilizzata per aprire un semaforo
+esistente o per crearne uno nuovi, i relativi prototipi sono:
+\begin{functions}
+  \headdecl{semaphore.h} 
+  
+  \funcdecl{sem\_t *sem\_open(const char *name, int oflag)}
+  
+  \funcdecl{sem\_t *sem\_open(const char *name, int oflag, mode\_t mode,
+    unsigned int value)} 
+
+  Crea un semaforo o ne apre uno esistente.
+  
+  \bodydesc{La funzione restituisce l'indirizzo del semaforo in caso di
+    successo e \const{SEM\_FAILED} in caso di errore; nel quel caso
+    \var{errno} assumerà i valori:
+    \begin{errlist}
+    \item[\errcode{EACCESS}] il semaforo esiste ma non si hanno permessi
+      sufficienti per accedervi.
+    \item[\errcode{EEXIST}] si sono specificati \const{O\_CREAT} e
+      \const{O\_EXCL} ma il semaforo esiste.
+    \item[\errcode{EINVAL}] il valore di \param{value} eccede
+      \const{SEM\_VALUE\_MAX}.
+    \item[\errcode{ENAMETOOLONG}] si è utilizzato un nome troppo lungo.
+    \item[\errcode{ENOENT}] non si è usato \const{O\_CREAT} ed il nome
+      specificato non esiste.
+    \end{errlist}    
+    ed inoltre \errval{ENFILE} ed \errval{ENOMEM}.}
+\end{functions}
+
+L'argomento \param{name} definisce il nome del semaforo che si vuole
+utilizzare, ed è quello che permette a processi diversi di accedere allo
+stesso semaforo. Questo deve essere specificato con un pathname nella forma
+\texttt{/qualchenome}, che non ha una corrispondenza diretta con un pathname
+reale; con Linux infatti i file associati ai semafori sono mantenuti nel
+filesystem virtuale \texttt{/dev/shm}, e gli viene assegnato automaticamente
+un nome nella forma \texttt{sem.qualchenome}.\footnote{si ha cioè una
+  corrispondenza per cui \texttt{/qualchenome} viene rimappato, nella
+  creazione tramite \func{sem\_open}, su \texttt{/dev/shm/sem.qualchenome}.}
+
+L'argomento \param{oflag} è quello che controlla le modalità con cui opera la
+funzione, ed è passato come maschera binaria; i bit corrispondono a quelli
+utilizzati per l'analogo argomento di \func{open}, anche se dei possibili
+valori visti in sez.~\ref{sec:file_open} sono utilizzati soltanto
+\const{O\_CREAT} e \const{O\_EXCL}.
+
+Se si usa \const{O\_CREAT} si richiede la creazione del semaforo qualora
+questo non esista, ed in tal caso occorre utilizzare la seconda forma della
+funzione, in cui si devono specificare sia un valore iniziale con l'argomento
+\param{value},\footnote{e si noti come così diventa possibile, differenza di
+  quanto avviene per i semafori del \textit{SysV IPC}, effettuare in maniera
+  atomica creazione ed inizializzazione di un semaforo usando una unica
+  funzione.} che una maschera dei permessi con l'argomento
+\param{mode};\footnote{anche questo argomento prende gli stessi valori
+  utilizzati per l'analogo di \func{open}, che si sono illustrati in dettaglio
+  sez.~\ref{sec:file_perm_overview}.} questi verranno assegnati al semaforo
+appena creato. Se il semaforo esiste già i suddetti valori saranno invece
+ignorati. Usando il flag \const{O\_EXCL} si richiede invece la verifica che il
+semaforo non esiste, usandolo insieme ad \const{O\_CREAT} la funzione fallisce
+qualora un semaforo con lo stesso nome sia già presente.
+
+La funzione restituisce in caso di successo un puntatore all'indirizzo del
+semaforo con un valore di tipo \ctyp{sem\_t *}, è questo valore che dovrà
+essere passato alle altre funzioni per operare sul semaforo stesso. Si tenga
+presente che, come accennato in sez.~\ref{sec:ipc_posix_generic}, i semafori
+usano la semantica standard dei file per quanto riguarda i controlli di
+accesso. 
+
+Questo significa che un nuovo semaforo viene sempre creato con l'user-ID ed il
+group-ID effettivo del processo chiamante, e che i permessi indicati con
+\param{mode} vengono filtrati dal valore della \itindex{umask} \textit{umask}
+del processo.  Inoltre per poter aprire un semaforo è necessario avere su di
+esso sia il permesso di lettura che quello di scrittura.
+
+Una volta che si sia ottenuto l'indirizzo di un semaforo, sarà possibile
+utilizzarlo; se si ricorda quanto detto all'inizio di
+sez.~\ref{sec:ipc_sysv_sem}, dove si sono introdotti i concetti generali
+relativi ai semafori, le operazioni principali sono due, quella che richiede
+l'uso di una risorsa bloccando il semaforo e quella che rilascia la risorsa
+liberando il semaforo. La prima operazione è effettuata dalla funzione
+\funcd{sem\_wait}, il cui prototipo è:
+\begin{functions}
+  \headdecl{semaphore.h} 
+  
+  \funcdecl{int sem\_wait(sem\_t *sem)}
+  
+  Blocca il semaforo \param{sem}.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore; nel quel caso \var{errno} assumerà i valori:
+    \begin{errlist}
+    \item[\errcode{EINTR}] la funzione è stata interrotta da un segnale.
+    \item[\errcode{EINVAL}] il semaforo \param{sem} non esiste.
+    \end{errlist}    
+}
+\end{functions}
+
+La funzione cerca di decrementare il valore del semaforo indicato dal
+puntatore \param{sem}, se questo ha un valore positivo, cosa che significa che
+la risorsa è disponibile, la funzione ha successo, il valore del semaforo
+viene diminuito di 1 ed essa ritorna immediatamente; se il valore è nullo la
+funzione si blocca fintanto che il valore del semaforo non torni
+positivo\footnote{ovviamente per opera di altro processo che lo rilascia
+  chiamando \func{sem\_post}.} così che poi essa possa decrementarlo con
+successo e proseguire. 
+
+Si tenga presente che la funzione può sempre essere interrotta da un segnale
+(nel qual caso si avrà un errore di \const{EINTR}) e che questo avverrà
+comunque, anche se si è richiesta la semantica BSD installando il relativo
+gestore con \const{SA\_RESTART} (vedi sez.~\ref{sec:sig_sigaction}) per
+riavviare le system call interrotte.
+
+Della funzione \func{sem\_wait} esistono due varianti che consentono di
+gestire diversamente le modalità di attesa in caso di risorsa occupata, la
+prima di queste è \funcd{sem\_trywait}, che serve ad effettuare un tentativo
+di acquisizione senza bloccarsi; il suo prototipo è:
+\begin{functions}
+  \headdecl{semaphore.h} 
+  
+  \funcdecl{int sem\_trywait(sem\_t *sem)}
+  
+  Tenta di bloccare il semaforo \param{sem}.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore; nel quel caso \var{errno} assumerà gli stessi valori:
+    \begin{errlist}
+    \item[\errcode{EAGAIN}] il semaforo non può essere acquisito senza
+      bloccarsi. 
+    \item[\errcode{EINVAL}] il semaforo \param{sem} non esiste.
+    \end{errlist}    
+}
+\end{functions}
+
+La funzione è identica a \func{sem\_wait} ed se la risorsa è libera ha lo
+stesso effetto, vale a dire che in caso di semaforo diverso da zero la
+funzione lo decrementa e ritorna immediatamente; la differenza è che nel caso
+in cui il semaforo è occupato essa non si blocca e di nuovo ritorna
+immediatamente, restituendo però un errore di \errval{EAGAIN}, così che il
+programma possa proseguire.
+
+La seconda variante di \func{sem\_wait} è una estensione specifica che può
+essere utilizzata soltanto se viene definita la macro \macro{\_XOPEN\_SOURCE}
+ad un valore di 600 prima di includere \texttt{semaphore.h}, la funzione è
+\func{sem\_timedwait}, ed il suo prototipo è:
+\begin{functions}
+  \headdecl{semaphore.h} 
+
+  \funcdecl{int sem\_timedwait(sem\_t *sem, const struct timespec
+    *abs\_timeout)}
+  
+  Blocca il semaforo \param{sem}.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore; nel quel caso \var{errno} assumerà gli stessi valori:
+    \begin{errlist}
+    \item[\errcode{ETIMEDOUT}] è scaduto il tempo massimo di attesa. 
+    \item[\errcode{EINVAL}] il semaforo \param{sem} non esiste.
+    \item[\errcode{EINTR}] la funzione è stata interrotta da un segnale.
+    \end{errlist}    
+}
+\end{functions}
+
+Anche in questo caso il comportamento della funzione è identico a quello di
+\func{sem\_wait}, la sola differenza consiste nel fatto che con questa
+funzione è possibile impostare tramite l'argomento \param{abs\_timeout} un
+tempo limite per l'attesa, scaduto il quale la funzione ritorna comunque,
+anche se non è possibile acquisire il semaforo. In tal caso la funzione
+fallirà, riportando un errore di \errval{ETIMEDOUT}.
+
+La seconda funzione principale utilizzata per l'uso dei semafori è
+\funcd{sem\_post}, che viene usata per rilasciare un semaforo occupato o, in
+generale, per aumentare di una unità il valore dello stesso anche qualora non
+fosse occupato;\footnote{si ricordi che in generale un semaforo viene usato
+  come indicatore di un numero di risorse disponibili.} il suo prototipo è:
+\begin{functions}
+  \headdecl{semaphore.h} 
+  
+  \funcdecl{int sem\_post(sem\_t *sem)}
+  
+  Rilascia il semaforo \param{sem}.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore; nel quel caso \var{errno} assumerà i valori:
+    \begin{errlist}
+    \item[\errcode{EINVAL}] il semaforo \param{sem} non esiste.
+    \end{errlist}    
+}
+\end{functions}
+
+La funzione incrementa di uno il valore corrente del semaforo indicato
+dall'argomento \param{sem}, se questo era nullo la relativa risorsa risulterà
+sbloccata, cosicché un altro processo (o \itindex{thread} \textit{thread})
+eventualmente bloccato in una \func{sem\_wait} sul semaforo potrà essere
+svegliato e rimesso in esecuzione.  Si tenga presente che la funzione è sicura
+\index{funzioni!sicure} per l'uso all'interno di un gestore di segnali (si
+ricordi quanto detto in sez.~\ref{sec:sig_signal_handler}).
+
+Se invece di operare su un semaforo se ne vuole solamente leggere il valore,
+si può usare la funzione \funcd{sem\_getvalue}, il cui prototipo è:
+\begin{functions}
+  \headdecl{semaphore.h} 
+  
+  \funcdecl{int sem\_getvalue(sem\_t *sem, int *sval)}
+  
+  Richiede il valore del semaforo \param{sem}.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore; nel quel caso \var{errno} assumerà i valori:
+    \begin{errlist}
+    \item[\errcode{EINVAL}] il semaforo \param{sem} non esiste.
+    \end{errlist}    
+}
+\end{functions}
+
+La funzione legge il valore del semaforo indicato dall'argomento \param{sem} e
+lo restituisce nella variabile intera puntata dall'argomento
+\param{sval}. Qualora ci siano uno o più processi bloccati in attesa sul
+semaforo lo standard prevede che la funzione possa restituire un valore nullo
+oppure il numero di processi bloccati in una \func{sem\_wait} sul suddetto
+semaforo; nel caso di Linux vale la prima opzione.
+
+Questa funzione può essere utilizzata per avere un suggerimento sullo stato di
+un semaforo, ovviamente non si può prendere il risultato riportato in
+\param{sval} che come indicazione, il valore del semaforo infatti potrebbe
+essere già stato modificato al ritorno della funzione.
+
+% TODO verificare comportamento sem_getvalue
+
+Una volta che non ci sia più la necessità di operare su un semaforo se ne può
+terminare l'uso con la funzione \funcd{sem\_close}, il cui prototipo è:
+\begin{functions}
+  \headdecl{semaphore.h} 
+  
+  \funcdecl{int sem\_close(sem\_t *sem)}
+  
+  Chiude il semaforo \param{sem}.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore; nel quel caso \var{errno} assumerà i valori:
+    \begin{errlist}
+    \item[\errcode{EINVAL}] il semaforo \param{sem} non esiste.
+    \end{errlist}    
+}
+\end{functions}
+
+La funzione chiude il semaforo indicato dall'argomento \param{sem}; questo
+comporta che tutte le risorse che il sistema può avere assegnato al processo
+nell'uso dello stesso vengono rilasciate. Questo significa che un altro
+processo bloccato sul semaforo a causa della acquisizione da parte del
+processo che chiama \func{sem\_close} potrà essere riavviato.
+
+Si tenga presente poi che come per i file all'uscita di un processo tutti i
+semafori che questo aveva aperto vengono automaticamente chiusi; questo
+comportamento risolve il problema che si aveva con i semafori del \textit{SysV
+  IPC} (di cui si è parlato in sez.~\ref{sec:ipc_sysv_sem}) per i quali le
+risorse possono restare bloccate. Si tenga poi presente che, a differenza di
+quanto avviene per i file, in caso di una chiamata ad \func{execve} tutti i
+semafori vengono chiusi automaticamente.
+
+Come per i semafori del \textit{SysV IPC} anche quelli POSIX hanno una
+persistenza di sistema; questo significa che una volta che si è creato un
+semaforo con \func{sem\_open} questo continuerà ad esistere fintanto che il
+kernel resta attivo (vale a dire fino ad un successivo riavvio) a meno che non
+lo si cancelli esplicitamente. Per far questo si può utilizzare la funzione
+\funcd{sem\_unlink}, il cui prototipo è:
+\begin{functions}
+  \headdecl{semaphore.h} 
+  
+  \funcdecl{int sem\_unlink(const char *name)}
+  
+  Rimuove il semaforo \param{name}.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore; nel quel caso \var{errno} assumerà i valori:
+    \begin{errlist}
+    \item[\errcode{EACCESS}] non si hanno i permessi necessari a cancellare il
+      semaforo.
+    \item[\errcode{ENAMETOOLONG}] il nome indicato è troppo lungo.
+    \item[\errcode{ENOENT}] il semaforo \param{name} non esiste.
+    \end{errlist}    
+}
+\end{functions}
+
+La funzione rimuove il semaforo indicato dall'argomento \param{name}, che
+prende un valore identico a quello usato per creare il semaforo stesso con
+\func{sem\_open}. Il semaforo viene rimosso dal filesystem immediatamente; ma
+il semaforo viene effettivamente cancellato dal sistema soltanto quando tutti
+i processi che lo avevano aperto lo chiudono. Si segue cioè la stessa
+semantica usata con \func{unlink} per i file, trattata in dettaglio in
+sez.~\ref{sec:file_link}.
+
+Una delle caratteristiche peculiari dei semafori POSIX è che questi possono
+anche essere utilizzati anche in forma anonima, senza necessità di fare
+ricorso ad un nome sul filesystem o ad altri indicativi.  In questo caso si
+dovrà porre la variabile che contiene l'indirizzo del semaforo in un tratto di
+memoria che sia accessibile a tutti i processi in gioco.  La funzione che
+consente di inizializzare un semaforo anonimo è \funcd{sem\_init}, il cui
+prototipo è:
+\begin{functions}
+  \headdecl{semaphore.h} 
+  
+  \funcdecl{int sem\_init(sem\_t *sem, int pshared, unsigned int value)}
+
+  Inizializza il semaforo anonimo \param{sem}.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore; nel quel caso \var{errno} assumerà i valori:
+    \begin{errlist}
+    \item[\errcode{EINVAL}] il valore di \param{value} eccede
+      \const{SEM\_VALUE\_MAX}.
+    \item[\errcode{ENOSYS}] il valore di \param{pshared} non è nullo ed il
+      sistema non supporta i semafori per i processi.
+    \end{errlist}
+}
+\end{functions}
+
+La funzione inizializza un semaforo all'indirizzo puntato dall'argomento
+\param{sem}, e come per \func{sem\_open} consente di impostare un valore
+iniziale con \param{value}. L'argomento \param{pshared} serve ad indicare se
+il semaforo deve essere utilizzato dai \itindex{thread} \textit{thread} di uno
+stesso processo (con un valore nullo) o condiviso fra processi diversi (con un
+valore non nullo).
+
+Qualora il semaforo debba essere condiviso dai \itindex{thread}
+\textit{thread} di uno stesso processo (nel qual caso si parla di
+\textit{thread-shared semaphore}), occorrerà che \param{sem} sia l'indirizzo
+di una variabile visibile da tutti i \itindex{thread} \textit{thread}, si
+dovrà usare cioè una variabile globale o una variabile allocata dinamicamente
+nello \itindex{heap} \textit{heap}.
+
+Qualora il semaforo debba essere condiviso fra più processi (nel qual caso si
+parla di \textit{process-shared semaphore}) la sola scelta possibile per
+renderlo visibile a tutti è di porlo in un tratto di memoria condivisa. Questo
+potrà essere ottenuto direttamente sia con \func{shmget} (vedi
+sez.~\ref{sec:ipc_sysv_shm}) che con \func{shm\_open} (vedi
+sez.~\ref{sec:ipc_posix_shm}), oppure, nel caso che tutti i processi in gioco
+abbiano un genitore comune, con una mappatura anonima con \func{mmap} (vedi
+sez.~\ref{sec:file_memory_map}),\footnote{si ricordi che i tratti di memoria
+  condivisa vengono mantenuti nei processi figli attraverso la funzione
+  \func{fork}.} a cui essi poi potranno accedere.
+
+Una volta inizializzato il semaforo anonimo con \func{sem\_init} lo si potrà
+utilizzare nello stesso modo dei semafori normali con \func{sem\_wait} e
+\func{sem\_post}. Si tenga presente però che inizializzare due volte lo stesso
+semaforo può dar luogo ad un comportamento indefinito. 
+
+Una volta che non si intenda più utilizzare un semaforo anonimo questo può
+essere eliminato dal sistema; per far questo di deve utilizzare una apposita
+funzione, \funcd{sem\_destroy}, il cui prototipo è:
+\begin{functions}
+  \headdecl{semaphore.h} 
+  
+  \funcdecl{int sem\_destroy(sem\_t *sem)}
+
+  Elimina il semaforo anonimo \param{sem}.
+  
+  \bodydesc{La funzione restituisce 0 in caso di successo e $-1$ in caso di
+    errore; nel quel caso \var{errno} assumerà i valori:
+    \begin{errlist}
+    \item[\errcode{EINVAL}] il valore di \param{value} eccede
+      \const{SEM\_VALUE\_MAX}.
+    \end{errlist}
+}
+\end{functions}
 
+La funzione prende come unico argomento l'indirizzo di un semaforo che deve
+essere stato inizializzato con \func{sem\_init}; non deve quindi essere
+applicata a semafori creati con \func{sem\_open}. Inoltre si deve essere
+sicuri che il semaforo sia effettivamente inutilizzato, la distruzione di un
+semaforo su cui sono presenti processi (o \itindex{thread} \textit{thread}) in
+attesa (cioè bloccati in una \func{sem\_wait}) provoca un comportamento
+indefinito.
+
+Si tenga presente infine che utilizzare un semaforo che è stato distrutto con
+\func{sem\_destroy} di nuovo può dare esito a comportamenti indefiniti.  Nel
+caso ci si trovi in una tale evenienza occorre reinizializzare il semaforo una
+seconda volta con \func{sem\_init}.
+
+Come esempio di uso sia della memoria condivisa che dei semafori POSIX si sono
+scritti due semplici programmi con i quali è possibile rispettivamente
+monitorare il contenuto di un segmento di memoria condivisa e modificarne il
+contenuto. 
+
+\begin{figure}[!h]
+  \footnotesize \centering
+  \begin{minipage}[c]{15cm}
+    \includecodesample{listati/message_getter.c}
+  \end{minipage} 
+  \normalsize 
+  \caption{Sezione principale del codice del programma
+    \file{message\_getter.c}.}
+  \label{fig:ipc_posix_sem_shm_message_server}
+\end{figure}
+
+Il corpo principale del primo dei due, il cui codice completo è nel file
+\file{message\_getter.c} dei sorgenti allegati, è riportato in
+fig.~\ref{fig:ipc_posix_sem_shm_message_server}; si è tralasciata la parte che
+tratta la gestione delle opzioni a riga di comando (che consentono di
+impostare un nome diverso per il semaforo e il segmento di memoria condivisa)
+ed il controllo che al programma venga fornito almeno un argomento, contenente
+la stringa iniziale da inserire nel segmento di memoria condivisa.
+
+Lo scopo del programma è quello di creare un segmento di memoria condivisa su
+cui registrare una stringa, e tenerlo sotto osservazione stampando la stessa
+una volta al secondo. Si utilizzerà un semaforo per proteggere l'accesso in
+lettura alla stringa, in modo che questa non possa essere modificata
+dall'altro programma prima di averla finita di stampare.
+
+La parte iniziale del programma contiene le definizioni (\texttt{\small 1--8})
+del gestore del segnale usato per liberare le risorse utilizzate, delle
+variabili globali contenenti i nomi di default del segmento di memoria
+condivisa e del semaforo (il default scelto è \texttt{messages}), e delle
+altre variabili utilizzate dal programma.
+
+Come prima istruzione (\texttt{\small 10}) si è provveduto ad installare un
+gestore di segnale che consentirà di effettuare le operazioni di pulizia
+(usando la funzione \func{Signal} illustrata in
+fig.~\ref{fig:sig_Signal_code}), dopo di che (\texttt{\small 10--16}) si è
+creato il segmento di memoria condivisa con la funzione \func{CreateShm} che
+abbiamo appena trattato in sez.~\ref{sec:ipc_posix_shm}, uscendo con un
+messaggio in caso di errore. 
+
+Si tenga presente che la funzione \func{CreateShm} richiede che il segmento
+non sia già presente e fallirà qualora un'altra istanza, o un altro programma
+abbia già allocato un segmento con quello stesso nome. Per semplicità di
+gestione si è usata una dimensione fissa pari a 256 byte, definita tramite la
+costante \texttt{MSGMAXSIZE}.
+
+Il passo successivo (\texttt{\small 17--21}) è quello della creazione del
+semaforo che regola l'accesso al segmento di memoria condivisa con
+\func{sem\_open}; anche in questo caso si gestisce l'uscita con stampa di un
+messaggio in caso di errore. Anche per il semaforo, avendo specificato la
+combinazione di flag \code{O\_CREAT|O\_EXCL} come secondo argomento, si esce
+qualora fosse già esistente; altrimenti esso verrà creato con gli opportuni
+permessi specificati dal terzo argomento, (indicante lettura e scrittura in
+notazione ottale). Infine il semaforo verrà inizializzato ad un valore nullo
+(il quarto argomento), corrispondete allo stato in cui risulta bloccato.
+
+A questo punto (\texttt{\small 23}) si potrà inizializzare il messaggio posto
+nel segmento di memoria condivisa usando la stringa passata come argomento al
+programma. Essendo il semaforo stato creato già bloccato non ci si dovrà
+preoccupare di eventuali \itindex{race~condition} \textit{race condition}
+qualora il programma di modifica del messaggio venisse lanciato proprio in
+questo momento.  Una volta inizializzato il messaggio occorrerà però
+rilasciare il semaforo (\texttt{\small 25--28}) per consentirne l'uso; in
+tutte queste operazioni si provvederà ad uscire dal programma con un opportuno
+messaggio in caso di errore.
+
+Una volta completate le inizializzazioni il ciclo principale del programma
+(\texttt{\small 29--47}) viene ripetuto indefinitamente (\texttt{\small 29})
+per stampare sia il contenuto del messaggio che una serie di informazioni di
+controllo. Il primo passo (\texttt{\small 30--34}) è quello di acquisire (con
+\func{sem\_getvalue}, con uscita in caso di errore) e stampare il valore del
+semaforo ad inizio del ciclo; seguito (\texttt{\small 35--36}) dal tempo
+corrente.
+
+\begin{figure}[!h]
+  \footnotesize \centering
+  \begin{minipage}[c]{15cm}
+    \includecodesample{listati/HandSigInt.c}
+  \end{minipage} 
+  \normalsize 
+  \caption{Codice del gestore di segnale del programma
+    \file{message\_getter.c}.}
+  \label{fig:ipc_posix_sem_shm_message_server_handler}
+\end{figure}
+
+Prima della stampa del messaggio invece si deve acquisire il semaforo
+(\texttt{\small 31--34}) per evitare accessi concorrenti alla stringa da parte
+del programma di modifica. Una volta eseguita la stampa (\texttt{\small 41})
+il semaforo dovrà essere rilasciato (\texttt{\small 42--45}). Il passo finale
+(\texttt{\small 46}) è attendere per un secondo prima di eseguire da capo il
+ciclo. 
+
+Per uscire in maniera corretta dal programma sarà necessario interromperlo con
+il break da tastiera (\texttt{C-c}), che corrisponde all'invio del segnale
+\const{SIGINT}, per il quale si è installato (\texttt{\small 10}) una
+opportuna funzione di gestione, riportata in
+fig.~\ref{fig:ipc_posix_sem_shm_message_server_handler}. La funzione è molto
+semplice e richiama le funzioni di rimozione sia per il segmento di memoria
+condivisa che per il semaforo, garantendo così che possa essere riaperto
+ex-novo senza errori in un futuro riutilizzo del comando.
+
+\begin{figure}[!h]
+  \footnotesize \centering
+  \begin{minipage}[c]{15cm}
+    \includecodesample{listati/message_setter.c}
+  \end{minipage} 
+  \normalsize 
+  \caption{Sezione principale del codice del programma
+    \file{message\_setter.c}.}
+  \label{fig:ipc_posix_sem_shm_message_setter}
+\end{figure}
+
+Il secondo programma di esempio è \file{message\_setter.c}, di cui si è
+riportato il corpo principale in
+fig.~\ref{fig:ipc_posix_sem_shm_message_setter},\footnote{al solito il codice
+  completo è nel file dei sorgenti allegati.} dove si è tralasciata, non
+essendo significativa per quanto si sta trattando, la parte relativa alla
+gestione delle opzioni a riga di comando e degli argomenti, che sono identici
+a quelli usati da \file{message\_getter}, con l'unica aggiunta di un'opzione
+``\texttt{-t}'' che consente di indicare un tempo di attesa (in secondi) in
+cui il programma si ferma tenendo bloccato il semaforo.
+
+Una volta completata la gestione delle opzioni e degli argomenti (ne deve
+essere presente uno solo, contenente la nuova stringa da usare come
+messaggio), il programma procede (\texttt{\small 10--14}) con l'acquisizione
+del segmento di memoria condivisa usando la funzione \func{FindShm} (trattata
+in sez.~\ref{sec:ipc_posix_shm}) che stavolta deve già esistere.  Il passo
+successivo (\texttt{\small 16--19}) è quello di aprire il semaforo, e a
+differenza di \file{message\_getter}, in questo caso si richiede a
+\func{sem\_open} che questo esista, passando uno zero come secondo ed unico
+argomento.
+
+Una volta completate con successo le precedenti inizializzazioni, il passo
+seguente (\texttt{\small 21--24}) è quello di acquisire il semaforo, dopo di
+che sarà possibile eseguire la sostituzione del messaggio (\texttt{\small 25})
+senza incorrere in possibili \itindex{race~condition} \textit{race condition}
+con la stampa dello stesso da parte di \file{message\_getter}.
+
+Una volta effettuata la modifica viene stampato (\texttt{\small 26}) il tempo
+di attesa impostato con l'opzione ``\texttt{-t}'' dopo di che (\texttt{\small
+  27}) viene eseguita la stessa, senza rilasciare il semaforo che resterà
+quindi bloccato (causando a questo punto una interruzione delle stampe
+eseguite da \file{message\_getter}). Terminato il tempo di attesa si rilascerà
+(\texttt{\small 29--32}) il semaforo per poi uscire.
+
+Per verificare il funzionamento dei programmi occorrerà lanciare per primo
+\file{message\_getter}\footnote{lanciare per primo \file{message\_setter} darà
+  luogo ad un errore, non essendo stati creati il semaforo ed il segmento di
+  memoria condivisa.} che inizierà a stampare una volta al secondo il
+contenuto del messaggio ed i suoi dati, con qualcosa del tipo:
+\begin{Verbatim}
+piccardi@hain:~/gapil/sources$  ./message_getter messaggio
+sem=1, Fri Dec 31 14:12:41 2010
+message: messaggio
+sem=1, Fri Dec 31 14:12:42 2010
+message: messaggio
+...
+\end{Verbatim}
+%$
+proseguendo indefinitamente fintanto che non si prema \texttt{C-c} per farlo
+uscire. Si noti come il valore del semaforo risulti sempre pari ad 1 (in
+quanto al momento esso sarà sempre libero). 
+
+A questo punto si potrà lanciare \file{message\_setter} per cambiare il
+messaggio, nel nostro caso per rendere evidente il funzionamento del blocco
+richiederemo anche una attesa di 3 secondi, ed otterremo qualcosa del tipo:
+\begin{Verbatim}
+piccardi@hain:~/gapil/sources$ ./message_setter -t 3 ciao
+Sleeping for 3 seconds
+\end{Verbatim}
+%$
+dove il programma si fermerà per 3 secondi prima di rilasciare il semaforo e
+terminare. 
+
+L'effetto di questo programma si potrà però apprezzare meglio nell'uscita di
+\file{message\_getter}, che verrà interrotta per questo stesso tempo, prima di
+ricominciare con il nuovo testo:
+\begin{Verbatim}
+...
+sem=1, Fri Dec 31 14:16:27 2010
+message: messaggio
+sem=1, Fri Dec 31 14:16:28 2010
+message: messaggio
+sem=0, Fri Dec 31 14:16:29 2010
+message: ciao
+sem=1, Fri Dec 31 14:16:32 2010
+message: ciao
+sem=1, Fri Dec 31 14:16:33 2010
+message: ciao
+...
+\end{Verbatim}
+%$
+
+E si noterà come nel momento in cui si è lanciato \file{message\_setter} le
+stampe di \file{message\_getter} si bloccheranno, come corretto, dopo aver
+registrato un valore nullo per il semaforo.  Il programma infatti resterà
+bloccato nella \func{sem\_wait} (quella di riga (\texttt{\small 37}) in
+fig.~\ref{fig:ipc_posix_sem_shm_message_server}) fino alla scadenza
+dell'attesa di \file{message\_setter} (con l'esecuzione della \func{sem\_post}
+della riga (\texttt{\small 29}) di
+fig.~\ref{fig:ipc_posix_sem_shm_message_setter}), e riprenderanno con il nuovo
+testo alla terminazione di quest'ultimo.
+
+
+% LocalWords:  like fifo System POSIX RPC Calls Common Object Request Brocker
+% LocalWords:  Architecture descriptor kernel unistd int filedes errno EMFILE
+% LocalWords:  ENFILE EFAULT BUF sez fig fork Stevens siblings EOF read SIGPIPE
+% LocalWords:  EPIPE shell CGI Gateway Interface HTML JPEG URL mime type gs dup
+% LocalWords:  barcode PostScript race condition stream BarCodePage WriteMess
+% LocalWords:  size PS switch wait popen pclose stdio const char command NULL
+% LocalWords:  EINVAL cap fully buffered Ghostscript l'Encapsulated epstopsf of
+% LocalWords:  PDF EPS lseek ESPIPE PPM Portable PixMap format pnmcrop PNG pnm
+% LocalWords:  pnmmargin png BarCode inode filesystem l'inode mknod mkfifo RDWR
+% LocalWords:  ENXIO deadlock client reinviate fortunes fortunefilename daemon
+% LocalWords:  FortuneServer FortuneParse FortuneClient pid libgapil  LD librt
+% LocalWords:  PATH linker pathname ps tmp killall fortuned crash socket domain
+% LocalWords:  socketpair BSD sys protocol sv EAFNOSUPPORT EPROTONOSUPPORT AF
+% LocalWords:  EOPNOTSUPP SOCK SysV IPC Process Comunication ipc perm key exec
+% LocalWords:  header ftok proj stat libc SunOS glibc XPG dell'inode number uid
+% LocalWords:  cuid cgid gid tab MSG shift group umask seq MSGMNI SEMMNI SHMMNI
+% LocalWords:  shmmni msgmni sem sysctl IPCMNI IPCTestId msgget EACCES EEXIST
+% LocalWords:  CREAT EXCL EIDRM ENOENT ENOSPC ENOMEM novo proc MSGMAX msgmax ds
+% LocalWords:  MSGMNB msgmnb linked list msqid msgid linux msg qnum lspid lrpid
+% LocalWords:  rtime ctime qbytes first last cbytes msgctl semctl shmctl ioctl
+% LocalWords:  cmd struct buf EPERM RMID msgsnd msgbuf msgp msgsz msgflg EAGAIN
+% LocalWords:  NOWAIT EINTR mtype mtext long message sizeof LENGTH ts sleep BIG
+% LocalWords:  msgrcv ssize msgtyp NOERROR EXCEPT ENOMSG multiplexing select ls
+% LocalWords:  poll polling queue MQFortuneServer write init HandSIGTERM  l'IPC
+% LocalWords:  MQFortuneClient mqfortuned mutex risorse' inter semaphore semget
+% LocalWords:  nsems SEMMNS SEMMSL semid otime semval sempid semncnt semzcnt nr
+% LocalWords:  SEMVMX SEMOPM semop SEMMNU SEMUME SEMAEM semnum union semun arg
+% LocalWords:  ERANGE SETALL SETVAL GETALL array GETNCNT GETPID GETVAL GETZCNT
+% LocalWords:  sembuf sops unsigned nsops UNDO flg nsop num undo pending semadj
+% LocalWords:  sleeper scheduler running next semundo MutexCreate semunion lock
+% LocalWords:  MutexFind wrapper MutexRead MutexLock MutexUnlock unlock locking
+% LocalWords:  MutexRemove shmget SHMALL SHMMAX SHMMIN shmid shm segsz atime FD
+% LocalWords:  dtime lpid cpid nattac shmall shmmax SHMLBA SHMSEG EOVERFLOW brk
+% LocalWords:  memory shmat shmdt void shmaddr shmflg SVID RND RDONLY rounded
+% LocalWords:  SIGSEGV nattch exit SharedMem ShmCreate memset fill ShmFind home
+% LocalWords:  ShmRemove DirMonitor DirProp chdir GaPiL shmptr DirScan ipcs NFS
+% LocalWords:  ComputeValues ReadMonitor touch SIGTERM dirmonitor unlink fcntl
+% LocalWords:  LockFile UnlockFile CreateMutex FindMutex LockMutex SETLKW GETLK
+% LocalWords:  UnlockMutex RemoveMutex ReadMutex UNLCK WRLCK RDLCK mapping MAP
+% LocalWords:  SHARED ANONYMOUS thread patch names strace system call userid Di
+% LocalWords:  groupid Michal Wronski Krzysztof Benedyczak wrona posix mqueue
+% LocalWords:  lmqueue gcc mount mqd name oflag attr maxmsg msgsize receive ptr
+% LocalWords:  send WRONLY NONBLOCK close mqdes EBADF getattr setattr mqstat to
+% LocalWords:  omqstat curmsgs flags timedsend len prio timespec abs EMSGSIZE
+% LocalWords:  ETIMEDOUT timedreceive getaddr notify sigevent notification l'I
+% LocalWords:  EBUSY sigev SIGNAL signo value sigval siginfo all'userid MESGQ
+% LocalWords:  Konstantin Knizhnik futex tmpfs ramfs cache shared swap CONFIG
+% LocalWords:  lrt blocks PAGECACHE TRUNC CLOEXEC mmap ftruncate munmap FindShm
+% LocalWords:  CreateShm RemoveShm LIBRARY Library libmqueue FAILED EACCESS has
+% LocalWords:  ENAMETOOLONG qualchenome RESTART trywait XOPEN SOURCE timedwait
+% LocalWords:  process getvalue sval execve pshared ENOSYS heap PAGE destroy it
+% LocalWords:  xffffffff Arrays owner perms Queues used bytes messages device
+% LocalWords:  Cannot find such Segments getter Signal MSGMAXSIZE been stable
+% LocalWords:  for now it's break Berlin sources Let's an accidental feature
+% LocalWords:  Larry Wall Escape the Hell William ipctestid Identifier segment
+% LocalWords:  violation dell'I SIGINT setter Fri Dec Sleeping seconds
 
 
 %%% Local Variables: