Reindicizzate alcune macro, messa sezione sulle opzioni di IP, risistemata
[gapil.git] / sockctrl.tex
index 1cd043457c240ac118d42b42224d3bbdcc0b8941..89c3bfce0cc97af6007417a308ab8a1f0e5e34eb 100644 (file)
@@ -1,6 +1,6 @@
 %% sockctrl.tex
 %%
-%% Copyright (C) 2004 Simone Piccardi.  Permission is granted to
+%% Copyright (C) 2004-2005 Simone Piccardi.  Permission is granted to
 %% copy, distribute and/or modify this document under the terms of the GNU Free
 %% Documentation License, Version 1.1 or any later version published by the
 %% Free Software Foundation; with the Invariant Sections being "Prefazione",
@@ -49,7 +49,7 @@ necessita di compiere questa operazione.
 
 \begin{figure}[htb]
   \centering
-  \includegraphics[width=10cm]{img/resolver}
+  \includegraphics[width=9cm]{img/resolver}
   \caption{Schema di funzionamento delle routine del \textit{resolver}.}
   \label{fig:sock_resolver_schema}
 \end{figure}
@@ -117,6 +117,7 @@ dell'ordine in cui questi vengono interrogati.\footnote{con le implementazioni
   funzioni di libreria, prevedendo un ordine di interrogazione predefinito e
   non modificabile (a meno di una ricompilazione delle librerie stesse).}
 
+\index{\textit{Name~Service~Switch}|(}
 Per risolvere questa serie di problemi la risoluzione dei nomi a dominio
 eseguirà dal \textit{resolver} è stata inclusa all'interno di un meccanismo
 generico per la risoluzione di corrispondenze fra nomi ed informazioni ad essi
@@ -192,6 +193,7 @@ quello che conta sono le funzioni classiche che il \textit{resolver} mette a
 disposizione,\footnote{è cura della implementazione fattane nelle \acr{glibc}
   tenere conto della presenza del \textit{Name Service Switch}.} e sono queste
 quelle che tratteremo nelle sezioni successive.
+\index{\textit{Name~Service~Switch}|)}
 
 
 \subsection{Le funzioni di interrogazione del \textit{resolver}}
@@ -1936,7 +1938,7 @@ socket, mentre l'ultimo argomento \param{optlen},\footnote{questo argomento 
   sez.~\ref{sec:TCP_func_accept}) ed adottato dalle \acr{glibc}.} è la
 dimensione in byte dei dati presenti all'indirizzo indicato da \param{optval}.
 Dato che il tipo di dati varia a seconda dell'opzione scelta, occorrerà
-individuare qual'è quello che deve essere usato, ed utilizzare le opportune
+individuare qual è quello che deve essere usato, ed utilizzare le opportune
 variabili.
 
 La gran parte delle opzioni utilizzano per \param{optval} un valore intero, se
@@ -2070,7 +2072,7 @@ anche di trattare i vari casi particolari, dato che nonostante queste opzioni
 siano indicate al livello generico, alcune di esse han senso solo per alcuni
 tipi di socket. L'elenco dettagliato del significato di ciascuna di esse è
 allora il seguente:
-\begin{basedescript}{\desclabelwidth{3cm}\desclabelstyle{\nextlinelabel}}
+\begin{basedescript}{\desclabelwidth{2.5cm}\desclabelstyle{\nextlinelabel}}
 \item[\const{SO\_KEEPALIVE}] una connessione può restare attiva se non viene
   effettuato alcun traffico su di essa; in certi casi però può essere utile
   controllarne lo stato per accorgersi di eventuali problemi. Per questo, se
@@ -2214,8 +2216,8 @@ allora il seguente:
   sez.~\ref{sec:unix_socket_xxx}). 
 
 \item[\const{SO\_BINDTODEVICE}] questa opzione permette di \textsl{legare} il
-  socket ad una particolare interfaccia interfaccia, in modo che esso possa
-  ricevere ed inviare pacchetti solo su quella. L'opzione richiede per
+  socket ad una particolare interfaccia, in modo che esso possa ricevere ed
+  inviare pacchetti solo su quella. L'opzione richiede per
   \param{optval} il puntatore ad una stringa contenente il nome
   dell'interfaccia (ad esempio \texttt{eth0}); se si utilizza una stringa
   nulla o un valore nullo per \param{optlen} si rimuove un precedente
@@ -2234,12 +2236,12 @@ allora il seguente:
   di amministratore (in particolare con la \textit{capability}
   \const{CAP\_NET\_ADMIN}).  L'opzione necessita inoltre dell'opportuno
   supporto nel kernel;\footnote{deve cioè essere definita la macro di
-    preprocessore \texttt{SOCK\_DEBUGGING} nel file \file{include/net/sock.h}
+    preprocessore \macro{SOCK\_DEBUGGING} nel file \file{include/net/sock.h}
     dei sorgenti del kernel, questo è sempre vero nei kernel delle serie
     superiori alla 2.3, per i kernel delle serie precedenti invece è
     necessario aggiungere a mano detta definizione; è inoltre possibile
     abilitare anche il tracciamento degli stati del TCP definendo la macro
-    \texttt{STATE\_TRACE} in \file{include/net/tcp.h}.}  quando viene
+    \macro{STATE\_TRACE} in \file{include/net/tcp.h}.}  quando viene
   abilitata una serie di messaggi con le informazioni di debug vengono inviati
   direttamente al sistema del kernel log.\footnote{si tenga presente che il
     comportamento è diverso da quanto avviene con BSD, dove l'opzione opera
@@ -2261,26 +2263,51 @@ allora il seguente:
   ma esistono ancora dei processi figli che mantengono attiva almeno una
   connessione remota che utilizza l'indirizzo locale; quando si riavvia il
   server questo viene bloccato sulla chiamata a \func{bind} dato che la porta
-  è ancora utilizzata in una connessione esistente.
-
-  Il punto più critico è che con il protocollo TCP questo può avvenire anche
-  dopo che l'ultimo processo figlio è terminato, in quanto la connessione può
-  restare attiva anche dopo la chiusura del socket mantenendosi nello stato
-  \texttt{TIME\_WAIT}. Usando \const{SO\_REUSEADDR} fra la chiamata a
-  \func{socket} e quella a \func{bind} si consente a quest'ultima di avere
-  successo anche in questo caso. È bene però ricordare che (si riveda quanto
-  detto in sez.~\ref{sec:TCP_time_wait}) la presenza dello stato
-  \texttt{TIME\_WAIT} ha una ragione, e che se si usa questa opzione esiste
-  sempre una probabilità, anche se estremamente remota,\footnote{perché ciò
-    avvenga infatti non solo devono coincidere gli indirizzi IP e le porte
-    degli estremi della nuova connessione, ma anche i numeri di sequenza dei
-    pacchetti, e questo è estremamente improbabile.}  che eventuali pacchetti
-  rimasti intrappolati in una precedente connessione possano finire fra quelli
-  di una nuova. 
-
-
-
-
+  è ancora utilizzata in una connessione esistente.\footnote{questa è una
+    delle domande più frequenti sui newsgroup dedicati allo sviluppo, in
+    quanto è piuttosto comune in questa situazione quando si sta sviluppando
+    un server che si ferma e si riavvia in continuazione.}  Inoltre se si usa
+  il protocollo TCP questo può avvenire anche dopo che l'ultimo processo
+  figlio è terminato, dato che la connessione può restare attiva anche dopo la
+  chiusura del socket mantenendosi nello stato \texttt{TIME\_WAIT}. 
+
+  Usando \const{SO\_REUSEADDR} fra la chiamata a \func{socket} e quella a
+  \func{bind} si consente a quest'ultima di avere comunque successo anche se
+  la connessione è attiva (o nello stato \texttt{TIME\_WAIT}). È bene però
+  ricordare (si riveda quanto detto in sez.~\ref{sec:TCP_time_wait}) che la
+  presenza dello stato \texttt{TIME\_WAIT} ha una ragione, ed infatti se si
+  usa questa opzione esiste sempre una probabilità, anche se estremamente
+  remota,\footnote{perché ciò avvenga infatti non solo devono coincidere gli
+    indirizzi IP e le porte degli estremi della nuova connessione, ma anche i
+    numeri di sequenza dei pacchetti, e questo è estremamente improbabile.}
+  che eventuali pacchetti rimasti intrappolati in una precedente connessione
+  possano finire fra quelli di una nuova.
+
+  Il secondo caso in cui viene usata questa opzione è quando si ha una
+  macchina cui sono assegnati diversi numeri IP (o come suol dirsi
+  \textit{multi-homed}) e si vuole porre in ascolto sulla stessa porta un
+  programma diverso (o una istanza diversa dello stesso programma) per
+  indirizzi IP diversi. Si ricordi infatti che è sempre possibile indicare a
+  \func{bind} di collegarsi solo su di un indirizzo specifico; in tal caso se
+  un altro programma cerca di riutilizzare la stessa porta (anche specificando
+  un indirizzo diverso) otterrà un errore a meno di non aver preventivamente
+  impostato \const{SO\_REUSEADDR}. Usando questa opzione diventa anche
+  possibile eseguire \func{bind} sull'indirizzo generico, e questo permetterà
+  il collegamento per tutti gli indirizzi (di quelli presenti) per i quali la
+  porta non risulti occupata da una precedente chiamata più specifica. Infine
+  si tenga presente che con il protocollo TCP non è mai possibile far partire
+  server che eseguano \func{bind} sullo stesso indirizzo e la stessa porta,
+  cioè ottenere quello che viene chiamato un \textit{completely duplicate
+    binding}.
+
+  Il terzo impiego è simile al precedente e prevede l'uso di \func{bind}
+  all'interno dello stesso programma per associare indirizzi diversi a socket
+  diversi. Il meccanismo funziona fintanto che ciascuna chiamata usa degli
+  indirizzi remoti diversi. In genere questo viene fatto per i socket UDP, per
+  ottenere l'indirizzo remoto, sui sistemi per i quali non è diponibile
+  l'opzione \const{IP\_RECVDSTADDR}, non viene usata per TCP dato che su tali
+  socket si può sempre invocare \func{getsockname} una volta che si è
+  completata la connessione.
 
 
 \item[\const{SO\_TYPE}] questa opzione permette di leggere il tipo di socket
@@ -2296,24 +2323,114 @@ allora il seguente:
 
 \item[\const{SO\_DONTROUTE}] questa opzione forza l'invio diretto dei
   pacchetti del socket, saltando ogni processo relativo all'uso della tabella
-  di routing del kernel. Prende come \param{optval} un intero usato come
-  valore logico. 
-
-\item[\const{SO\_BROADCAST}]
-
-
-\item[\const{SO\_SNDBUF}]
+  di routing del kernel. Prende per \param{optval} un intero usato come valore
+  logico.
+
+\item[\const{SO\_BROADCAST}] questa opzione abilita il \textit{broadcast};
+  quanto abilitata i socket di tipo \const{SOCK\_DGRAM} riceveranno i
+  pacchetti inviati all'indirizzo di broadcast, e potranno scrivere pacchetti
+  su tale indirizzo.  Prende per \param{optval} un intero usato come valore
+  logico. L'opzione non ha effetti su un socket di tipo \const{SOCK\_STREAM}.
+
+
+\item[\const{SO\_SNDBUF}] questa opzione imposta la dimenzione del buffer di
+  uscita del socket. Prende per \param{optval} un intero indicante il numero
+  di byte. Il valore di default ed il valore massimo che si può specificare
+  come argomento per questa opzione sono impostabili tramiti gli opportuni
+  valori di \func{sysctl} (vedi sez.~\ref{sec:sock_sysctl}).
+
+
+\item[\const{SO\_RCVBUF}] questa opzione imposta la dimenzione del buffer di
+  ingresso del socket. Prende per \param{optval} un intero indicante il numero
+  di byte. Il valore di default ed il valore massimo che si può specificare
+  come argomento per questa opzione sono impostabili tramiti gli opportuni
+  valori di \func{sysctl} (vedi sez.~\ref{sec:sock_sysctl}).
+
+
+\item[\const{SO\_LINGER}] 
+
+\item[\const{SO\_PRIORITY}] questa opzione permette di impostare le priorità
+  per tutti i pacchetti che sono inviati sul socket, prende per \param{optval}
+  un valore intero. Con questa opzione il kernel usa il valore per ordinare le
+  priorità sulle code di rete,\footnote{questo richiede che sia abilitato il
+    sistema di \textit{Quality of Service} disponibile con le opzioni di
+    routing avanzato.} i pacchetti con priorità più alta vengono processati
+  per primi, in modalità che dipendono dalla disciplina di gestione della
+  coda. Nel caso di protocollo IP questa opzione permette anche di impostare i
+  valori del campo \textit{type of service} (noto come TOS, vedi
+  sez.~\ref{sec:IP_xxx}) per i pacchetti uscenti. Per impostare una priorità
+  al di fuori dell'intervallo di valori fra 0 e 6 sono richiesti i privilegi
+  di amministratore con la capability \const{CAP\_NET\_ADMIN}.
+
+\item[\const{SO\_ERROR}] questa opzione riceve un errore presente sul socket;
+  può essere utilizzata soltanto con \func{getsockopt} e prende per
+  \param{optval} un valore intero.  
+\end{basedescript}
 
 
-\item[\const{SO\_RCVBUF}]  
+\subsection{Le opzioni per il protocollo IPv4}
+\label{sec:sock_ipv4_options}
 
+Il secondo insieme di opzioni dei socket che tratteremo è quello relativo ai
+socket che usano il protocollo IPv4.\footnote{come per le precedenti opzioni
+  generiche una descrizione di esse è disponibile nella settima sezione delle
+  pagine di manuale, nel caso specifico la documentazione si può consultare
+  con \texttt{man 7 ip}.}  Se si vuole operare su queste opzioni generiche il
+livello da utilizzare è \const{SOL\_IP}; si è riportato un elenco di queste
+opzioni in tab.~\ref{tab:sock_opt_iplevel}.
 
-\item[\const{SO\_LINGER}]  
-\item[\const{SO\_PRIORITY}]
 
-\item[\const{SO\_ERROR}] 
+\begin{table}[!htb]
+  \centering
+  \footnotesize
+  \begin{tabular}[c]{|l|c|c|c|l|l|}
+    \hline
+    \textbf{Opzione}&\texttt{get}&\texttt{set}&\textbf{flag}&\textbf{Tipo}&
+                    \textbf{Descrizione}\\
+    \hline
+    \hline
+    \const{IP\_OPTIONS}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_PKTINFO}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_RECVTOS}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_RECVTTL}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_RECVOPTS}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_RETOPTS}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_TOS}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_TTL}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_HDRINCL}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_RECVERR}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_MTU\_DISCOVER}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_MTU}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_ROUTER\_ALERT}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_MULTICAST\_TTL}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_MULTICAST\_LOOP}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_ADD\_MEMBERSHIP}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_DROP\_MEMBERSHIP}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+    \const{IP\_MULTICAST\_IF}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& 
+                          .\\
+   \hline
+  \end{tabular}
+  \caption{Le opzioni disponibili al livello \const{SOL\_IP}.} 
+  \label{tab:sock_opt_iplevel}
+\end{table}
 
-\end{basedescript}
 
 
 
@@ -2357,7 +2474,45 @@ certo tipo o di tutti quelli che usano un certo protocollo) rispetto alle
 funzioni viste finora che consentono di controllare quelle di un singolo
 socket. 
 
+Le opzioni disponibili per le proprietà della rete sono riportate nella
+gerarchia dei valori impostabili con \func{sysctl}, sotto il nodo
+\texttt{net}, o, se acceduti tramite l'interfaccia del filesystem
+\texttt{/proc}, sotto \texttt{/proc/sys/net}. In genere sotto questa directory
+compaiono le sottodirectory (corrispondenti ad altrettanti sottonodi per
+\func{sysctl}) relative ai vari protocolli e tipi di interfacce su cui è
+possibile intervenire; un contenuto tipico è il seguente:
+\begin{verbatim}
+/proc/sys/net/
+|-- core
+|-- ethernet
+|-- ipv4
+|-- ipv6
+|-- irda
+|-- token-ring
+`-- unix
+\end{verbatim}
+
+
+Nella directory \texttt{/proc/sys/net/core} sono disponibili le opzioni
+generiche dei socket, descritte anche nella rispettiva pagina di
+manuale.\footnote{quella accessibile con \texttt{man 7 socket}.} Queste sono:
 
+\begin{basedescript}{\desclabelwidth{3cm}\desclabelstyle{\nextlinelabel}}
+\item[\texttt{rmem\_default}] imposta la dimensione di default del buffer di
+  lettura (cioè per i dati in ingresso) dei socket.
+\item[\texttt{rmem\_max}] imposta la dimensione massima che si può assegnare al
+  buffer di ingresso dei socket attraverso l'uso dell'opzione
+  \const{SO\_RCVBUF}.
+\item[\texttt{wmem\_default}] imposta la dimensione di default del buffer di
+  scrittura (cioè per i dati in uscita) dei socket.
+\item[\texttt{wmem\_max}] imposta la dimensione massima che si può assegnare al
+  buffer di uscita dei socket attraverso l'uso dell'opzione
+  \const{SO\_SNDBUF}.
+\item[\texttt{message\_cost}] 
+\item[\texttt{message\_burst}] 
+\item[\texttt{netdev\_max\_backlog}] 
+\item[\texttt{optmem\_max}] 
+\end{basedescript}
 
 
 %%% Local Variables: