\param{aiocbp}.
\bodydesc{La funzione restituisce 0 se le operazioni si sono concluse con
- successo, altrimenti restituisce il codice di errore.}
-% }, che viene salvato
-% anche in \var{errno}, i valori possibili sono:
-% \begin{errlist}
-% \item[\macro{ENOSYS}] La funzione non è implementata.
-% \item[\macro{EINPROGRESS}] L'operazione è ancora in corso.
-% \item[\macro{EINVAL}] Si è specificato un valore non valido per i campi
-% \var{aio\_offset} o \var{aio\_reqprio} di \param{aiocbp}.
-% \item[\macro{EBADF}] Si è specificato un file descriptor sbagliato.
-% \end{errlist}
-% più tutti quelli possibili per le sottostanti operazioni, .}
+ successo, altrimenti restituisce il codice di errore relativo al loro
+ fallimento.}
\end{prototype}
Se l'operazione non si è ancora completata viene restituito l'errore di
Per questo motivo BSD 4.2\footnote{Le due funzioni sono riprese da BSD4.4 ed
integrate anche dallo standard Unix 98; fino alle libc5 Linux usava
\type{size\_t} come tipo dell'argomento \param{count}, una scelta logica,
- che è stata dismessa per restare aderenti allo standard.} ha introdotto due
-nuove system call, \func{readv} e \func{writev}, che permettono di effettuare
-con una sola chiamata una lettura o una scrittura su una serie di buffer
-(quello che viene chiamato \textsl{I/O vettorizzato}. I relativi prototipi
-sono:
+ che però è stata dismessa per restare aderenti allo standard.} ha introdotto
+due nuove system call, \func{readv} e \func{writev}, che permettono di
+effettuare con una sola chiamata una lettura o una scrittura su una serie di
+buffer (quello che viene chiamato \textsl{I/O vettorizzato}. I relativi
+prototipi sono:
\begin{functions}
\headdecl{sys/uio.h}
\label{fig:file_iovec}
\end{figure}
-I buffer da utilizzare sono specificati attraverso l'argomento \var{vector} che
-è un vettore di tale strutture, la cui lunghezza è specificata da \param{count}.
-Essi verranno letti (o scritti) nell'ordine in cui li si sono specificati.
-
+I buffer da utilizzare sono indicati attraverso l'argomento \param{vector} che
+è un vettore di strutture \var{iovec}, la cui lunghezza è specificata da
+\param{count}. Ciascuna struttura dovrà essere inizializzata per
+opportunamente per indicare i vari buffer da/verso i quali verrà eseguito il
+trasferimento dei dati. Essi verranno letti (o scritti) nell'ordine in cui li
+si sono specificati nel vattore \var{vector}.
\subsection{File mappati in memoria}
Una modalità alternativa di I/O, che usa una interfaccia completamente diversa
rispetto a quella classica vista in \capref{cha:file_unix_interface}, è il
-cosiddetto \textit{memory-mapped I/O}, che attraverso il meccanismo della
+cosiddetto \textit{memory-mapped I/O}, che, attraverso il meccanismo della
\textsl{paginazione}\index{paginazione} usato dalla memoria virtuale (vedi
-\secref{sec:proc_mem_gen}) permette di \textsl{mappare} il contenuto di un
-file in una sezione dello spazio di indirizzi del processo.
+\secref{sec:proc_mem_gen}), permette di \textsl{mappare} il contenuto di un
+file in una sezione dello spazio di indirizzi del processo. Il meccanismo è
+illustrato in \figref{fig:file_mmap_layout}; una sezione del file viene
+riportata direttamente nello spazio degli indirizzi del programma. Tutte le
+operazioni su questo zona verranno riportate indietro sul file dal meccanismo
+della memoria virtuale che trasferirà il contenuto di quel segmento sul file
+invece che nella swap.
+
+\begin{figure}[htb]
+ \centering
+ \includegraphics[width=10cm]{img/mmap_layout}
+ \caption{Disposizione della memoria di un processo quando si esegue la
+ mappatuara in memoria di un file.}
+ \label{fig:file_mmap_layout}
+\end{figure}
Tutto questo comporta una notevole semplificazione delle operazioni di I/O, in
quanto non sarà più necessario utilizzare dei buffer intermedi su cui
appoggiare i dati da traferire, ma questi potranno essere acceduti
-direttamente dalla sezione di memoria; inoltre questa interfaccia
-è più efficiente delle usuali funzioni di I/O, in quanto permette di caricare
-in memoria solo le parti del file che sono effettivamente usate ad un dato
+direttamente nella sezione di memoria mappata; inoltre questa interfaccia è
+più efficiente delle usuali funzioni di I/O, in quanto permette di caricare in
+memoria solo le parti del file che sono effettivamente usate ad un dato
istante.
Infatti, dato che l'accesso è fatto direttamente attraverso la memoria
virtuale, la sezione di memoria mappata su cui si opera sarà a sua volta letta
o scritta sul file una pagina alla volta e solo per le parti effettivamente
-usate, il tutto in maniera completamente trasparente al processo; l'acceso
+usate, il tutto in maniera completamente trasparente al processo; l'accesso
alle pagine non ancora caricate avverrà allo stesso modo con cui vengono
caricate in memoria le pagine che sono state salvate sullo swap.
il cui solo limite è quello dello spazio di indirizzi disponibile, e non della
memoria su cui possono esserne lette delle porzioni.
-L'interfaccia prevede varie funzioni per la gestione del \textit{memory
- mapping}, la prima di queste è \func{mmap}, che esegue la mappatura in
-memoria un file; il suo prototipo è:
+L'interfaccia prevede varie funzioni per la gestione del \textit{memory mapped
+ I/O}, la prima di queste è \func{mmap}, che serve ad eseguire la mappatura
+in memoria di un file; il suo prototipo è:
\begin{functions}
\headdecl{unistd.h}
\macro{MAP\_EXECUTABLE}& Ignorato. \\
\macro{MAP\_NORESERVE} & Si usa con \macro{MAP\_PRIVATE}. Non riserva
delle pagine di swap ad uso del meccanismo di
- \textit{copy on write} per mantenere le modifiche
- fatte alla regione mappata, in
+ \textit{copy on write} per mantenere le
+ modifiche fatte alla regione mappata, in
questo caso dopo una scrittura, se non c'è più
memoria disponibile, si ha l'emissione di
un \macro{SIGSEGV}. \\
(un esempio è l'interfaccia ponte PCI-VME del chip Universe) di dispositivi
che sono utilizzabili praticamente solo con questa interfaccia.
-Passando attraverso una \func{fork} i file mappati in memoria vengono
-ereditati in maniera trasparente dal processo figlio, mantenendo gli stessi
-attributi avuti nel padre; così se si è usato \macro{MAP\_SHARED} padre e
-figlio accederanno allo stesso file in maniera condivisa, mentre se si è usato
-\macro{MAP\_PRIVATE} ciascuno di essi manterrà una sua versione privata
-indipendente. Non c'è invece nessun passaggio attraverso una \func{exec}, dato
-che quest'ultima sostituisce tutto lo spazio degli indirizzi di un processo
-con quello di un nuovo programma.
+Dato che, passando attraverso una \func{fork}, lo spazio di indirizzi viene
+sempre copiato, i file mappati in memoria verranno ereditati in maniera
+trasparente dal processo figlio, mantenendo gli stessi attributi avuti nel
+padre; così se si è usato \macro{MAP\_SHARED} padre e figlio accederanno allo
+stesso file in maniera condivisa, mentre se si è usato \macro{MAP\_PRIVATE}
+ciascuno di essi manterrà una sua versione privata indipendente. Non c'è
+invece nessun passaggio attraverso una \func{exec}, dato che quest'ultima
+sostituisce tutto lo spazio degli indirizzi di un processo con quello di un
+nuovo programma.
Quando si effettua la mappatura di un file vengono pure modificati i tempi ad
esso associati (si ricordi quanto esposto in \secref{sec:file_file_times}). Il
Indicare un intervallo che non contiene pagine mappate non è un errore.
Alla conclusione del processo, ogni pagina mappata verrà automaticamente
-rilasciata, mentre la chiusura del file descriptor non ha alcun effetto sulla
-mappatura della memoria.
+rilasciata, mentre la chiusura del file descriptor usato per effettuare la
+mappatura in memoria non ha alcun effetto sulla stessa.
\section{Il file locking}