X-Git-Url: https://gapil.gnulinux.it/gitweb/?p=gapil.git;a=blobdiff_plain;f=sockctrl.tex;h=7d860f348fc018208a36f62d883aff6ea06eff4d;hp=c074a44669fbc839a93785b570d64bb30d633a03;hb=7e19b798d0cc09960daad695d8f3b242170bb3b4;hpb=0fb2222078a11ed92c0f4b256a1446955ad0f7fd diff --git a/sockctrl.tex b/sockctrl.tex index c074a44..7d860f3 100644 --- a/sockctrl.tex +++ b/sockctrl.tex @@ -1,6 +1,6 @@ %% sockctrl.tex %% -%% Copyright (C) 2004-2017 Simone Piccardi. Permission is granted to +%% Copyright (C) 2004-2018 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", @@ -2207,6 +2207,8 @@ riportato un elenco di queste opzioni in tab.~\ref{tab:sock_opt_socklevel}. \hline \const{SO\_ACCEPTCONN}&$\bullet$& & &\texttt{int}& Indica se il socket è in ascolto.\\ + \const{SO\_ATTACH\_FILTER}& &$\bullet$& &\texttt{sock\_fprog}& + Aggancia un filtro BPF al socket.\\ \const{SO\_BINDTODEVICE}&$\bullet$&$\bullet$& &\texttt{char *}& Lega il socket ad un dispositivo.\\ \const{SO\_BROADCAST}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& @@ -2217,6 +2219,8 @@ riportato un elenco di queste opzioni in tab.~\ref{tab:sock_opt_socklevel}. Attiva il ``\textit{busy poll}'' sul socket.\\ \const{SO\_DEBUG} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& Abilita il debugging sul socket.\\ + \const{SO\_DETACH\_FILTER}& &$\bullet$&$\bullet$&\texttt{int}& + Rimuove il filtro BPF agganciato al socket.\\ \const{SO\_DOMAIN} &$\bullet$& & &\texttt{int}& Legge il tipo di socket.\\ \const{SO\_DONTROUTE}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& @@ -2227,6 +2231,8 @@ riportato un elenco di queste opzioni in tab.~\ref{tab:sock_opt_socklevel}. Controlla l'attività della connessione.\\ \const{SO\_LINGER} &$\bullet$&$\bullet$& &\texttt{linger}& Indugia nella chiusura con dati da spedire.\\ + \const{SO\_LOCK\_FILTER}& &$\bullet$&$\bullet$&\texttt{int}& + Blocca il filtro BPF agganciato al socket.\\ \const{SO\_MARK} &$\bullet$&$\bullet$& &\texttt{int}& Imposta un ``\textit{firewall mark}'' sul socket.\\ \const{SO\_OOBINLINE}&$\bullet$&$\bullet$&$\bullet$&\texttt{int}& @@ -2276,7 +2282,10 @@ riportato un elenco di queste opzioni in tab.~\ref{tab:sock_opt_socklevel}. % TODO aggiungere e documentare SO_ATTACH_BPF, introdotta con il kernel 3.19, % vedi http://lwn.net/Articles/625224/ % TODO aggiungere e documentare SO_INCOMING_CPU, introdotta con il kernel 3.19, - +% TODO documentare SO_PEERGROUPS introdotta con il kernel 4.13, citata +% in https://lwn.net/Articles/727385/ +% TODO documentare SO_ZEROCOPY, vedi https://lwn.net/Articles/726917/ (e il +% resto pure) introdotta con il kernel 4.14 La tabella elenca le costanti che identificano le singole opzioni da usare come valore per \param{optname}; le due colonne seguenti indicano per quali @@ -2299,15 +2308,23 @@ tab.~\ref{tab:sock_opt_socklevel} sul significato delle varie opzioni: \item[\constd{SO\_ACCEPTCONN}] questa opzione permette di rilevare se il socket su cui opera è stato posto in modalità di ricezione di eventuali connessioni con una chiamata a \func{listen}. L'opzione può essere usata soltanto con - \func{getsockopt} e utilizza per \param{optval} un intero in cui viene - restituito 1 se il socket è in ascolto e 0 altrimenti. + \func{getsockopt} ed utilizza per \param{optval} un intero in cui viene + restituito 1 se il socket è in ascolto e 0 altrimenti. \item[\constd{SO\_ATTACH\_FILTER}] questa opzione permette di agganciare ad un - socket un filtro di pacchetti che consente di selezionare quali pacchetti, - fra tutti quelli ricevuti, verranno letti. Viene usato principalmente con i - socket di tipo \const{PF\_PACKET} con la libreria \texttt{libpcap} per - implementare programmi di cattura dei pacchetti, torneremo su questo in - sez.~\ref{sec:packet_socket}. + socket un filtro di selezione dei pacchetti con la stessa sintassi del BPF + (\textit{Berkley Packet Filter}) di BSD, che consente di selezionare, fra + tutti quelli ricevuti, verranno letti. Può essere usata solo con + \func{setsockopt} ed utilizza per \param{optval} un puntatore ad una + struttura \struct{sock\_fprog} (definita in + \headfile{linux/filter.h}). Questa opzione viene usata principalmente con i + socket di tipo \const{PF\_PACKET} (torneremo su questo in + sez.~\ref{sec:packet_socket}) dalla libreria \texttt{libpcap} per + implementare programmi di cattura dei pacchetti, e per questo tipo di + applicazione è opportuno usare sempre quest'ultima.\footnote{la trattazione + del BPF va al di là dell'argomento di questa sezione per la documentazione + si consulti il file \texttt{networking/filter.txt} nella documentazione + del kernel.} \item[\constd{SO\_BINDTODEVICE}] questa opzione permette di \textsl{legare} il socket ad una particolare interfaccia, in modo che esso possa ricevere ed @@ -2381,11 +2398,13 @@ tab.~\ref{tab:sock_opt_socklevel} sul significato delle varie opzioni: programma, \cmd{trpt}.} \item[\constd{SO\_DETACH\_FILTER}] consente di distaccare un filtro - precedentemente aggiunto ad un socket. - -% TODO documentare SO_ATTACH_FILTER e SO_DETACH_FILTER -% riferimenti http://www.rcpt.to/lsfcc/lsf.html -% Documentation/networking/filter.txt + precedentemente aggiunto ad un socket con l'opzione + \const{SO\_ATTACH\_FILTER}, in genere non viene usata direttamente in quanto + i filtri BPF vengono automaticamente rimossi alla chiusura del socket, il + suo utilizzo è pertanto limitato ai rari casi in cui si vuole rimuovere un + precedente filtro per inserirne uno diverso. Come \const{SO\_ATTACH\_FILTER} + può essere usato solo \func{setsockopt} e prende per \param{optval} un + intero usato come valore logico. \item[\constd{SO\_DOMAIN}] questa opzione, presente dal kernel 2.6.32, legge il ``\textsl{dominio}'' (la famiglia di indirizzi) del socket. @@ -2425,6 +2444,15 @@ tab.~\ref{tab:sock_opt_socklevel} sul significato delle varie opzioni: fig.~\ref{fig:sock_linger_struct}. Maggiori dettagli sul suo funzionamento sono forniti in sez.~\ref{sec:sock_options_main}. +\item[\constd{SO\_LOCK\_FILTER}] consente di bloccare un filtro + precedentemente aggiunto ad un socket con l'opzione + \const{SO\_ATTACH\_FILTER}, in modo che non possa essere né rimosso né + modificato, questo consente di impostare un filtro su un socket, bloccarlo e + poi cedere i privilegi con la sicurezza che il filtro permarrà fino alla + chiusura del socket. Come \const{SO\_ATTACH\_FILTER} può essere usato solo + \func{setsockopt} e prende per \param{optval} un intero usato come valore + logico. + \item[\constd{SO\_MARK}] questa opzione, presente dal kernel 2.6.25, imposta un valore di marcatura sui pacchetti del socket. Questa è una funzionalità specifica di Linux, ottenibile anche con l'uso del target \texttt{MARK} @@ -2575,31 +2603,11 @@ tab.~\ref{tab:sock_opt_socklevel} sul significato delle varie opzioni: socket. Maggiori dettagli sul suo funzionamento sono forniti in sez.~\ref{sec:sock_options_main}. - \item[\const{SO\_REUSEPORT}] questa opzione, presente a partire dal kernel 3.9, permette di far usare a più socket di tipo \const{AF\_INET} o - \const{AF\_INET6} lo stesso indirizzo locale. L'opzione deve essere attivata - sul socket prima di chiamare \func{bind} e richiede che tutti i processi che - si mettono in ascolto sullo stesso indirizzo abbiano lo stesso \ids{UID} - effettivo, per evitare che un altro utente possa ottenere il relativo - traffico (eseguendo quello che viene definito in \textit{port hijacking}); - l'opzione utilizza per \param{optval} un intero usato come valore logico. - - L'opzione si usa sia per socket TCP che UDP, nel primo caso consente un uso - distribuito si \func{accept} in una applicazione \textit{multithreaded} - passando un diverso \textit{listening socket} ad ogni thread (cosa che - migliora le prestazioni rispetto all'approccio tradizionale di usare un - thread per usare \func{accept} e distribuire le connessioni o avere più - thread che competono per usare \func{accept} sul socket. Nel caso di UDP - l'opzione consente di distribuire meglio i pacchetti su più processi o - thread rispetto all'approccio tradizionale di far competere gli stessi per - l'accesso in ricezione al socket. - - -% TODO documentare SO_REUSEPORT introdotta con il kernel 3.9, vedi -% http://git.kernel.org/linus/c617f398edd4db2b8567a28e899a88f8f574798d -% TODO: in cosa differisce da REUSEADDR? - + \const{AF\_INET6} lo stesso indirizzo locale, e costituisce una estensione + della precedente \const{SO\_REUSEADDR}. Maggiori dettagli sul suo + funzionamento sono forniti in sez.~\ref{sec:sock_options_main}. \item[\constd{SO\_RXQ\_OVFL}] questa opzione, presente dal kernel 2.6.33, permette di abilitare o disabilitare sul socket la ricezione di un messaggio @@ -2662,30 +2670,6 @@ tab.~\ref{tab:sock_opt_socklevel} sul significato delle varie opzioni: \param{optval} un intero in cui verrà restituito il valore numerico che lo identifica (ad esempio \const{SOCK\_STREAM}). -\item[\constd{SO\_DETACH\_FILTER}] consente di distaccare un filtro - precedentemente aggiunto ad un socket. - -% TODO documentare SO_ATTACH_FILTER e SO_DETACH_FILTER -% riferimenti http://www.rcpt.to/lsfcc/lsf.html -% Documentation/networking/filter.txt - -% TODO documentare SO_MARK, introdotta nel 2.6.25, richiede CAP_NET_ADMIN -%A userspace program may wish to set the mark for each packets its send -%without using the netfilter MARK target. Changing the mark can be used -%for mark based routing without netfilter or for packet filtering. - - -% TODO documentare SO_TIMESTAMP e le altre opzioni di timestamping dei -% pacchetti, introdotte nel 2.6.30, vedi nei sorgenti del kernel: -% Documentation/networking/timestamping.txt - - -% TOFO documentare SO_REUSEPORT introdotta con il kernel 3.9, vedi -% http://git.kernel.org/linus/c617f398edd4db2b8567a28e899a88f8f574798d - -% TODO documentare SO_PEERGROUPS introdotta con il kernel 4.13, citata -% in https://lwn.net/Articles/727385/ - \end{basedescript} @@ -2808,9 +2792,9 @@ attivando il relativo comportamento. \constbeg{SO\_REUSEADDR} -\subsubsection{L'opzione \const{SO\_REUSEADDR}} +\subsubsection{Le opzioni \const{SO\_REUSEADDR} e \const{SO\_REUSEPORT}} -La seconda opzione da approfondire è \const{SO\_REUSEADDR}, che consente di +La seconda opzione da approfondire è \constd{SO\_REUSEADDR}, che consente di eseguire \func{bind} su un socket anche quando la porta specificata è già in uso da parte di un altro socket. Si ricordi infatti che, come accennato in sez.~\ref{sec:TCP_func_bind}, normalmente la funzione \func{bind} fallisce con @@ -2832,25 +2816,13 @@ figli che mantengono attiva almeno una connessione remota che utilizza l'indirizzo locale, mantenendo occupata la porta. Quando si riesegue il server allora questo riceve un errore sulla chiamata a \func{bind} dato che la porta è ancora utilizzata in una connessione esistente.\footnote{questa è una delle - domande più frequenti sui newsgroup dedicati allo sviluppo, in quanto è - piuttosto comune trovarsi in questa situazione quando si sta sviluppando un - server che si ferma e si riavvia in continuazione dopo aver fatto - modifiche.} Inoltre se si usa il protocollo TCP questo può avvenire anche -dopo tutti i processi figli sono terminati, dato che una connessione può -restare attiva anche dopo la chiusura del socket, mantenendosi nello stato -\texttt{TIME\_WAIT} (vedi sez.~\ref{sec:TCP_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. + domande più frequenti relative allo sviluppo, in quanto è piuttosto comune + trovarsi in questa situazione quando si sta sviluppando un server che si + ferma e si riavvia in continuazione dopo aver fatto modifiche.} Inoltre se +si usa il protocollo TCP questo può avvenire anche dopo tutti i processi figli +sono terminati, dato che una connessione può restare attiva anche dopo la +chiusura del socket, mantenendosi nello stato \texttt{TIME\_WAIT} (vedi +sez.~\ref{sec:TCP_time_wait}). \begin{figure}[!htbp] \footnotesize \centering @@ -2863,6 +2835,17 @@ finire fra quelli di una nuova. \label{fig:sockbindopt_code} \end{figure} +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. Come esempio di uso di questa connessione abbiamo predisposto una nuova versione della funzione \texttt{sockbind} (vedi fig.~\ref{fig:sockbind_code}) @@ -2908,7 +2891,7 @@ valore, per cui in tal caso la successiva chiamata (\texttt{\small 13--17}) a \func{setsockopt} attiverà l'opzione \const{SO\_REUSEADDR}. Il secondo caso in cui viene usata \const{SO\_REUSEADDR} è quando si ha una -macchina cui sono assegnati diversi numeri IP (o come suol dirsi +macchina cui sono assegnati diversi indirizzi 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} @@ -2920,10 +2903,12 @@ 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 è in genere 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}. +una precedente chiamata più specifica. Si tenga presente infatti che con il +protocollo TCP non è in genere possibile far partire più server che eseguano +\func{bind} sullo stesso indirizzo e la stessa porta se su di esso c'è già un +socket in ascolto, cioè ottenere quello che viene chiamato un +\itindex{completely~duplicate~binding} \textit{completely duplicate binding} +(per questo è stata introdotta \const{SO\_REUSEPORT}). Il terzo impiego è simile al precedente e prevede l'uso di \func{bind} all'interno dello stesso programma per associare indirizzi locali diversi a @@ -2939,53 +2924,74 @@ invocare \func{getsockname} una volta che si è completata la connessione. Infine il quarto caso è quello in cui si vuole effettivamente ottenere un \textit{completely duplicate binding}, quando cioè si vuole eseguire -\func{bind} su un indirizzo ed una porta che sono già \textsl{legati} ad un -altro socket. Questo ovviamente non ha senso per il normale traffico di rete, -in cui i pacchetti vengono scambiati direttamente fra due applicazioni; ma -quando un sistema supporta il traffico in \textit{multicast}, allora ha senso -che su una macchina i pacchetti provenienti dal traffico in \textit{multicast} -possano essere ricevuti da più applicazioni o da diverse istanze della stessa -applicazione. - -L'esempio classico di traffico in \textit{multicast} è quello di uno streaming -di dati (audio, video, ecc.), l'uso del \textit{multicast} consente in tal -caso di trasmettere un solo pacchetto, che potrà essere ricevuto da tutti i -possibili destinatari (invece di inviarne un duplicato a ciascuno); in questo -caso è perfettamente logico aspettarsi che sulla stessa macchina più utenti -possano lanciare un programma che permetta loro di ricevere gli stessi dati. - -In questo caso utilizzando \const{SO\_REUSEADDR} si consente ad una +\func{bind} su un indirizzo ed una porta che sono già ``\textsl{legati}'' ad +un altro socket. Come accennato questo con TCP non è possibile, ed ha anche +poco senso pensare di mettere in ascolto due server sulla stessa porta. Se +però si prende in considerazione il traffico in \textit{multicast}, diventa +assolutamente normale che i pacchetti provenienti dal traffico in +\textit{multicast} possano essere ricevuti da più applicazioni o da diverse +istanze della stessa applicazione sulla stessa porte di un indirizzo di +\textit{multicast}. + +Un esempio classico è quello di uno streaming di dati (audio, video, ecc.) in +cui l'uso del \textit{multicast} consente di trasmettere un solo pacchetto da +recapitare a tutti i possibili destinatari (invece di inviarne un duplicato a +ciascuno); in questo caso è perfettamente logico aspettarsi che sulla stessa +macchina più utenti possano lanciare un programma che permetta loro di +ricevere gli stessi dati, e quindi effettuare un \textit{completely duplicate + binding}. + +In questo caso utilizzando \const{SO\_REUSEADDR} si può consentire ad una applicazione eseguire \func{bind} sulla stessa porta ed indirizzo usata da -un'altra, così che anche essa possa ricevere gli stessi pacchetti (chiaramente -la cosa non ha alcun senso per i socket TCP, ed infatti in questo tipo di -applicazione è normale l'uso del protocollo UDP). La regola è che quando si +un'altra, così che anche essa possa ricevere gli stessi pacchetti. Come detto +la cosa non è possibile con i socket TCP (per i quali il \textit{multicast} +comunque non è applicabile), ma lo è per quelli UDP che è il protocollo +normalmente in uso da parte di queste applicazioni. La regola è che quando si hanno più applicazioni che hanno eseguito \func{bind} sulla stessa porta, di tutti pacchetti destinati ad un indirizzo di \textit{broadcast} o di -\textit{multicast} viene inviata una copia a ciascuna applicazione. Non è +\textit{multicast} viene inviata una copia a ciascuna applicazione. Non è definito invece cosa accade qualora il pacchetto sia destinato ad un indirizzo normale (\textit{unicast}). % TODO documentare SO_REUSEPORT, vedi https://lwn.net/Articles/542260/ -Essendo questo un caso particolare in alcuni sistemi (come BSD) è stata -introdotta una opzione ulteriore, \const{SO\_REUSEPORT} che richiede che detta -opzione sia specificata per tutti i socket per i quali si vuole eseguire il -\textit{completely duplicate binding}. Nel caso di Linux questa opzione non -esisteva fino al kernel 3.9, ma il comportamento di \const{SO\_REUSEADDR} è -analogo, sarà cioè possibile effettuare un \textit{completely duplicate - binding} ed ottenere il successo di \func{bind} su un socket legato allo -stesso indirizzo e porta solo se il programma che ha eseguito per primo -\func{bind} su di essi ha impostato questa opzione. - -Questa restrizione permette di evitare parzialmente il cosiddetto \textit{port - stealing}, in cui un programma, usando \const{SO\_REUSEADDR}, può collegarsi -ad una porta già in uso e ricevere i pacchetti destinati ad un altro -programma; con questa caratteristica ciò è possibile soltanto se il primo -programma a consentirlo, avendo usato fin dall'inizio -\const{SO\_REUSEADDR}. Con l'introduzione di \const{SO\_REUSEPORT} una -ulteriore protezione deriva dalla richiesta che tutti i processi che usano -questa opzione per un socket abbiano lo stesso \ids{UID} effettivo. +\constbeg{SO\_REUSEPORT} + +Esistono però dei casi, in particolare per l'uso di programmi +\textit{multithreaded}, in cui può servire un \textit{completely duplicate + binding} anche per delle ordinarie connessioni TCP. Per supportare queste +esigenze a partire dal kernel 3.9 è stata introdotta un'altra opzione, +\const{SO\_REUSEPORT} (già presente in altri sistemi come BSD), che consente +di eseguire il \textit{completely duplicate binding}, fintanto che essa venga +specificata per tutti i socket interessati. Come per \const{SO\_REUSEADDR} +sarà possibile usare l'opzione su un socket legato allo stesso indirizzo e +porta solo se il programma che ha eseguito il primo \func{bind} ha impostato +questa opzione. + +Nel caso di \const{SO\_REUSEPORT} oltre al fatto che l'opzione deve essere +attivata sul socket prima di chiamare \func{bind} ed attiva su tutti i socket +con \textit{completely duplicate binding}, è richiesto pure che tutti i +processi che si mettono in ascolto sullo stesso indirizzo e porta abbiano lo +stesso \ids{UID} effettivo, per evitare che un altro utente possa ottenere il +relativo traffico (eseguendo quello che viene definito \textit{port hijacking} +o \textit{port stealing}). L'opzione utilizza per \param{optval} un intero +usato come valore logico. + +L'opzione si usa sia per socket TCP che UDP, nel primo caso consente un uso +distribuito di \func{accept} in una applicazione \textit{multithreaded} +passando un diverso \textit{listening socket} ad ogni thread, cosa che +migliora le prestazioni rispetto all'approccio tradizionale di usare un thread +per usare \func{accept} e distribuire le connessioni agli altri o avere più +thread che competono per usare \func{accept} sul socket. Nel caso di UDP +l'opzione consente di distribuire meglio i pacchetti su più processi o thread, +rispetto all'approccio tradizionale di far competere gli stessi per l'accesso +in ricezione al socket. + +% TODO documentare SO_REUSEPORT introdotta con il kernel 3.9, vedi +% http://git.kernel.org/linus/c617f398edd4db2b8567a28e899a88f8f574798d TODO: +% in cosa differisce da REUSEADDR? +\constend{SO\_REUSEPORT} \constend{SO\_REUSEADDR} @@ -3099,170 +3105,202 @@ manuale, nel caso specifico la documentazione si può consultare con \hline \const{IP\_ADD\_MEMBERSHIP} & &$\bullet$& &\struct{ip\_mreqn}& Si unisce a un gruppo di \textit{multicast}.\\ - \const{IP\_ADD\_SOURCE\_MEMBERSHIP} & &$\bullet$& &\struct{ip\_mreqn\_source}& + \const{IP\_ADD\_SOURCE\_MEMBERSHIP} & &$\bullet$& &\struct{ip\_mreq\_source}& Si unisce a un gruppo di \textit{multicast} per una sorgente.\\ + \const{IP\_BLOCK\_SOURCE} & &$\bullet$& &\struct{ip\_mreq\_source}& + Smette di ricevere dati di \textit{multicast} per una sorgente.\\ \const{IP\_DROP\_MEMBERSHIP}& &$\bullet$& &\struct{ip\_mreqn}& Si sgancia da un gruppo di \textit{multicast}.\\ + \const{IP\_DROP\_SOURCE\_MEMBERSHIP}& &$\bullet$& &\struct{ip\_mreq\_source}& + Si sgancia da un gruppo di \textit{multicast} per una sorgente.\\ + \const{IP\_FREEBIND} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& + Abilita il \textit{binding} a un indirizzo IP non locale ancora non assegnato.\\ \const{IP\_HDRINCL} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& Passa l'intestazione di IP nei dati.\\ \const{IP\_MINTTL} &$\bullet$&$\bullet$& &\texttt{int}& Imposta il valore minimo del TTL per i pacchetti accettati.\\ + \const{IP\_MSFILTER} &$\bullet$&$\bullet$& &\struct{ip\_msfilter}& + Accesso completo all'interfaccia per il filtraggio delle sorgenti + \textit{multicast}.\\ \const{IP\_MTU} &$\bullet$& & &\texttt{int}& Legge il valore attuale della MTU.\\ \const{IP\_MTU\_DISCOVER} &$\bullet$&$\bullet$& &\texttt{int}& Imposta il \textit{Path MTU Discovery}.\\ + \const{IP\_MULTICAST\_ALL} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& + Imposta l'interfaccia locale di un socket \textit{multicast}.\\ \const{IP\_MULTICAST\_IF} & &$\bullet$& &\struct{ip\_mreqn}& Imposta l'interfaccia locale di un socket \textit{multicast}.\\ \const{IP\_MULTICAST\_LOOP} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& Controlla il reinvio a se stessi dei dati di \textit{multicast}.\\ \const{IP\_MULTICAST\_TTL} &$\bullet$&$\bullet$& &\texttt{int}& Imposta il TTL per i pacchetti \textit{multicast}.\\ + \const{IP\_NODEFRAG} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& + Disabilita il riassemblaggio di pacchetti frammentati.\\ \const{IP\_OPTIONS} &$\bullet$&$\bullet$&&\texttt{void *}& %??? Imposta o riceve le opzioni di IP.\\ \const{IP\_PKTINFO} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& - Passa un messaggio di informazione.\\ + Abilita i messaggi di informazione.\\ \const{IP\_RECVERR} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& - Abilita la gestione degli errori.\\ + Abilita i messaggi di errore affidabili.\\ \const{IP\_RECVOPTS} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& Passa un messaggio con le opzioni IP.\\ + \const{IP\_RECVORIGSTADDR} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& + Abilita i messaggi con l'indirizzo di destinazione originale.\\ \const{IP\_RECVTOS} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& Passa un messaggio col campo TOS.\\ \const{IP\_RECVTTL} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& - Passa un messaggio col campo TTL.\\ + Abilita i messaggi col campo TTL.\\ \const{IP\_RETOPTS} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& - Passa un messaggio con le opzioni IP non trattate.\\ + Abilita i messaggi con le opzioni IP non trattate.\\ \const{IP\_ROUTER\_ALERT} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& Imposta l'opzione \textit{IP router alert} sui pacchetti.\\ \const{IP\_TOS} &$\bullet$&$\bullet$& &\texttt{int}& Imposta il valore del campo TOS.\\ + \const{IP\_TRANSPARENT} &$\bullet$&$\bullet$&$\bullet$&\texttt{int}& + Abilita un \textit{proxing} trasparente sul socket.\\ \const{IP\_TTL} &$\bullet$&$\bullet$& &\texttt{int}& Imposta il valore del campo TTL.\\ + \const{IP\_UNBLOCK\_SOURCE} & &$\bullet$& &\struct{ip\_mreq\_source}& + Ricomincia a ricevere dati di \textit{multicast} per una sorgente.\\ \hline \end{tabular} - \caption{Le opzioni disponibili al livello \const{SOL\_IP}.} + \caption{Le opzioni disponibili al livello \const{IPPROTO\_IP}.} \label{tab:sock_opt_iplevel} \end{table} -Se si vuole operare su queste opzioni generiche il livello -da utilizzare è \const{SOL\_IP} (o l'equivalente \constd{IPPROTO\_IP}); si è -riportato un elenco di queste opzioni in tab.~\ref{tab:sock_opt_iplevel}. Le -costanti indicanti le opzioni, e tutte le altre costanti ad esse collegate, -sono definite in \headfiled{netinet/ip.h}, ed accessibili includendo detto -file. +Se si vuole operare su queste opzioni generiche il livello da utilizzare è +\constd{IPPROTO\_IP} (o l'equivalente \const{SOL\_IP}); si è riportato un +elenco di queste opzioni in tab.~\ref{tab:sock_opt_iplevel}. Le costanti +indicanti le opzioni, e tutte le altre costanti ad esse collegate, sono +definite in \headfiled{netinet/ip.h}, ed accessibili includendo detto file. Le descrizioni riportate in tab.~\ref{tab:sock_opt_iplevel} sono estremamente succinte, una maggiore quantità di dettagli sulle varie opzioni è fornita nel seguente elenco: \begin{basedescript}{\desclabelwidth{2.0cm}\desclabelstyle{\nextlinelabel}} - - -\item[\constd{IP\_OPTIONS}] l'opzione permette di impostare o leggere le - opzioni del protocollo IP (si veda sez.~\ref{sec:IP_options}). L'opzione - prende come valore dell'argomento \param{optval} un puntatore ad un buffer - dove sono mantenute le opzioni, mentre \param{optlen} indica la dimensione - di quest'ultimo. Quando la si usa con \func{getsockopt} vengono lette le - opzioni IP utilizzate per la spedizione, quando la si usa con - \func{setsockopt} vengono impostate le opzioni specificate. L'uso di questa - opzione richiede una profonda conoscenza del funzionamento del protocollo, - torneremo in parte sull'argomento in sez.~\ref{sec:sock_IP_options}. - - -\item[\constd{IP\_PKTINFO}] Quando abilitata l'opzione permette di ricevere - insieme ai pacchetti un messaggio ancillare (vedi - sez.~\ref{sec:net_ancillary_data}) di tipo \const{IP\_PKTINFO} contenente - una struttura \struct{pktinfo} (vedi fig.~\ref{fig:sock_pktinfo_struct}) che - mantiene una serie di informazioni riguardo i pacchetti in arrivo. In - particolare è possibile conoscere l'interfaccia su cui è stato ricevuto un - pacchetto (nel campo \var{ipi\_ifindex}),\footnote{in questo campo viene - restituito il valore numerico dell'indice dell'interfaccia, - sez.~\ref{sec:sock_ioctl_netdevice}.} l'indirizzo locale da esso - utilizzato (nel campo \var{ipi\_spec\_dst}) e l'indirizzo remoto dello - stesso (nel campo \var{ipi\_addr}). +\item[\constd{IP\_ADD\_MEMBERSHIP}] L'opzione consente di unirsi ad gruppo di + \textit{multicast}, e può essere usata solo con \func{setsockopt}. + L'argomento \param{optval} in questo caso deve essere una struttura di tipo + \struct{ip\_mreqn}, illustrata in fig.~\ref{fig:ip_mreqn_struct}, che + permette di indicare, con il campo \var{imr\_multiaddr} l'indirizzo del + gruppo di \textit{multicast} a cui ci si vuole unire, con il campo + \var{imr\_address} l'indirizzo dell'interfaccia locale con cui unirsi al + gruppo di \textit{multicast} e con \var{imr\_ifindex} l'indice + dell'interfaccia da utilizzare (un valore nullo indica una interfaccia + qualunque). \begin{figure}[!htb] \footnotesize \centering - \begin{minipage}[c]{0.80\textwidth} - \includestruct{listati/pktinfo.h} + \begin{minipage}[c]{0.70\textwidth} + \includestruct{listati/ip_mreqn.h} \end{minipage} - \caption{La struttura \structd{pktinfo} usata dall'opzione - \const{IP\_PKTINFO} per ricavare informazioni sui pacchetti di un socket - di tipo \const{SOCK\_DGRAM}.} - \label{fig:sock_pktinfo_struct} + \caption{La struttura \structd{ip\_mreqn} utilizzata per unirsi a un gruppo di + \textit{multicast}.} + \label{fig:ip_mreqn_struct} \end{figure} +Questa struttura è presente a partire dal kernel 2.2, per compatibilità è +possibile utilizzare anche un argomento di tipo \struct{ip\_mreq}, presente +fino dal kernel 1.2, che differisce da essa soltanto per l'assenza del campo +\var{imr\_ifindex}; il kernel riconosce il tipo di struttura in base alla +differente dimensione passata in \param{optlen}. -L'opzione è utilizzabile solo per socket di tipo \const{SOCK\_DGRAM}. Questa è -una opzione introdotta con i kernel della serie 2.2.x, ed è specifica di -Linux;\footnote{non dovrebbe pertanto essere utilizzata se si ha a cuore la - portabilità.} essa permette di sostituire le opzioni \const{IP\_RECVDSTADDR} -e \const{IP\_RECVIF} presenti in altri Unix (la relativa informazione è quella -ottenibile rispettivamente dai campi \var{ipi\_addr} e \var{ipi\_ifindex} di -\struct{pktinfo}). +\item[\constd{IP\_ADD\_SOURCE\_MEMBERSHIP}] L'opzione consente di unirsi ad + gruppo di \textit{multicast}, ricevendo i dati solo da una sorgente + specifica; come \const{IP\_ADD\_MEMBERSHIP} può essere usata solo con + \func{setsockopt}. -L'opzione prende per \param{optval} un intero usato come valore logico, che -specifica soltanto se insieme al pacchetto deve anche essere inviato o -ricevuto il messaggio \const{IP\_PKTINFO} (vedi -sez.~\ref{sec:net_ancillary_data}); il messaggio stesso dovrà poi essere -letto o scritto direttamente con \func{recvmsg} e \func{sendmsg} (vedi -sez.~\ref{sec:net_sendmsg}). +\begin{figure}[!htb] + \footnotesize \centering + \begin{minipage}[c]{0.70\textwidth} + \includestruct{listati/ip_mreq_source.h} + \end{minipage} + \caption{La struttura \structd{ip\_mreqn} utilizzata per unirsi a un gruppo di + \textit{multicast} per una specifica sorgente.} + \label{fig:ip_mreq_source_struct} +\end{figure} +L'argomento \param{optval} in questo caso è una struttura +\struct{ip\_mreq\_source} illustrata in fig.~\ref{fig:ip_mreq_source_struct}, +dove il campo \var{imr\_multiaddr} è l'indirizzo del gruppo di +\textit{multicast}, il campo \var{imr\_interface} l'indirizzo dell'interfaccia +locale che deve essere usata per aggiungersi al gruppo di \textit{multicast} e +il campo \var{imr\_sourceaddr} l'indirizzo della sorgente da cui +l'applicazione vuole ricevere i dati. L'opzione può essere ripetuta più volte +per collegarsi a diverse sorgenti. + +\item[\constd{IP\_BLOCK\_SOURCE}] Questa opzione, disponibile dal kernel + 2.4.22, consente di smettere di ricevere dati di \textit{multicast} dalla + sorgente (e relativo gruppo) specificati dalla struttura + \struct{ip\_mreq\_source} (vedi fig.~\ref{fig:ip_mreq_source_struct}) + passata come argomento \param{optval}. L'opzione è utilizzabile solo se si è + già registrati nel gruppo di \textit{multicast} indicato con un precedente + utilizzo di \const{IP\_ADD\_MEMBERSHIP} o + \const{IP\_ADD\_SOURCE\_MEMBERSHIP}. -\item[\constd{IP\_RECVTOS}] Quando abilitata l'opzione permette di ricevere - insieme ai pacchetti un messaggio ancillare (vedi - sez.~\ref{sec:net_ancillary_data}) di tipo \const{IP\_TOS}, che contiene un - byte con il valore del campo \textit{Type of Service} dell'intestazione IP - del pacchetto stesso (vedi sez.~\ref{sec:IP_header}). Prende per +\item[\constd{IP\_DROP\_MEMBERSHIP}] Lascia un gruppo di \textit{multicast}, + prende per \param{optval} la stessa struttura \struct{ip\_mreqn} (o + \struct{ip\_mreq}) usata per \const{IP\_ADD\_MEMBERSHIP} (vedi + fig.~\ref{fig:ip_mreqn_struct}). + +\item[\constd{IP\_DROP\_SOURCE\_MEMBERSHIP}] Lascia un gruppo di + \textit{multicast} per una specifica sorgente, prende per \param{optval} la + stessa struttura \struct{ip\_mreq\_source} usata per + \const{IP\_ADD\_SOURCE\_MEMBERSHIP} (vedi + fig.~\ref{fig:ip_mreq_source_struct}). Se ci si è registrati per più + sorgenti nello stesso gruppo, si continuerà a ricevere dati sulle altre. Per + smettere di ricevere dati da tutte le sorgenti occorre usare l'opzione + \const{IP\_LEAVE\_GROUP}. + +\item[\constd{IP\_FREEBIND}] Se abilitata questa opzione, disponibile dal + kernel 2.4, consente di usare \func{bind} anche su un indirizzo IP non + locale o che ancora non è stato assegnato. Questo permette ad una + applicazione di mettersi in ascolto su un socket prima che l'interfaccia + sottostante o l'indirizzo che questa deve usare sia stato configurato. È + l'equivalente a livello di singolo socket dell'uso della \textit{sysctl} + \texttt{ip\_nonlocal\_bind} che vedremo in + sez.~\ref{sec:sock_ipv4_sysctl}. Prende per \param{optval} un intero usato come valore logico. -\item[\constd{IP\_RECVTTL}] Quando abilitata l'opzione permette di ricevere - insieme ai pacchetti un messaggio ancillare (vedi - sez.~\ref{sec:net_ancillary_data}) di tipo \const{IP\_RECVTTL}, contenente - un byte con il valore del campo \textit{Time to Live} dell'intestazione IP - (vedi sez.~\ref{sec:IP_header}). L'opzione richiede per \param{optval} un - intero usato come valore logico. L'opzione non è supportata per socket di - tipo \const{SOCK\_STREAM}. - -\item[\constd{IP\_RECVOPTS}] Quando abilitata l'opzione permette di ricevere - insieme ai pacchetti un messaggio ancillare (vedi - sez.~\ref{sec:net_ancillary_data}) di tipo \const{IP\_OPTIONS}, contenente - le opzioni IP del protocollo (vedi sez.~\ref{sec:IP_options}). Le - intestazioni di instradamento e le altre opzioni sono già riempite con i - dati locali. L'opzione richiede per \param{optval} un intero usato come - valore logico. L'opzione non è supportata per socket di tipo - \const{SOCK\_STREAM}. - -\item[\constd{IP\_RETOPTS}] Identica alla precedente \const{IP\_RECVOPTS}, ma - in questo caso restituisce i dati grezzi delle opzioni, senza che siano - riempiti i capi di instradamento e le marche temporali. L'opzione richiede - per \param{optval} un intero usato come valore logico. L'opzione non è - supportata per socket di tipo \const{SOCK\_STREAM}. - -\item[\constd{IP\_TOS}] L'opzione consente di leggere o impostare il campo - \textit{Type of Service} dell'intestazione IP (per una trattazione più - dettagliata, che riporta anche i valori possibili e le relative costanti di - definizione si veda sez.~\ref{sec:IP_header}) che permette di indicare le - priorità dei pacchetti. Se impostato il valore verrà mantenuto per tutti i - pacchetti del socket; alcuni valori (quelli che aumentano la priorità) - richiedono i privilegi di amministrazione con la \textit{capability} - \const{CAP\_NET\_ADMIN}. +\item[\constd{IP\_HDRINCL}] Se viene abilitata questa opzione, presente dal + kernel 2.0, l'utente deve fornire lui stesso l'intestazione del protocollo + IP in testa ai propri dati. L'opzione è valida soltanto per socket di tipo + \const{SOCK\_RAW}, e quando utilizzata eventuali valori impostati con + \const{IP\_OPTIONS}, \const{IP\_TOS} o \const{IP\_TTL} sono ignorati. In + ogni caso prima della spedizione alcuni campi dell'intestazione vengono + comunque modificati dal kernel, torneremo sull'argomento in + sez.~\ref{sec:socket_raw}. Prende per \param{optval} un intero usato come + valore logico. + +\item[\constd{IP\_MSFILTER}] L'opzione, introdotta con il kernel 2.4.22, + fornisce accesso completo all'interfaccia per il filtraggio delle sorgenti + di \textit{multicast} (il cosiddetto \textit{multicast source filtering}, + definito dall'\href{http://www.ietf.org/rfc/rfc3376.txt}{RFC~3376}). - Il campo TOS è di 8 bit e l'opzione richiede per \param{optval} un intero - che ne contenga il valore. Sono definite anche alcune costanti che - definiscono alcuni valori standardizzati per il \textit{Type of Service}, - riportate in tab.~\ref{tab:IP_TOS_values}, il valore di default usato da - Linux è \const{IPTOS\_LOWDELAY}, ma esso può essere modificato con le - funzionalità del cosiddetto \textit{Advanced Routing}. Si ricordi che la - priorità dei pacchetti può essere impostata anche in maniera indipendente - dal protocollo utilizzando l'opzione \const{SO\_PRIORITY} illustrata in - sez.~\ref{sec:sock_generic_options}. +\begin{figure}[!htb] + \footnotesize \centering + \begin{minipage}[c]{0.70\textwidth} + \includestruct{listati/ip_msfilter.h} + \end{minipage} + \caption{La struttura \structd{ip\_msfilter} utilizzata per il + \textit{multicast source filtering}.} + \label{fig:ip_msfilter_struct} +\end{figure} -\item[\constd{IP\_TTL}] L'opzione consente di leggere o impostare per tutti i - pacchetti associati al socket il campo \textit{Time to Live} - dell'intestazione IP che indica il numero massimo di \textit{hop} (passaggi - da un router ad un altro) restanti al paccheto (per una trattazione più - estesa si veda sez.~\ref{sec:IP_header}). Il campo TTL è di 8 bit e - l'opzione richiede che \param{optval} sia un intero, che ne conterrà il - valore. +L'argomento \param{optval} è una struttura \struct{ip\_msfilter} illustrata in +fig.~\ref{fig:ip_msfilter_struct}, il campo \var{imsf\_multiaddr} è +l'indirizzo del gruppo di \textit{multicast}, il campo \var{imsf\_interface} +l'indirizzo dell'interfaccia locale, il campo \var{imsf\_mode} indica la +modalità di filtraggio e con i campi \var{imsf\_numsrc} e \var{imsf\_slist} +rispettivamente la lunghezza della lista, e la lista stessa, degli indirizzi +sorgente. + +Come ausilio all'uso di questa opzione sono disponibili le macro +\macro{MCAST\_INCLUDE} e \macro{MCAST\_EXCLUDE} che si possono usare per +\var{imsf\_mode}. Inoltre si può usare la macro +\macro{IP\_MSFILTER\_SIZE}\texttt{(\textsf{n})} per determinare il valore +di \param{optlen} con una struttura \struct{ip\_msfilter} contenente +\texttt{\textsf{n}} sorgenti in \var{imsf\_slist}. \item[\constd{IP\_MINTTL}] L'opzione, introdotta con il kernel 2.6.34, imposta un valore minimo per il campo \textit{Time to Live} dei pacchetti associati @@ -3282,26 +3320,27 @@ sez.~\ref{sec:net_sendmsg}). senza carico aggiuntivo sulla CPU (che altrimenti dovrebbe calcolare una checksum).} -\item[\constd{IP\_HDRINCL}] Se abilitata l'utente deve fornire lui stesso - l'intestazione IP in cima ai propri dati. L'opzione è valida soltanto per - socket di tipo \const{SOCK\_RAW}, e quando utilizzata eventuali valori - impostati con \const{IP\_OPTIONS}, \const{IP\_TOS} o \const{IP\_TTL} sono - ignorati. In ogni caso prima della spedizione alcuni campi - dell'intestazione vengono comunque modificati dal kernel, torneremo - sull'argomento in sez.~\ref{sec:socket_raw} +\itindbeg{Path~MTU} +\item[\constd{IP\_MTU}] Permette di leggere il valore della \textit{Path MTU} + di percorso del socket. L'opzione richiede per \param{optval} un intero che + conterrà il valore della \textit{Path MTU} in byte. Questa è una opzione + introdotta con i kernel della serie 2.2.x, ed è specifica di Linux. -\item[\constd{IP\_RECVERR}] Questa è una opzione introdotta con i kernel della - serie 2.2.x, ed è specifica di Linux. Essa permette di usufruire di un - meccanismo affidabile per ottenere un maggior numero di informazioni in caso - di errori. Se l'opzione è abilitata tutti gli errori generati su un socket - vengono memorizzati su una coda, dalla quale poi possono essere letti con - \func{recvmsg} (vedi sez.~\ref{sec:net_sendmsg}) come messaggi ancillari - (torneremo su questo in sez.~\ref{sec:net_ancillary_data}) di tipo - \const{IP\_RECVERR}. L'opzione richiede per \param{optval} un intero usato - come valore logico e non è applicabile a socket di tipo - \const{SOCK\_STREAM}. + È tramite questa opzione che un programma può leggere, quando si è avuto un + errore di \errval{EMSGSIZE}, il valore della MTU corrente del socket. Si + tenga presente che per poter usare questa opzione, oltre ad avere abilitato + la scoperta della \textit{Path MTU}, occorre che il socket sia stato + esplicitamente connesso con \func{connect}. + + Ad esempio con i socket UDP si potrà ottenere una stima iniziale della + \textit{Path MTU} eseguendo prima una \func{connect} verso la destinazione, + e poi usando \func{getsockopt} con questa opzione. Si può anche avviare + esplicitamente il procedimento di scoperta inviando un pacchetto di grosse + dimensioni (che verrà scartato) e ripetendo l'invio coi dati aggiornati. Si + tenga infine conto che durante il procedimento i pacchetti iniziali possono + essere perduti, ed è compito dell'applicazione gestirne una eventuale + ritrasmissione. -\itindbeg{Path~MTU} \item[\constd{IP\_MTU\_DISCOVER}] Questa è una opzione introdotta con i kernel della serie 2.2.x, ed è specifica di Linux. L'opzione permette di scrivere o leggere le impostazioni della modalità usata per la determinazione della @@ -3326,6 +3365,7 @@ sez.~\ref{sec:net_sendmsg}). \constd{IP\_PMTUDISC\_DO} &2& Esegue la procedura di determinazione della \textit{Path MTU} come richiesto dall'\href{http://www.ietf.org/rfc/rfc1191.txt}{RFC~1191}.\\ + \constd{IP\_PMTUDISC\_PROBE}&?& .\\ \hline \end{tabular} \caption{Valori possibili per l'argomento \param{optval} di @@ -3344,43 +3384,11 @@ sez.~\ref{sec:net_sendmsg}). della MTU con un errore di \errval{EMSGSIZE}.\footnote{in caso contrario la trasmissione del pacchetto sarebbe effettuata, ottenendo o un fallimento successivo della trasmissione, o la frammentazione dello stesso.} - -\item[\constd{IP\_MTU}] Permette di leggere il valore della \textit{Path MTU} - di percorso del socket. L'opzione richiede per \param{optval} un intero che - conterrà il valore della \textit{Path MTU} in byte. Questa è una opzione - introdotta con i kernel della serie 2.2.x, ed è specifica di Linux. - - È tramite questa opzione che un programma può leggere, quando si è avuto un - errore di \errval{EMSGSIZE}, il valore della MTU corrente del socket. Si - tenga presente che per poter usare questa opzione, oltre ad avere abilitato - la scoperta della \textit{Path MTU}, occorre che il socket sia stato - esplicitamente connesso con \func{connect}. - - Ad esempio con i socket UDP si potrà ottenere una stima iniziale della - \textit{Path MTU} eseguendo prima una \func{connect} verso la destinazione, - e poi usando \func{getsockopt} con questa opzione. Si può anche avviare - esplicitamente il procedimento di scoperta inviando un pacchetto di grosse - dimensioni (che verrà scartato) e ripetendo l'invio coi dati aggiornati. Si - tenga infine conto che durante il procedimento i pacchetti iniziali possono - essere perduti, ed è compito dell'applicazione gestirne una eventuale - ritrasmissione. - \itindend{Path~MTU} -\item[\constd{IP\_ROUTER\_ALERT}] Questa è una opzione introdotta con i - kernel della serie 2.2.x, ed è specifica di Linux. Prende per - \param{optval} un intero usato come valore logico. Se abilitata - passa tutti i pacchetti con l'opzione \textit{IP Router Alert} (vedi - sez.~\ref{sec:IP_options}) che devono essere inoltrati al socket - corrente. Può essere usata soltanto per socket di tipo raw. - -\item[\constd{IP\_MULTICAST\_TTL}] L'opzione permette di impostare o leggere il - valore del campo TTL per i pacchetti \textit{multicast} in uscita associati - al socket. È importante che questo valore sia il più basso possibile, ed il - default è 1, che significa che i pacchetti non potranno uscire dalla rete - locale. Questa opzione consente ai programmi che lo richiedono di superare - questo limite. L'opzione richiede per - \param{optval} un intero che conterrà il valore del TTL. +\item[\constd{IP\_MULTICAST\_IF}] Imposta l'interfaccia locale per l'utilizzo + del \textit{multicast}, ed utilizza come \param{optval} le stesse strutture + \struct{ip\_mreqn} o \struct{ip\_mreq} delle due precedenti opzioni. \item[\constd{IP\_MULTICAST\_LOOP}] L'opzione consente di decidere se i dati che si inviano su un socket usato con il \textit{multicast} vengano ricevuti @@ -3393,43 +3401,138 @@ sez.~\ref{sec:net_sendmsg}). disponibili in locale l'uso di questa opzione permette di disabilitare questo tipo di traffico. -\item[\constd{IP\_ADD\_MEMBERSHIP}] L'opzione consente di unirsi ad gruppo di - \textit{multicast}, e può essere usata solo con \func{setsockopt}. - L'argomento \param{optval} in questo caso deve essere una struttura di tipo - \struct{ip\_mreqn}, illustrata in fig.~\ref{fig:ip_mreqn_struct}, che - permette di indicare, con il campo \var{imr\_multiaddr} l'indirizzo del - gruppo di \textit{multicast} a cui ci si vuole unire, con il campo - \var{imr\_address} l'indirizzo dell'interfaccia locale con cui unirsi al - gruppo di \textit{multicast} e con \var{imr\_ifindex} l'indice - dell'interfaccia da utilizzare (un valore nullo indica una interfaccia - qualunque). +\item[\constd{IP\_MULTICAST\_TTL}] L'opzione permette di impostare o leggere il + valore del campo TTL per i pacchetti \textit{multicast} in uscita associati + al socket. È importante che questo valore sia il più basso possibile, ed il + default è 1, che significa che i pacchetti non potranno uscire dalla rete + locale. Questa opzione consente ai programmi che lo richiedono di superare + questo limite. L'opzione richiede per + \param{optval} un intero che conterrà il valore del TTL. +% TODO chiarire quale è la struttura \struct{ip\_mreq} - Per compatibilità è possibile utilizzare anche un argomento di tipo - \struct{ip\_mreq}, una precedente versione di \struct{ip\_mreqn}, che - differisce da essa soltanto per l'assenza del campo \var{imr\_ifindex}. +\item[\constd{IP\_OPTIONS}] l'opzione permette di impostare o leggere le + opzioni del protocollo IP (si veda sez.~\ref{sec:IP_options}). L'opzione + prende come valore dell'argomento \param{optval} un puntatore ad un buffer + dove sono mantenute le opzioni, mentre \param{optlen} indica la dimensione + di quest'ultimo. Quando la si usa con \func{getsockopt} vengono lette le + opzioni IP utilizzate per la spedizione, quando la si usa con + \func{setsockopt} vengono impostate le opzioni specificate. L'uso di questa + opzione richiede una profonda conoscenza del funzionamento del protocollo, + torneremo in parte sull'argomento in sez.~\ref{sec:sock_IP_options}. + +\item[\constd{IP\_PKTINFO}] Quando abilitata l'opzione permette di ricevere + insieme ai pacchetti un messaggio ancillare (vedi + sez.~\ref{sec:net_ancillary_data}) di tipo \const{IP\_PKTINFO} contenente + una struttura \struct{pktinfo} (vedi fig.~\ref{fig:sock_pktinfo_struct}) che + mantiene una serie di informazioni riguardo i pacchetti in arrivo. In + particolare è possibile conoscere l'interfaccia su cui è stato ricevuto un + pacchetto (nel campo \var{ipi\_ifindex}),\footnote{in questo campo viene + restituito il valore numerico dell'indice dell'interfaccia, + sez.~\ref{sec:sock_ioctl_netdevice}.} l'indirizzo locale da esso + utilizzato (nel campo \var{ipi\_spec\_dst}) e l'indirizzo remoto dello + stesso (nel campo \var{ipi\_addr}). \begin{figure}[!htb] \footnotesize \centering \begin{minipage}[c]{0.80\textwidth} - \includestruct{listati/ip_mreqn.h} + \includestruct{listati/pktinfo.h} \end{minipage} - \caption{La struttura \structd{ip\_mreqn} utilizzata dalle opzioni dei - socket per le operazioni concernenti l'appartenenza ai gruppi di - \textit{multicast}.} - \label{fig:ip_mreqn_struct} + \caption{La struttura \structd{pktinfo} usata dall'opzione + \const{IP\_PKTINFO} per ricavare informazioni sui pacchetti di un socket + di tipo \const{SOCK\_DGRAM}.} + \label{fig:sock_pktinfo_struct} \end{figure} -\item[\constd{IP\_DROP\_MEMBERSHIP}] Lascia un gruppo di \textit{multicast}, - prende per \param{optval} la stessa struttura \struct{ip\_mreqn} (o - \struct{ip\_mreq}) usata anche per \const{IP\_ADD\_MEMBERSHIP}. -\item[\constd{IP\_MULTICAST\_IF}] Imposta l'interfaccia locale per l'utilizzo - del \textit{multicast}, ed utilizza come \param{optval} le stesse strutture - \struct{ip\_mreqn} o \struct{ip\_mreq} delle due precedenti opzioni. +L'opzione è utilizzabile solo per socket di tipo \const{SOCK\_DGRAM}. Questa è +una opzione introdotta con i kernel della serie 2.2.x, ed è specifica di +Linux;\footnote{non dovrebbe pertanto essere utilizzata se si ha a cuore la + portabilità.} essa permette di sostituire le opzioni \const{IP\_RECVDSTADDR} +e \const{IP\_RECVIF} presenti in altri Unix (la relativa informazione è quella +ottenibile rispettivamente dai campi \var{ipi\_addr} e \var{ipi\_ifindex} di +\struct{pktinfo}). -% TODO chiarire quale è la struttura \struct{ip\_mreq} +L'opzione prende per \param{optval} un intero usato come valore logico, che +specifica soltanto se insieme al pacchetto deve anche essere inviato o +ricevuto il messaggio \const{IP\_PKTINFO} (vedi +sez.~\ref{sec:net_ancillary_data}); il messaggio stesso dovrà poi essere +letto o scritto direttamente con \func{recvmsg} e \func{sendmsg} (vedi +sez.~\ref{sec:net_sendmsg}). + +\item[\constd{IP\_RECVERR}] Questa è una opzione introdotta con i kernel della + serie 2.2.x, ed è specifica di Linux. Essa permette di usufruire di un + meccanismo affidabile per ottenere un maggior numero di informazioni in caso + di errori. Se l'opzione è abilitata tutti gli errori generati su un socket + vengono memorizzati su una coda, dalla quale poi possono essere letti con + \func{recvmsg} (vedi sez.~\ref{sec:net_sendmsg}) come messaggi ancillari + (torneremo su questo in sez.~\ref{sec:net_ancillary_data}) di tipo + \const{IP\_RECVERR}. L'opzione richiede per \param{optval} un intero usato + come valore logico e non è applicabile a socket di tipo + \const{SOCK\_STREAM}. + +\item[\constd{IP\_RECVOPTS}] Quando abilitata l'opzione permette di ricevere + insieme ai pacchetti un messaggio ancillare (vedi + sez.~\ref{sec:net_ancillary_data}) di tipo \const{IP\_OPTIONS}, contenente + le opzioni IP del protocollo (vedi sez.~\ref{sec:IP_options}). Le + intestazioni di instradamento e le altre opzioni sono già riempite con i + dati locali. L'opzione richiede per \param{optval} un intero usato come + valore logico. L'opzione non è supportata per socket di tipo + \const{SOCK\_STREAM}. + +\item[\constd{IP\_RECVTOS}] Quando abilitata l'opzione permette di ricevere + insieme ai pacchetti un messaggio ancillare (vedi + sez.~\ref{sec:net_ancillary_data}) di tipo \const{IP\_TOS}, che contiene un + byte con il valore del campo \textit{Type of Service} dell'intestazione IP + del pacchetto stesso (vedi sez.~\ref{sec:IP_header}). Prende per + \param{optval} un intero usato come valore logico. + +\item[\constd{IP\_RECVTTL}] Quando abilitata l'opzione permette di ricevere + insieme ai pacchetti un messaggio ancillare (vedi + sez.~\ref{sec:net_ancillary_data}) di tipo \const{IP\_RECVTTL}, contenente + un byte con il valore del campo \textit{Time to Live} dell'intestazione IP + (vedi sez.~\ref{sec:IP_header}). L'opzione richiede per \param{optval} un + intero usato come valore logico. L'opzione non è supportata per socket di + tipo \const{SOCK\_STREAM}. + +\item[\constd{IP\_RETOPTS}] Identica alla precedente \const{IP\_RECVOPTS}, ma + in questo caso restituisce i dati grezzi delle opzioni, senza che siano + riempiti i capi di instradamento e le marche temporali. L'opzione richiede + per \param{optval} un intero usato come valore logico. L'opzione non è + supportata per socket di tipo \const{SOCK\_STREAM}. +\item[\constd{IP\_ROUTER\_ALERT}] Questa è una opzione introdotta con i + kernel della serie 2.2.x, ed è specifica di Linux. Prende per + \param{optval} un intero usato come valore logico. Se abilitata + passa tutti i pacchetti con l'opzione \textit{IP Router Alert} (vedi + sez.~\ref{sec:IP_options}) che devono essere inoltrati al socket + corrente. Può essere usata soltanto per socket di tipo raw. +\item[\constd{IP\_TOS}] L'opzione consente di leggere o impostare il campo + \textit{Type of Service} dell'intestazione IP (per una trattazione più + dettagliata, che riporta anche i valori possibili e le relative costanti di + definizione si veda sez.~\ref{sec:IP_header}) che permette di indicare le + priorità dei pacchetti. Se impostato il valore verrà mantenuto per tutti i + pacchetti del socket; alcuni valori (quelli che aumentano la priorità) + richiedono i privilegi di amministrazione con la \textit{capability} + \const{CAP\_NET\_ADMIN}. + + Il campo TOS è di 8 bit e l'opzione richiede per \param{optval} un intero + che ne contenga il valore. Sono definite anche alcune costanti che + definiscono alcuni valori standardizzati per il \textit{Type of Service}, + riportate in tab.~\ref{tab:IP_TOS_values}, il valore di default usato da + Linux è \const{IPTOS\_LOWDELAY}, ma esso può essere modificato con le + funzionalità del cosiddetto \textit{Advanced Routing}. Si ricordi che la + priorità dei pacchetti può essere impostata anche in maniera indipendente + dal protocollo utilizzando l'opzione \const{SO\_PRIORITY} illustrata in + sez.~\ref{sec:sock_generic_options}. + +\item[\constd{IP\_TTL}] L'opzione consente di leggere o impostare per tutti i + pacchetti associati al socket il campo \textit{Time to Live} + dell'intestazione IP che indica il numero massimo di \textit{hop} (passaggi + da un router ad un altro) restanti al paccheto (per una trattazione più + estesa si veda sez.~\ref{sec:IP_header}). Il campo TTL è di 8 bit e + l'opzione richiede che \param{optval} sia un intero, che ne conterrà il + valore. \end{basedescript} @@ -4560,7 +4663,9 @@ di manuale accessibile con \texttt{man 7 ip}, sono i seguenti: \item[\sysctlrelfiled{net/ipv4}{ip\_nonlocal\_bind}] se abilitato rende possibile ad una applicazione eseguire \func{bind} anche su un indirizzo che non è presente su nessuna interfaccia locale. Prende un valore logico e di - default è disabilitato. + default è disabilitato. La funzionalità può essere abilitata a livello di + singolo socket con l'opzione \const{IP\_FREEBIND} illustrata in + sez.~\ref{sec:sock_ipv4_options}. Questo può risultare utile per applicazioni particolari (come gli \textit{sniffer}) che hanno la necessità di ricevere pacchetti anche non