Il sistema fa partire qualunque programma chiamando la funzione \func{main};
sta al programmatore chiamare così la funzione principale del programma da cui
si suppone iniziare l'esecuzione; in ogni caso senza questa funzione lo stesso
-\textit{linker} darebbe luogo ad errori.
-
-Lo standard ISO C specifica che la funzione \func{main} può non avere
-argomenti o prendere due argomenti che rappresentano gli argomenti passati da
-linea di comando, in sostanza un prototipo che va sempre bene è il seguente:
+\textit{linker} (si chiama così il programma che effettua i collegamenti di
+cui sopra) darebbe luogo ad errori. Lo standard ISO C specifica che la
+funzione \func{main} può non avere argomenti o prendere due argomenti che
+rappresentano gli argomenti passati da linea di comando, in sostanza un
+prototipo che va sempre bene è il seguente:
\includecodesnip{listati/main_def.c}
-In realtà nei sistemi Unix esiste un'altro modo per definire la funzione
+In realtà nei sistemi Unix esiste un altro modo per definire la funzione
\func{main}, che prevede la presenza di un terzo argomento, \code{char
- *envp[]}, che fornisce l'\textsl{ambiente} (vedi sez.~\ref{sec:proc_environ})
-del programma; questa forma però non è prevista dallo standard POSIX.1 per cui
-se si vogliono scrivere programmi portabili è meglio evitarla.
+ *envp[]}, che fornisce (vedi sez.~\ref{sec:proc_environ})
+l'\textsl{ambiente} del programma; questa forma però non è prevista dallo
+standard POSIX.1 per cui se si vogliono scrivere programmi portabili è meglio
+evitarla.
\subsection{Come chiudere un programma}
La funzione chiude tutti i file descriptor appartenenti al processo (si tenga
presente che questo non comporta il salvataggio dei dati bufferizzati degli
-stream), fa sì che ogni figlio del processo sia ereditato da \cmd{init} (vedi
+stream), fa sì che ogni figlio del processo sia adottato da \cmd{init} (vedi
cap.~\ref{cha:process_handling}), manda un segnale \const{SIGCHLD} al processo
padre (vedi sez.~\ref{sec:sig_job_control}) ed infine ritorna lo stato di
uscita specificato in \param{status} che può essere raccolto usando la
in cui gli indirizzi vanno da zero ad un qualche valore massimo.\footnote{nel
caso di Linux fino al kernel 2.2 detto massimo era, per macchine a 32bit, di
2Gb. Con il kernel 2.4 ed il supporto per la \textit{high-memory} il limite
- è stato esteso.}
+ è stato esteso anche per macchine a 32 bit.}
Come accennato in cap.~\ref{cha:intro_unix} questo spazio di indirizzi è
virtuale e non corrisponde all'effettiva posizione dei dati nella RAM del
per queste variabili viene allocato nello stack quando viene eseguita la
funzione e liberato quando si esce dalla medesima.
-Esiste però un terzo tipo di allocazione, l'\textsl{allocazione dinamica della
- memoria}, che non è prevista direttamente all'interno del linguaggio C, ma
-che è necessaria quando il quantitativo di memoria che serve è determinabile
-solo durante il corso dell'esecuzione del programma.
+Esiste però un terzo tipo di allocazione, l'\textsl{allocazione dinamica}
+della memoria, che non è prevista direttamente all'interno del linguaggio C,
+ma che è necessaria quando il quantitativo di memoria che serve è
+determinabile solo durante il corso dell'esecuzione del programma.
Il C non consente di usare variabili allocate dinamicamente, non è possibile
cioè definire in fase di programmazione una variabile le cui dimensioni
tollerante nei confronti di piccoli errori come quello di chiamate doppie a
\func{free}. In particolare:
\begin{itemize}
-\item se la variabile è posta a zero gli errori vengono ignorati.
+\item se la variabile è posta a zero gli errori vengono ignorati;
\item se è posta ad 1 viene stampato un avviso sullo \textit{standard error}
- (vedi sez.~\ref{sec:file_std_stream}).
+ (vedi sez.~\ref{sec:file_std_stream});
\item se è posta a 2 viene chiamata \func{abort}, che in genere causa
l'immediata conclusione del programma.
\end{itemize}
In altri linguaggi come il java e recentemente il C\# il problema non si pone
nemmeno perché la gestione della memoria viene fatta totalmente in maniera
automatica, ovvero il programmatore non deve minimamente preoccuparsi di
-liberare la memoria allocata precedentemente quando non serve più, poiché il
-framework gestisce automaticamente la cosiddetta \textit{garbage collection}.
-In tal caso, attraverso meccanismi simili a quelli del \textit{reference
- counting}, quando una zona di memoria precedentemente allocata non è più
-riferita da nessuna parte del codice in esecuzione, può essere deallocata
-automaticamente in qualunque momento dall'infrastruttura.
+liberare la memoria allocata precedentemente quando non serve più, poiché
+l'infrastruttura del linguaggio gestisce automaticamente la cosiddetta
+\index{\textit{garbage~collection}}\textit{garbage collection}. In tal caso,
+attraverso meccanismi simili a quelli del \textit{reference counting}, quando
+una zona di memoria precedentemente allocata non è più riferita da nessuna
+parte del codice in esecuzione, può essere deallocata automaticamente in
+qualunque momento dall'infrastruttura.
Anche questo va a scapito delle prestazioni dell'applicazione in esecuzione
(inoltre le applicazioni sviluppate con tali linguaggi di solito non sono
Per limitare l'impatto di questi problemi, e semplificare la ricerca di
eventuali errori, l'implementazione delle routine di allocazione delle
\acr{glibc} mette a disposizione una serie di funzionalità che permettono di
-tracciare le allocazioni e le disallocazione, e definisce anche una serie di
+tracciare le allocazioni e le disallocazioni, e definisce anche una serie di
possibili \textit{hook} (\textsl{ganci}) che permettono di sostituire alle
funzioni di libreria una propria versione (che può essere più o meno
specializzata per il debugging). Esistono varie librerie che forniscono dei
cui torneremo in sez.~\ref{sec:proc_auto_var}.
-Queste due funzioni vengono utilizzate soltanto quando è necessario effettuare
-direttamente la gestione della memoria associata allo spazio dati di un
-processo, ad esempio qualora si debba implementare la propria versione delle
-routine di allocazione della memoria viste in sez.~\ref{sec:proc_mem_malloc}.
-La prima funzione è \funcd{brk}, ed il suo prototipo è:
+Le due funzioni seguenti vengono utilizzate soltanto quando è necessario
+effettuare direttamente la gestione della memoria associata allo spazio dati
+di un processo, ad esempio qualora si debba implementare la propria versione
+delle routine di allocazione della memoria viste in
+sez.~\ref{sec:proc_mem_malloc}. La prima funzione è \funcd{brk}, ed il suo
+prototipo è:
\begin{prototype}{unistd.h}{int brk(void *end\_data\_segment)}
Sposta la fine del segmento dei dati.
Il \textit{memory lock} persiste fintanto che il processo che detiene la
memoria bloccata non la sblocca. Chiaramente la terminazione del processo
comporta anche la fine dell'uso della sua memoria virtuale, e quindi anche di
-tutti i suoi \textit{memory lock}. Infine \textit{memory lock} non sono
+tutti i suoi \textit{memory lock}. Infine i \textit{memory lock} non sono
ereditati dai processi figli.\footnote{ma siccome Linux usa il \textit{copy on
write} (vedi sez.~\ref{sec:proc_fork}) gli indirizzi virtuali del figlio
sono mantenuti sullo stesso segmento di RAM del padre, quindi fintanto che
\subsection{Il formato degli argomenti}
\label{sec:proc_par_format}
-In genere passaggio degli argomenti al programma viene effettuato dalla shell,
-che si incarica di leggere la linea di comando e di effettuarne la scansione
-(il cosiddetto \textit{parsing}) per individuare le parole che la compongono,
-ciascuna delle quali viene considerata un argomento. Di norma per individuare
-le parole viene usato come carattere di separazione lo spazio o il tabulatore,
-ma il comportamento è modificabile attraverso l'impostazione della variabile
-di ambiente \cmd{IFS}.
+In genere il passaggio degli argomenti al programma viene effettuato dalla
+shell, che si incarica di leggere la linea di comando e di effettuarne la
+scansione (il cosiddetto \textit{parsing}) per individuare le parole che la
+compongono, ciascuna delle quali viene considerata un argomento. Di norma per
+individuare le parole viene usato come carattere di separazione lo spazio o il
+tabulatore, ma il comportamento è modificabile attraverso l'impostazione della
+variabile di ambiente \cmd{IFS}.
\begin{figure}[htb]
\centering
funzione all'interno di un ciclo, fintanto che essa non ritorna il valore -1
che indica che non ci sono più opzioni. Nel caso si incontri un'opzione non
dichiarata in \param{optstring} viene ritornato il carattere \texttt{'?'}
-mentre se un opzione che lo richiede non è seguita da un parametro viene
+mentre se un'opzione che lo richiede non è seguita da un parametro viene
ritornato il carattere \texttt{':'}, infine se viene incontrato il valore
\texttt{'-{}-'} la scansione viene considerata conclusa, anche se vi sono altri
elementi di \param{argv} che cominciano con il carattere \texttt{'-'}.
\subsection{Opzioni in formato esteso}
\label{sec:proc_opt_extended}
-Un'estensione di questo schema è costituito dalle cosiddette
+Un'estensione di questo schema è costituita dalle cosiddette
\textit{long-options} espresse nella forma \cmd{-{}-option=parameter}, anche
la gestione di queste ultime è stata standardizzata attraverso l'uso di una
versione estesa di \func{getopt}.
La shell ad esempio ne usa molte per il suo funzionamento (come \texttt{PATH}
per la ricerca dei comandi, o \texttt{IFS} per la scansione degli argomenti),
-e alcune di esse (come \texttt{HOME}, \texttt{USER}, etc.) sono definite al
+e alcune di esse (come \texttt{HOME}, \texttt{USER}, ecc.) sono definite al
login (per i dettagli si veda sez.~\ref{sec:sess_login}). In genere è cura
dell'amministratore definire le opportune variabili di ambiente in uno script
di avvio. Alcune servono poi come riferimento generico per molti programmi
Gli standard POSIX e XPG3 definiscono alcune di queste variabili (le più
comuni), come riportato in tab.~\ref{tab:proc_env_var}. GNU/Linux le supporta
tutte e ne definisce anche altre: per una lista più completa si può
-controllare \cmd{man environ}.
+controllare \cmd{man 5 environ}.
\begin{table}[htb]
\centering
variabile esista già, sovrascrivendola se diverso da zero, lasciandola
immutata se uguale a zero.
-La seconda funzione prende come argomento una stringa analoga quella
+La seconda funzione prende come argomento una stringa analoga a quella
restituita da \func{getenv}, e sempre nella forma \code{NOME=valore}. Se la
variabile specificata non esiste la stringa sarà aggiunta all'ambiente, se
invece esiste il suo valore sarà impostato a quello specificato da
sua sintassi la possibilità di definire delle \textit{variadic
function}\index{variadic} che abbiano un numero variabile di argomenti,
attraverso l'uso nella dichiarazione della funzione dello speciale costrutto
-``\texttt{...}'', che viene chiamato \textit{ellipsis}.
+``\texttt{\textellipsis}'', che viene chiamato \textit{ellipsis}.
Lo standard però non provvede a livello di linguaggio alcun meccanismo con cui
dette funzioni possono accedere ai loro argomenti. L'accesso viene pertanto
\item Dichiarare la conclusione dell'estrazione degli argomenti invocando la
macro \macro{va\_end}.
\end{enumerate}
-in generale è perfettamente legittimo richiedere meno argomenti di quelli che
+In generale è perfettamente legittimo richiedere meno argomenti di quelli che
potrebbero essere stati effettivamente forniti, e nella esecuzione delle
\macro{va\_arg} ci si può fermare in qualunque momento ed i restanti argomenti
saranno ignorati; se invece si richiedono più argomenti di quelli forniti si
espressione di controllo di un comando condizionale, di selezione o di
iterazione;
\item come operando per l'operatore di negazione (\code{!}) in una espressione
- di controllo di un comando condizionale, di selezione o di iterazione.
+ di controllo di un comando condizionale, di selezione o di iterazione;
\item come espressione a sé stante.
\end{itemize}
In generale, dato che l'unica differenza fra la chiamata diretta e quella
-ottenuta da un \func{longjmp}, è il valore di ritorno di \func{setjmp}, essa è
-usualmente chiamata all'interno di un comando \code{if}.
+ottenuta da un \func{longjmp} è costituita dal valore di ritorno di
+\func{setjmp}, essa è usualmente chiamata all'interno di un comando \code{if}.
Uno dei punti critici dei salti non-locali è quello del valore delle
variabili, ed in particolare quello delle variabili automatiche della funzione