Iniziato esempio Mutex
[gapil.git] / ipc.tex
diff --git a/ipc.tex b/ipc.tex
index ee3270c3e067e7f67e2c65e8a1fc90b67ba962ed..9b04f516ff264eea8f358a29be2d5e1917aa3d0f 100644 (file)
--- a/ipc.tex
+++ b/ipc.tex
@@ -882,7 +882,7 @@ 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
 avanti faremo riferimento come \textit{SysV IPC} (dove IPC è la sigla di
-\textit{Inter-Process Comunication})}.
+\textit{Inter-Process Comunication}).
 
 
 
@@ -2439,6 +2439,10 @@ 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), 
+
+
 
 \subsection{Memoria condivisa}
 \label{sec:ipc_sysv_shm}
@@ -2720,9 +2724,9 @@ automaticamente sganciati. Lo stesso avviene all'uscita del processo
 attraverso una \func{exit}.
 
 
-Una volta che un segmento di memoria condivisa non serve più si può sganciarlo
-esplicitamente dal processo usando la seconda funzione dell'interfaccia,
-\func{shmdt}, il cui  il suo prototipo è:
+Una volta che un segmento di memoria condivisa non serve più, si può
+sganciarlo esplicitamente dal processo usando l'altra funzione
+dell'interfaccia, \func{shmdt}, il cui prototipo è:
 \begin{functions}
   \headdecl{sys/types.h} 
   \headdecl{sys/shm.h}
@@ -2730,7 +2734,7 @@ esplicitamente dal processo usando la seconda funzione dell'interfaccia,
   \funcdecl{int shmdt(const void *shmaddr)}
   Sgancia dal processo un segmento di memoria condivisa.
   
-  \bodydesc{La funzione restituisce 0 in caso di succes so, e -1 in caso di
+  \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
     \macro{EINVAL}.}
@@ -2741,7 +2745,6 @@ memoria condivisa; questo viene identificato con l'indirizzo \param{shmaddr}
 restituito dalla precedente chiamata a \func{shmat} con il quale era stato
 agganciato al processo.
 
-
 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
@@ -2810,28 +2813,49 @@ ritorni un errore quando usata con i flag di \macro{O\_CREAT} e
 \macro{O\_EXCL}. In tal modo la creazione di un 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}.
-
-Questa tecnica ha però parecchi problemi, che non la rendono una alternativa
-praticabile; anzitutto anche in questo caso in caso di terminazione imprevista
-del processo lascia allocata la risorsa (il file di lock) che deve comunque
-essere cancellata esplicitamente. Inoltre il controllo della disponibilità può
-essere fatto solo con una tecnica di polling, che è molto inefficiente.
-Modalità alternative prevedono l'uso di \func{link}, che fallisce se il nome
-esiste già, ma i problemi sono gli stessi.
-
-Per questo motivo la tecnica più pulita è quella di utilizzare \func{fcntl} su
-un file creato per l'occazione per ottenere un write lock sul primo byte del
-file (che non è detto debba esistere); 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; l'accesso sarà controllabile, senza
-necessità di ricorrere al \textit{polling}\index{polling}.
-
+il rilascio si può eseguire con una chiamata ad
+\func{unlink}.\footnote{abbiamo già accennato in \secref{sec:file_open} che
+  questa tecnica può non funzionare se il filesystem su cui si va ad operare è
+  su NFS; in tal caso si può adottare una tecnica alternativa che prevede
+  l'uso di \func{link} per creare come file di lock un hard link ad un file
+  esistente; se il link esiste già e la funzione fallisce, la risorsa
+  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; il difetto di questa
+  soluzione è che funziona solo se si opera all'interno di uno stesso
+  filesystem.}
+
+L'uso di un file di lock presenta però parecchi problemi, che non lo rendono
+una alternativa praticabile per la sincronizzazione:\footnote{ma può essere
+  una tecnica 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 trovi un file di lock il
+  programma che cerca di accedere alla seriale si limita a segnalare che la
+  risorsa non è disponibile.}  anzitutto anche in questo caso in caso di
+terminazione imprevista del processo lascia allocata la risorsa (il file di
+lock) e questa deve essere sempre cancellata esplicitamente.  Inoltre il
+controllo della disponibilità può essere fatto solo con una tecnica di
+polling\index{polling}, che è molto inefficiente. 
+
+Per questo motivo la tecnica alternativa più pulita è quella di fare ricorso
+al \textit{file locking} visto in \secref{sec:file_locking} ed utilizzare
+\func{fcntl} su un file creato per l'occazione 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 determimanare la dispobilità 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
+chiusura dei relativi file) e non ci si deve preoccupare di niente, e non
+consuma risorse permanentemente allocate nel sistema, lo svantaggio è che
+dovendo fare ricorso a delle operazioni sul filesystem esso è in genere
+leggermente più lento.
 
-Una possibile alternativa all'uso dei semafori come meccanismo di
-sincronizzazione è quello di fare ricorso al \textit{file locking} visto in
-\secref{sec:file_locking}. 
 
 
 \subsection{Il \textit{memory mapping} anonimo}
@@ -2843,29 +2867,52 @@ Abbiamo visto in \secref{sec:file_memory_map} come sia possibile
 \section{La comunicazione fra processi di POSIX}
 \label{sec:ipc_posix}
 
-Lo standard POSIX.1b ha introdotto dei nuovi meccanismi di comunicazione,
-rifacendosi a quelli di System V, introducendo una nuova interfaccia che
-evitasse i principali problemi evidenziati in coda a
-\secref{sec:ipc_sysv_generic}.  
+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
+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.
 
 
 
 \subsection{Considerazioni generali}
 \label{sec:ipc_posix_generic}
 
+Il Linux non tutti gli oggetti del POSIX IPC sono supportati nel kernel
+ufficiale; solo la memoria condivisa è presente, ma solo a partire dal kernel
+2.4.x, per gli altri oggetti esistono patch e librerie non
+ufficiali. Nonostante questo è importante esaminare questa interfaccia per la
+sua netta superiorità nei confronti di quella del \textit{SysV IPC}.
 
 
 \subsection{Code di messaggi}
 \label{sec:ipc_posix_mq}
 
+Le code di messaggi non sono supportate a livello del kernel, esse però
+possono essere implementate, usando la memoria condivisa ed i mutex, con
+funzioni di libreria. In generale esse sono comunque poco usate, i socket, nei
+casi in cui sono sufficienti, sono più comodi, e negli altri casi la
+comunicazione può essere gestita direttamente con la stessa metodologia usata
+per implementare le code di messaggi. Per questo ci limiteremo ad una
+descrizione essenziale. 
+
+
 
 \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. Esiste una 
+
 
 \subsection{Memoria condivisa}
 \label{sec:ipc_posix_shm}
 
+La memoria condivisa è l'unico degli oggetti di IPC POSIX già presente nel
+kernel ufficiale. 
+
+
 %%% Local Variables: 
 %%% mode: latex
 %%% TeX-master: "gapil"