1 \chapter{La comunicazione fra processi}
5 Uno degli aspetti fondamentali della programmazione in un sistema unix-like è
6 la comunicazione fra processi. In questo capitolo affronteremo solo i
7 meccanismi più elementari che permettono di mettere in comunicazione processi
8 diversi, come quelli tradizionali che coinvolgono \textit{pipe} e
9 \textit{fifo} e i meccanismi di intercomunicazione di System V.
11 Tralasceremo invece tutte le problematiche relative alla comunicazione
12 attraverso la rete (e le relative interfacce) che saranno affrontate in
13 dettaglio in un secondo tempo. Non affronteremo invece meccanismi più
14 complessi ed evoluti come le RPC (\textit{Remote Procedure Calls}) e CORBA
15 (\textit{Common Object Request Brocker Architecture}) che in genere sono
16 implementati con un ulteriore livello sopra i meccanismi elementari.
20 \section{La comunicazione fra processi tradizionale}
23 Il primo meccanismo di comunicazione fra processi usato dai sistemi unix-like,
24 e quello che viene correntemente usato di più, è quello delle \textit{pipe},
25 che sono una delle caratteristiche peculiari del sistema, in particolar modo
26 dell'interfaccia a linea di comando. In questa sezione descriveremo le sue
27 basi, le funzioni che ne gestiscono l'uso e le varie forme in cui si è
31 \subsection{Le \textit{pipe} standard}
34 Le \textit{pipe} nascono sostanzialmente con Unix, e sono il primo, e tuttora
35 uno dei più usati, meccanismi di comunicazione fra processi. Si tratta in
36 sostanza di uno speciale tipo di file descriptor, più precisamente una coppia
37 di file descriptor,\footnote{si tenga presente che le pipe sono oggetti creati
38 dal kernel e non risiedono su disco.} su cui da una parte si scrive e da
39 un'altra si legge. Si viene così a costituire un canale di comunicazione
40 tramite i due file descriptor, nella forma di un \textsl{tubo} (da cui il
41 nome) in cui in genere un processo immette dati che poi arriveranno ad un
44 La funzione che permette di creare una pipe è appunto \func{pipe}; il suo
46 \begin{prototype}{unistd.h}
47 {int pipe(int filedes[2])}
49 Crea una coppia di file descriptor associati ad una pipe.
51 \bodydesc{La funzione restituisce zero in caso di successo e -1 per un
52 errore, nel qual caso \var{errno} potrà assumere i valori \macro{EMFILE},
53 \macro{ENFILE} e \macro{EFAULT}.}
56 La funzione restituisce una coppia di file descriptor nell'array
57 \param{filedes}; il primo aperto in lettura ed il secondo in scrittura. Il
58 concetto di funzionamento di una pipe è relativamente semplice, quello che si
59 scrive nel file descriptor aperto in scrittura viene ripresentato tale e quale
60 nel file descriptor aperto in lettura, da cui può essere riletto.
62 I file descriptor infatti non sono connessi a nessun file reale, ma ad un
63 buffer nel kernel, la cui dimensione è specificata dalla costante
64 \macro{PIPE\_BUF}, (vedi \secref{sec:sys_file_limits}); lo schema di
65 funzionamento di una pipe è illustrato in \figref{fig:ipc_pipe_singular}, in
66 cui sono illustrati i due capi della pipe, associati a ciascun file
67 descriptor, con le frecce che indicano la direzione del flusso dei dati
72 \includegraphics[height=5cm]{img/pipe}
73 \caption{Schema della struttura di una pipe.}
74 \label{fig:ipc_pipe_singular}
77 Chiaramente creare una pipe all'interno di un processo non serve a niente; se
78 però ricordiamo quanto esposto in \secref{sec:file_sharing} riguardo al
79 comportamento dei file descriptor nei processi figli, è immediato capire come
80 una pipe possa diventare un meccanismo di intercomunicazione. Un processo
81 figlio infatti condivide gli stessi file descriptor del padre, compresi quelli
82 associati ad una pipe (secondo la situazione illustrata in
83 \figref{fig:ipc_pipe_fork}). In questo modo se uno dei processi scrive su un
84 capo della pipe, l'altro può leggere.
88 \includegraphics[height=5cm]{img/pipefork}
89 \caption{Schema dell'uso di una pipe come mezzo di comunicazione fra
90 processo attraverso una \func{fork}.}
91 \label{fig:ipc_pipe_fork}
94 Tutto ciò ci mostra come sia immediato realizzare un meccanismo di
95 comunicazione fra processi attraverso una pipe, utilizzando le ordinarie
96 proprietà dei file, ma ci mostra anche qual'è il principale\footnote{Stevens
97 in \cite{APUE} riporta come limite anche il fatto che la comunicazione è
98 unidirezionale, in realtà questo è un limite facilmente superabile usando
99 una coppia di pipe.} limite nell'uso delle pipe. È necessario infatti che i
100 processi possano condividere i file descriptor della pipe, e per questo essi
101 devono comunque derivare da uno stesso processo padre che ha aperto la pipe,
102 o, più comunemente, essere nella relazione padre/figlio.
105 \subsection{Un esempio dell'uso delle pipe}
106 \label{sec:ipc_pipe_use}
108 Per capire meglio il funzionamento di una pipe faremo un esempio di quello che
109 è il loro uso più comune, analogo a quello effettuato della shell, e che
110 consiste nell'inviare l'output di un processo (lo standard output) sull'input
111 di un'altro. Realizzaremo il programma nella forma di un
112 \textit{CGI}\footnote{Un CGI (\textit{Common Gateway Interface} è un programma
113 che permette la creazione dinamica di un oggetto da inserire all'interno di
114 una pagina HTML.} per apache, che genera una immagine JPEG di un codice a
115 barre, specificato come parametro di input.
117 Un programma che deve essere eseguito come \textit{cgi} per apache deve
118 rispondere a delle caratteristiche specifiche, esso infatti non viene lanciato
119 da una shell, ma dallo stesso web server, alla richiesta di una specifica URL
120 che di solito ha la forma:
122 http://www.sito.it/cgi-bin/programma?parametro
124 ed il risultato dell'elaborazione deve essere presentato (con una intestazione
125 che ne descrive il mime-type) sullo standard output, in modo che apache possa
126 reinviarlo al browser che ha effettuato la richiesta.
128 Per fare questo useremo in sequenza i programmi \cmd{barcode} e \cmd{gs}, il
129 primo infatti è in grado di generare immagini postscript di codici a barre
130 corrispondenti ad una qualunque stringa, mentre il secondo serve per poter
131 effettuare la conversione della stessa immagine in formato JPEG.
133 Si potrebbe obiettare che sarebbe molto più semplice salvare il risultato
134 intermedio su un file temporaneo. Questo però non tiene conto del fatto che il
135 \textit{cgi} deve poter gestire più richieste in concorrenza, e si avrebbe una
136 evidente race condition in caso di accesso simultaneo a detto
137 file.\footnote{la questione potrebbe essere evitata creando prima dei file
138 temporanei, da comunicare poi ai vari sotto-processi, da cancellare alla
139 fine dell'esecuzione; ma a questo punto avremmo perso tutta la semplicità.}
140 L'uso di una pipe invece permette di risolvere il problema in maniera semplice
143 Il programma ci servirà anche come esempio dell'uso di alcune delle funzioni
144 di manipolazione dei file descriptor, come \func{dup} e \func{dup2}, viste in
145 \secref{sec:file_dup}; è attraverso queste funzioni che è possibile dirottare
146 gli stream standard dei processi (che abbiamo visto in
147 \secref{sec:file_std_descr} e \secref{sec:file_std_stream}) sulla pipe. Le
148 sezioni significative del programma è riportato in
149 \figref{fig:ipc_barcode_code}, il codice è disponibile nel file
150 \file{BarCode.c} nella directory dei sorgenti.
154 \footnotesize \centering
155 \begin{minipage}[c]{15cm}
157 int main(int argc, char *argv[], char *envp[])
160 /* create two pipes to handle process communication */
161 if ( (retval = pipe(pipein)) ) {
162 WriteMess("input pipe creation error");
165 if ( (retval = pipe(pipeout)) ) {
166 WriteMess("output pipe creation error");
169 /* First fork: use child to run barcode program */
170 if ( (pid = fork()) == -1) { /* on error exit */
171 WriteMess("child creation error");
176 close(pipein[1]); /* close pipe write end */
177 dup2(pipein[0], STDIN_FILENO); /* remap stdin to pipe read end */
179 dup2(pipeout[1], STDOUT_FILENO); /* remap stdout in pipe output */
180 execlp("barcode", "barcode", size, NULL); //"-o", "-", NULL);
182 close(pipein[0]); /* close input side of input pipe */
183 write(pipein[1], argv[1], strlen(argv[1])); /* write parameter to pipe */
184 close(pipein[1]); /* closing write end */
185 waitpid(pid, NULL, 0); /* wait child completion */
186 /* Second fork: use child to run ghostscript */
187 if ( (pid = fork()) == -1) { /* on error exit */
188 WriteMess("child creation error");
191 /* second child, convert PS to JPEG */
193 close(pipeout[1]); /* close write end */
194 dup2(pipeout[0], STDIN_FILENO); /* remap read end to stdin */
196 write(STDOUT_FILENO, content, strlen(content));
197 execlp("gs", "gs", "-q", "-sDEVICE=jpeg", "-sOutputFile=-", "-", NULL);
201 waitpid(pid, NULL, 0);
207 \caption{Codice del \textit{cgi-bin} \cmd{BarCode}.}
208 \label{fig:ipc_barcode_code}
211 Il primo passo (\texttt{\small 4--12}) è quello di creare le due pipe che
212 servono per la comunicazione fra i due programmi che verranno utilizzati per
213 produrre il codice a barre; si ha cura di controllare la riuscita della
214 chiamata, inviando in caso di errore un messaggio invece dell'immagine
215 richiesta.\footnote{la funzione \func{WriteMess}, non è riportata in
216 \ref{fig:ipc_barcode_code}, ma si incarica semplicemente di formattare
217 l'uscita, aggiungendo un \textit{mime type}, in modo che possa essere
218 interpretata direttamente da un browser.}
220 Una volta create le pipe il programma può creare (\texttt{\small 13-17}) il
221 primo processo figlio, che si incaricherà (\texttt{\small 19--25}) di eseguire
222 il programma \cmd{barcode}: quest'ultimo funziona ricevendo dallo standard
223 input la stringa da convertire nell'immagine postscript del codice a barre,
224 che sarà scritta sullo standard output.
226 Per utilizzare queste caratteristiche il primo figlio chiude (\texttt{\small
227 20}) il capo aperto in scrittura della prima pipe, dato che userà il capo
228 aperto in lettura per ricevere dal padre la stringa da codificare; per far
229 questo collega (\texttt{\small 21}) il capo in lettura della pipe allo
230 standard input usando \func{dup2}. Dato che \cmd{barcode} scrive l'immagine
231 postscript del codice a barre sullo standard output per poter effettuare una
232 ulteriore redirezione il capo in lettura della seconda pipe viene chiuso
233 (\texttt{\small 22}) mentre il capo in scrittura viene collegato allo standard
234 output (\texttt{\small 23}).
236 In questo modo all'esecuzione (\texttt{\small 25}) di \cmd{barcode} (cui si
237 passa in \var{size} la dimensione per l'immagine) quest'ultimo leggerà la
238 stringa da codificare che gli viene inviata dal padre dalla prima pipe e
239 scriverà l'immagine postscript del codice a barre sulla seconda.
241 Dall'altra parte il processo padre prima chiude (\texttt{\small 26}) il capo
242 inutilizzato della prima pipe (quello in input), poi scrive (\texttt{\small
243 27}) la stringa da convertire sul capo in output, così che \cmd{barcode}
244 possa riceverla dallo standard input; a questo punto l'uso della prima pipe è
245 finito ed essa può essere definitivamente chiusa (\texttt{\small 28}), si
246 attende poi (\texttt{\small 29}) che l'esecuzione di \cmd{barcode} sia
249 Alla conclusione della sua esecuzione \cmd{barcode} avrà inviato l'immagine
250 postscript del codice a barre sul capo in scrittura della seconda pipe; a
251 questo punto si può eseguire la seconda conversione, da PS a JPEG, usando il
252 programma \cmd{gs}. Per questo si crea (\texttt{\small 30--34}) un secondo
253 processo figlio, che poi (\texttt{\small 35--42}) eseguirà questo programma
254 leggendo l'immagine postscript creata da \cmd{barcode} dallo standard input,
255 per convertirla in JPEG.
257 Per fare tutto ciò il secondo figlio anzitutto chiude (\texttt{\small 37}) il
258 capo in scrittura della seconda pipe, e ne collega (\texttt{\small 38}) il
259 capo in lettura allo standard input. Per poter formattare l'output del
260 programma in maniera utilizzabile da un browser, si provvede anche
261 \texttt{\small 40}) alla scrittura dell'apposita stringa di mime-type in testa
262 allo standard output. A questo punto si può invocare \texttt{\small 41}) il
263 programma \cmd{gs}, provvedendo gli appositi switch che consentono di leggere
264 il file da convertire dallo standard input, ed inviare la conversione sullo
267 Per concludere le operazioni il processo padre chiude \texttt{\small 44}) il
268 capo in scrittura della seconda pipe, e attende la conclusione del figlio
269 \texttt{\small 45}), per poi uscire \texttt{\small 46}). Si tenga conto che,
270 l'operazione di chiudere il capo in scrittura della seconda pipe è necessaria,
271 infatti non chiudendola \cmd{gs}, che legge il suo stardard input da detta
272 pipe, resterebbe bloccato in attesa di ulteriore input (l'unico modo che un
273 programma ha per sapere che l'input è terminato è rilevare che lo standard
274 input è stato chiuso), e la \func{wait} non ritornerebbe.
277 \subsection{Le funzioni \func{popen} e \func{pclose}}
278 \label{sec:ipc_popen}
280 Come si è visto la modalità più comune di utilizzo di una pipe è quella di
281 utilizzarla per fare da tramite fra output ed input di due programmi invocati
282 in sequenza; per questo motivo lo standard POSIX.2 ha introdotto due funzioni
283 che permettono di sintetizzare queste operazioni. La prima di esse si chiama
284 \func{popen} ed il suo prototipo è:
285 \begin{prototype}{stdio.h}
286 {FILE *popen(const char *command, const char *type)}
288 Esegue il programma \param{command}, di cui, a seconda di \param{type},
289 restituisce, lo standard input o lo standard output nella pipe collegata allo
290 stream restituito come valore di ritorno.
292 \bodydesc{La funzione restituisce l'indirizzo dello stream associato alla pipe
293 in caso di successo e \macro{NULL} per un errore, nel qual caso \var{errno}
294 potrà assumere i valori relativi alle sottostanti invocazioni di \func{pipe}
295 e \func{fork} o \macro{EINVAL} se \param{type} non è valido.}
297 \noindent e serve per semplificare l'uso di \func{pipe}.
299 La funzione crea una pipe, esegue una \func{fork}, ed invoca il programma
300 \param{command} attraverso la shell (in sostanza esegue \file{/bin/sh} con il
301 flag \code{-c}); l'argomento \param{type} deve essere una stringa \verb|"w"| o
302 \verb|"r"|, per indicare se la pipe sarà collegata allo standard input o allo
303 standard output del comando invocato.
305 La funzione restituisce il puntatore allo stream associato alla pipe creata,
306 che sarà aperto in sola lettura (e quindi associato allo standard output del
307 programma indicato) in caso si sia indicato \code{"r"}, o in sola scrittura (e
308 quindi associato allo standard input) in caso di \code{"w"}.
310 Lo stream restituito da \func{popen} è identico a tutti gli effetti ai file
311 standard visti in \secref{cha:files_std_interface}, e viene sempre aperto in
312 modalità \textit{fully-buffered} (vedi \secref{sec:file_buffering}); l'unica
313 differenza è che deve essere chiuso dalla seconda delle due funzioni,
314 \func{pclose}, il cui prototipo è:
315 \begin{prototype}{stdio.h}
316 {int pclose(FILE *stream)}
318 Chiude il file \param{stream}, restituito da una prededente \func{popen}
319 attendendo la terminazione del processo ad essa associato.
321 \bodydesc{La funzione restituisce 0 in caso di successo e -1 in caso di
322 errore; nel quel caso il valore di \func{errno} deriva dalle sottostanti
325 \noindent che si incarica anche di attendere la conclusione del processo
326 creato dalla precedente \func{popen}.
328 Per illustrare l'uso di queste due funzioni riprendiamo l'esempio in
329 \figref{fig:ipc_barcode_code}: esso per quanto funzionante, è piuttosto
330 complesso; inoltre nella pratica sconta un problema di \cmd{gs} che non è in
331 grado\footnote{nella versione GNU Ghostscript 6.53 (2002-02-13).} di
332 riconoscere correttamente l'encapsulated postscript, per cui tutte le volte
333 generata una pagina intera, invece che una semplice figura. Se si vuole
334 generare una immagine di dimensioni corrette si deve allora ricorrere ad
335 ulteriore programma, \cmd{epstopsf}, per convertire in PDF il file EPS
336 generato da \cmd{barcode}. Utilizzando un file in PDF invece, \cmd{gs} esegue
337 la conversione rispettando le dimensioni originarie del codice a barre.
339 Ci si trova dunque davanti al classico caso dell'uso delle pipe in cui si
340 devono eseguire più processi in fila, inviando l'output di ciascuno all'input
341 del successivo, per poi ottenere il risultato finale sullo standard output.
342 Dato che questo caso ciascun processo deve scrivere il suo output sullo
343 standard input del successivo, occorrerà usare \func{popen} aprendo la pipe in
346 Il codice del nuovo programma è riportato in \figref{fig:ipc_barcode2_code};
347 come si può notare l'ordine di invocazione dei programmi è l'inverso di quello
348 in cui ci si aspetta vengano effettivamente eseguiti. Questo non comporta
349 nessun problema; infatti la lettura su una pipe è bloccante, per cui ciascun
350 processo, per quanto lanciato per primo, si bloccherà in attesa di ricevere
351 sullo standard input il risultato dell'elaborazione del precendente, benchè
352 quest'ultimo venga invocato dopo.
355 \footnotesize \centering
356 \begin{minipage}[c]{15cm}
358 int main(int argc, char *argv[], char *envp[])
365 \caption{Codice del \textit{cgi-bin} \cmd{BarCode2}.}
366 \label{fig:ipc_barcode2_code}
369 Nel nostro caso il primo passo (\texttt{\small 12}) è scrivere il mime-type
370 sullo standard output; a questo punto il processo padre non necessita più di
371 eseguire ulteriori operazioni sullo standard output e può tranquillamente
372 provvedere alla redirezione. Il primo processo figlio ad essere invocato
373 (\texttt{\small 14}) è necessariamente l'ultimo della sequenza, in quanto è
374 lui che deve uscire sullo standard output, gli altri saranno tutti rediretti.
376 Una volta lanciato il processo finale si può iniziare la catena delle
377 redirezioni; ogni volta (\texttt{\small 16} e \texttt{\small 20}) duplicheremo
378 il file restituito dalla chiamata precedente a \func{popen} sullo standard
379 output, in questo modo alla successiva chiamata di \func{popen} il processo
380 eseguito scriverà il suo standard output sulla pipe collegata allo standard
381 input del precedente.
383 Alla fine tutto quello che resta da fare è scrivere (\texttt{\small 22}) la
384 stringa del codice a barre sulla pipe collegata allo standard input
385 dell'ultimo processo lanciato, e poi chiudere tutte le pipe create con
389 \subsection{Le \textit{pipe} con nome, o \textit{fifo}}
390 \label{sec:ipc_named_pipe}
392 Come accennato in \secref{sec:ipc_pipes} il problema delle \textit{pipe} è che
393 esse possono essere utilizzate solo da processi con un progenitore comune o
394 nella relazione padre/figlio; per superare questo problema lo standard POSIX.1
395 ha definito dei nuovi oggetti, le \textit{fifo}, che hanno le stesse
396 caratteristiche delle pipe, ma invece che essere struttura interne del kernel
397 visibili solo attraverso un file descriptor comune, possono essere viste
398 attraverso un inode che risiede sul filesystem.
400 Utilizzando una fifo tutti i dati passeranno attraverso un apposito buffer nel
401 kernel, senza transitare dal filesystem, l'inode serve solo a fornire un punto
402 d'appoggio per i vari processi che permetta loro di accedere alla stessa
408 Abbiamo già visto in \secref{sec:file_mknod} le modalità che permettono di
409 creare una fifo, attraverso le funzioni \func{mknod} e \func{mkfifo}; per
410 utilizzarle un processo non avrà che da aprire il relativo file in lettura o
411 scrittura (a seconda della direzione che si vuole dare ai dati).
413 che invece possono risiedere
414 sul filesystem, e che i processi possono usare per le comunicazioni senza
415 dovere per forza essere in relazione diretta.
420 Per poter superare il problema delle \textit{pipe}, illustrato in
421 \secref{sec:ipc_pipes}, che ne consente l'uso solo fra processi con un
422 progenitore comune o nella relazione padre/figlio,
424 \section{La comunicazione fra processi di System V}
427 Per ovviare ai vari limiti dei meccanismo tradizionale di comunicazione fra
428 processi visto in \secref{sec:ipc_unix}, nello sviluppo di System V vennero
429 introdotti una serie di nuovi oggetti e relative interfacce che garantissero
430 una maggiore flessibilità; in questa sezione esamineremo quello che viene
431 ormai chiamato il \textit{System V Inter-Process Comunication System}, più
432 comunemente noto come \textit{SystemV IPC}.
435 \subsection{Code di messaggi}
436 \label{sec:ipc_messque}
438 Il primo oggetto introdotto dal \textit{SystemV IPC} è quello delle code di
441 \subsection{Semafori}
442 \label{sec:ipc_semaph}
444 Il secondo oggetto introdotto dal \textit{SystemV IPC} è quello dei semafori.
447 \subsection{Memoria condivisa}
448 \label{sec:ipc_shar_mem}
450 Il terzo oggetto introdotto dal \textit{SystemV IPC} è quello della memoria
455 %%% TeX-master: "gapil"