Le prime funzioni che considereremo sono quelle relative alla gestione di file
e directory, secondo le caratteristiche standard che essi presentano in un
-filesystem unix, già esaminate in precedenza (vedi
+filesystem unix, la cui struttura abbiamo esaminato in precedenza (vedi
\secref{sec:fileintr_filesystem}).
\subsection{Le funzioni \texttt{link} e \texttt{unlink}}
il caso ad esempio del filesystem \texttt{vfat} di windows).
La funzione opera sui file ordinari, come sugli altri oggetti del filesystem,
-ma solo l'amministratore è in grado di creare un collegamento diretto ad
-un'altra directory, questo lo si fa perché in questo caso è possibile creare
-dei circoli nel filesystem (vedi \secref{sec:fileintr_symlink}) che molti
-programmi non sono in grado di gestire e la cui rimozione diventa estremamente
-complicata (in genere occorre far girare il programma \texttt{fsck} per
-riparare il filesystem); data la sua pericolosità in Linux questa
-caratteristica è stata disabilitata, e la funzione restituisce l'errore
-\texttt{EPERM}.
+in alcuni filesystem solo l'amministratore è in grado di creare un
+collegamento diretto ad un'altra directory, questo lo si fa perché in questo
+caso è possibile creare dei circoli nel filesystem (vedi
+\secref{sec:fileintr_symlink}) che molti programmi non sono in grado di
+gestire e la cui rimozione diventa estremamente complicata (in genere occorre
+far girare il programma \texttt{fsck} per riparare il filesystem); data la sua
+pericolosità in generale nei filesystem usati in Linux questa caratteristica è
+stata disabilitata, e la funzione restituisce l'errore \texttt{EPERM}.
La rimozione di un file (o più precisamente della voce che lo referenzia) si
effettua con la funzione \texttt{unlink}; il suo prototipo è il seguente:
ad una \texttt{open} o una \texttt{stat} su un link simbolico comporta la
lettura del contenuto del medesimo e l'applicazione della funzione al file
specificato da quest'ultimo. Invece altre funzioni come quelle per cancellare
-o rinominare i file operano direttamente sul link simbolico. Inoltre esistono
-funzioni apposite, come la \texttt{readlink} e la \texttt{lstat} per accedere
-alle informazioni del link invece che a quelle del file a cui esso fa
-riferimento.
+o rinominare i file operano direttamente sul link simbolico (per l'elenco vedi
+\ntab). Inoltre esistono funzioni apposite, come la \texttt{readlink} e la
+\texttt{lstat} per accedere alle informazioni del link invece che a quelle del
+file a cui esso fa riferimento.
Le funzioni per operare sui link simbolici sono le seguenti, esse sono tutte
dichiarate nell'header file \texttt{unistd.h}.
\end{errlist}
\end{prototype}
+In \ntab\ si è riportato un elenco dei comportamenti delle varie funzioni che
+operano sui file rispetto ai link simbolici; specificando quali seguono il
+link simbolico e quali possono operare direttamente sul suo contenuto.
+\begin{table}[htb]
+ \centering
+ \footnotesize
+ \begin{tabular}[c]{|l|c|c|}
+ \hline
+ Funzione & Segue il link & Non segue il link \\
+ \hline
+ \hline
+ \func{access} & $\bullet$ & \\
+ \func{chdir} & $\bullet$ & \\
+ \func{chmod} & $\bullet$ & \\
+ \func{chown} & & $\bullet$ \\
+ \func{creat} & $\bullet$ & \\
+ \func{exec} & $\bullet$ & \\
+ \func{lchown} & $\bullet$ & $\bullet$ \\
+ \func{link} & & \\
+ \func{lstat} & & $\bullet$ \\
+ \func{mkdir} & $\bullet$ & \\
+ \func{mkfifo} & $\bullet$ & \\
+ \func{mknod} & $\bullet$ & \\
+ \func{open} & $\bullet$ & \\
+ \func{opendir} & $\bullet$ & \\
+ \func{pathconf} & $\bullet$ & \\
+ \func{readlink} & & $\bullet$ \\
+ \func{remove} & & $\bullet$ \\
+ \func{rename} & & $\bullet$ \\
+ \func{stat} & $\bullet$ & \\
+ \func{truncate} & $\bullet$ & \\
+ \func{unlink} & & $\bullet$ \\
+ \hline
+ \end{tabular}
+ \caption{Uso dei link simbolici da parte di alcune funzioni.}
+ \label{tab:filedir_symb_effect}
+\end{table}
+si noti che non si è specificato il comportamento delle funzioni che operano
+con i file descriptor, in quanto la gestione del link simbolico viene in
+genere effttuata dalla funzione che restituisce il file descriptor
+(normalmente la \func{open}).
+
+\begin{figure}[htb]
+ \centering
+ \includegraphics[width=5cm]{img/link_loop.eps}
+ \caption{Esempio di loop nel filesystem creato con un link simbolico.}
+ \label{fig:filedir_link_loop}
+\end{figure}
+
+Un caso comune che si può avere con i link simbolici è la creazione dei
+cosiddetti \textit{loop}. La situazione è illustrata in \curfig, che riporta
+la struttura della directory \file{/boot}. Come si vede si è creato al suo
+interno un link simbolico che punta di nuovo a \file{/boot}\footnote{Questo
+ tipo di loop è stato effettuato per poter permettere a \cmd{grub} (un
+ bootloader estremamente avanzato in grado di accedere direttamente
+ attraverso vari filesystem al file da lanciare come sistema operativo) di
+ vedere i file in questa directory, che è montata su una partizione separata
+ (e che grub vedrebbe come radice), con lo stesso path con cui verrebbero
+ visti dal sistema operativo.}.
+
+Questo può causare problemi per tutti quei programmi che effettuassero uno
+scan di una directory senza tener conto dei link simbolici, in quel caso
+infatti il loop nella directory
+
+Un secondo punto da tenere presente è che un link simbolico può essere fatto
+anche ad un file che non esiste; ad esempio possiamo creare un file temporaneo
+nella nostra directory con un link del tipo:
+\begin{verbatim}
+$ln -s /tmp/tmp_file temporaneo
+\end{verbatim}%$
+ma anche se \file{/tmp/tmp_file} non esiste. Aprendo in scrittura
+\file{temporaneo} questo verrà scritto; ma se cercassimo di accederlo in sola
+lettura (ad esempio con \cmd{cat}) otterremmo:
+\begin{verbatim}
+$ cat prova
+cat: prova: No such file or directory
+\end{verbatim}%$
+con un errore che sembra sbagliato, dato \cmd{ls} ci mostrerebbe l'esistenza
+di \file{temporaneo}.
+
+
\subsection{Le funzioni \texttt{mkdir} e \texttt{rmdir}}
\label{sec:filedir_dir_creat_rem}
Il primo valore definisce la maschera dei bit usati nei quali viene
memorizzato il tipo di files, mentre gli altri possono essere usati per
-effettuare delle selezioni sul tipo di file voluto.
+effettuare delle selezioni sul tipo di file voluto, combinando opportunamente
+i vari flag; ad esempio se si volesse controllare se un file è una directory o
+un file ordinario si potrebbe definire la condizione:
+\begin{lstlisting}
+#define IS_FILE_DIR(x) ( ((x) & S_IFMT) & (S_IFDIR | S_IFREG) )
+\end{lstlisting}
+in cui prima si estraggono da \var{st\_mode} i bit relativi al tipo di file e
+poi si effettua il confronto con la combinazione di tipi scelta.
\subsection{La dimensione dei file}
\label{sec:filedir_file_size}
Il membro \var{st\_size} contiene la dimensione del file in bytes (se il file
è un file normale, nel caso di un link simbolico al dimensione è quella del
-pathname che contiene, per le directory è in genere un multiplo di 512).
+pathname che contiene).
Il campo \var{st\_blocks} definisce la lunghezza del file in blocchi di 512
bytes. Il campo \var{st\_blksize} infine definisce la dimensione preferita per
i trasferimenti sui file (che è la dimensione usata anche dalle librerie del C
-per l'interfaccia deglli stream); scrivere in blocchi di dimensione inferiore
-sarebbe inefficiente.
+per l'interfaccia degli stream); scrivere sul file a blocchi di dati di
+dimensione inferiore sarebbe inefficiente.
Si tenga conto che lunghezza del file riportata in \var{st\_size} non è detto
che corrisponda all'occupazione dello spazio su disco per via della possibile
parti non scritte vengono restituiti degli zeri, si avrà lo stesso risultato
di \cmd{ls}.
-
Se è sempre possibile allargare un file scrivendoci sopra od usando la
funzione \func{seek} per spostarsi oltre la sua fine. Esistono però anche casi
in cui si può avere bisogno di effettuare un troncamento scartando i dati al
questo è un caso particolare; per qualunque altra dimensione si possono usare
le due funzioni:
\begin{functions}
- \headdecl{unistd.h} \funcdecl{int truncate(const char *file\_name, off_t
+ \headdecl{unistd.h} \funcdecl{int truncate(const char *file\_name, off\_t
length)} Fa si che la dimensione del file \var{file\_name} sia troncata ad
un valore massimo specificato da \var{lenght}.
- \funcdecl{int ftruncate(int fd, off_t length))} Identica a \func{truncate}
+ \funcdecl{int ftruncate(int fd, off\_t length))} Identica a \func{truncate}
eccetto che si usa con un file aperto, specificato tramite il suo file
descriptor \var{fd},
Se il file è più lungo della lunghezza specificata i dati in eccesso saranno
perduti; il comportamento in caso di lunghezza inferiore non è specificato e
-dipende dall'implementazione, il file può essere lasciato invariato o esteso
+dipende dall'implementazione: il file può essere lasciato invariato o esteso
fino alla lunghezza scelta; in quest'ultimo caso lo spazio viene riempito con
zeri (e in genere si ha la creazione di un hole nel file).
\subsection{I tempi dei file}
\label{sec:filedir_file_times}
-Il sistema mantiene tre tempi per ciascun file, corrispondenti a tre campi
-della struttura \func{stat}, come riassunto in \ntab:
+Il sistema mantiene per ciascun file tre tempi. Questi sono registrati
+nell'inode insieme agli altri attibuti del file e possono essere letti tramite
+la funzione \func{stat}, che li restituisce attraverso tre campi della
+struttura in \figref{fig:filedir_stat_struct} il cui signifato è riportato
+nello schema in \ntab:
\begin{table}[htb]
\centering
\begin{tabular}[c]{|c|l|l|c|}
- \var{st\_atime} & & & \\
- \var{st\_mtime} & & & \\
- \var{st\_ctime} & & & \\
+ \var{st\_atime}& ultimo accesso ai dati del file &\func{read}& \cmd{-u}\\
+ \var{st\_mtime}& ultima modifica ai dati del file &\func{write}& default\\
+ \var{st\_ctime}& ultima modifica ai dati dell'inode&\func{chmod},
+ \func{utime} & \cmd{-c} \\
\end{tabular}
\caption{I tre tempi associati a ciascun file}
\label{tab:filedir_file_times}
\end{table}
+La differenza principale di cui tenere presente è quella fra tempo di modifica
+\var{st\_mtime} e tempo di cambiamento di stato \var{st\_ctime}. Il primo
+infatti fa riferimento ad una modifica del contenuto di un file, mentre il
+secondo ad una modifica dell'inode; siccome esistono molte operazioni (come la
+funzione \func{link} e molte altre che vedremo in seguito) che modificano solo
+le informazioni contenute nell'inode senza toccare il file, dato che queste
+ultime sono separate dal contenuto del file diventa necessario l'utilizzo di
+un altro tempo. Si noti inoltre come \var{st\_ctime} non abbia nulla a che
+fare con il tempo di creazione usato da molti altri sistemi operativi, che in
+unix non esiste.
+
+
+
+
\subsection{La funzione \texttt{utime}}
\label{sec:filedir_utime}
\section{Gli standard di unix e GNU/Linux}
\label{sec:intro_standard}
-
+In questa sezione prenderemo in esame alcune caratteristiche generali del
+sistema e gli standard adottati per le funzioni, i prototipi, gli errori, i
+tipi di dati.
+
+\subsection{Prototipi e puntatori}
+\label{sec:intro_function}
+
+\subsection{La misura del tempo in unix}
+\label{sec:intro_unix_time}
+
+Storicamente i sistemi unix-like hanno sempre mantenuto due distinti valori
+per i tempi all'interno del sistema, chiamati rispettivamente \textit{calendar
+ time} e \textit{process time}, secondo le definizioni:
+\begin{itemize}
+\item \textit{calendar time}: è il numero di secondi dalla mezzanotte del
+ primo gennaio 1970, in tempo universale coordinato (o UTC, data che viene
+ usualmente indicata con 00:00:00 Jan, 1 1970 (UTC) e chiamata \textit{the
+ Epoch}). Viene chiamato anche GMT (Greenwich Mean Time) dato che l'UTC
+ corrisponde all'ora locale di Greenwich. E' il tempo su cui viene mantenuto
+ l'orologio del calcolatore, e viene usato ad esempio per indicare le date di
+ modifica dei file o quelle di avvio dei processi. Per memorizzare questo
+ tempo è stato riservato il tipo primitivo \func{time\_t}.
+\item \textit{process time}: talvolta anche detto tempo di CPU. Viene misurato
+ in \textit{clock tick}, corripondenti al numero di interruzioni effettuate
+ dal timer di sistema, e che per Linux sono ogni centesimo di secondo
+ (eccetto per la piattaforma alpha). Il dato primitivo usato per questo tempo
+ è \func{clock\_t}, inoltre la costante \macro{HZ} restituisce la frequenza
+ di operazione del timer, e corrisponde dunque al numero di tick al secondo
+ (Posix definisce allo stesso modo la costante \macro{CLK_TCK}); questo
+ valore può comunque essere ottenuto con \func{sysconf} (vedi
+ \secref{sec:intro_limits}).
+\end{itemize}
+
+In genere si usa il \textit{calendar time} per tenere le date dei file e le
+informazioni analoghe che riguardano i tempi di ``orologio'' (usati ad esempio
+per i demoni che compiono lavori amministrativi ad ore definite, come
+\cmd{cron}). Di solito questo vene convertito automaticamente dal valore in
+UTC al tempo locale, utilizzando le opportune informazioni di localizzazione
+(specificate in \file{/etc/timezone}). E da tenere presente che questo tempo è
+mantenuto dal sistema e non corrisponde all'orologio hardware del calcolatore.
+
+Il \textit{process time} di solito si esprime in secondi e viene usato appunto
+per tenere conto dei tempi di esecuzione dei processi. Per ciascun processo il
+kernel tiene tre di questi tempi:
+\begin{itemize}
+\item \textit{clock time}
+\item \textit{user time}
+\item \textit{system time}
+\end{itemize}
+il primo è il tempo ``reale'' (viene anche chiamato \textit{wall clock time})
+dall'avvio del processo, e misura il tempo trascorso fino alla sua
+conclusione; chiaramente un tale tempo dipede anche dal carico del sistema e
+da quanti altri processi stavano girando nello stesso periodo. Il secondo
+tempo è quello che la CPU ha speso nell'esecuzione delle istruzioni del
+processo in user space. Il terzo è il tempo impiegato dal kernel per eseguire
+delle system call per conto del processo medesimo (tipo quello usato per
+eseguire una \func{write} su un file). In genere la somma di user e system
+time viene chiamato \textit{CPU time}.
\subsection{Lo standard ANSI C}
\label{sec:intro_ansiC}
-
-
\subsection{Lo standard POSIX}
\label{sec:intro_posix}
+\subsection{Valori e limiti del sistema}
+\label{sec:intro_limits}
-
-
+\subsection{Tipi di dati primitivi}
+\label{sec:intro_data_types}