Corretto titolo della sezione IPC, e iniziato a scrivere funzione generica
authorSimone Piccardi <piccardi@gnulinux.it>
Sat, 4 Dec 2004 16:08:27 +0000 (16:08 +0000)
committerSimone Piccardi <piccardi@gnulinux.it>
Sat, 4 Dec 2004 16:08:27 +0000 (16:08 +0000)
per connettere un socket.

ipc.tex
sockctrl.tex
sources/sockconn.c [new file with mode: 0644]

diff --git a/ipc.tex b/ipc.tex
index 4168b12..22d6e76 100644 (file)
--- a/ipc.tex
+++ b/ipc.tex
@@ -774,7 +774,7 @@ dello stesso non all'interno di uno stesso processo, ma fra processi distinti
 (torneremo su questa funzionalità in sez.~\ref{sec:xxx_fd_passing}).
 
 
-\section{La comunicazione fra processi di System V}
+\section{Il sistema di comunicazione fra processi di System V}
 \label{sec:ipc_sysv}
 
 Benché le pipe e le fifo siano ancora ampiamente usate, esse scontano il
@@ -786,7 +786,7 @@ Per questo nello sviluppo di System V vennero introdotti una serie di nuovi
 oggetti per la comunicazione fra processi ed una nuova interfaccia di
 programmazione, che fossero in grado di garantire una maggiore flessibilità.
 In questa sezione esamineremo come Linux supporta quello che viene chiamato il
-\textsl{Sistema di comunicazione inter-processo} di System V, cui da qui in
+\textsl{Sistema di comunicazione fra processi} di System V, cui da qui in
 avanti faremo riferimento come \textit{SysV IPC} (dove IPC è la sigla di
 \textit{Inter-Process Comunication}).
 
@@ -3226,7 +3226,7 @@ sez.~\ref{sec:ipc_sysv_shm} che possa restituisca i risultati via rete.
 
 
 
-\section{La comunicazione fra processi di POSIX}
+\section{Il sistema di comunicazione fra processi di POSIX}
 \label{sec:ipc_posix}
 
 Per superare i numerosi problemi del \textit{SysV IPC}, evidenziati per i suoi
index 62fd3d7..b4b229e 100644 (file)
@@ -1538,7 +1538,7 @@ nello stesso ordine in cui vengono inviati dal server DNS. In particolare
 nulla garantisce che vengano forniti prima i dati relativi ai servizi di un
 determinato protocollo o tipo di socket, se ne sono presenti di diversi.  Se
 allora utilizziamo il nostro programma potremo verificare il risultato:
-\begin{verbatim}
+\begin{Verbatim}
 [piccardi@gont sources]$ ./mygetaddr -c  gapil.truelite.it echo
 Canonical name sources2.truelite.it
 IPv4 address:
@@ -1549,7 +1549,7 @@ IPv4 address:
         Indirizzo 62.48.34.25
         Protocollo 17
         Porta 7
-\end{verbatim}
+\end{Verbatim}
 %$
 
 Una volta estratti i risultati dalla \textit{linked list} puntata da
@@ -1650,14 +1650,25 @@ indirizzi indicati dagli argomenti \param{host} e \param{serv} come stringhe
 terminate dal carattere NUL, a meno che queste non debbano essere troncate
 qualora la loro dimensione ecceda quelle specificate dagli argomenti
 \param{hostlen} e \param{servlen}. Sono comunque definite le due costanti
-\const{NI\_MAXHOST} e \const{NI\_MAXSERV}\footnote{le due costanti sono
-  definite in \file{netdb.h} ed hanno rispettivamente il valore 1024 e 12.}
-che possono essere utilizzate come limiti massimi.  In caso di errore viene
-restituito invece un codice che assume gli stessi valori illustrati in
+\const{NI\_MAXHOST} e \const{NI\_MAXSERV}\footnote{in Linux le due costanti
+  sono definite in \file{netdb.h} ed hanno rispettivamente il valore 1024 e
+  12.}  che possono essere utilizzate come limiti massimi.  In caso di errore
+viene restituito invece un codice che assume gli stessi valori illustrati in
 tab.~\ref{tab:addrinfo_error_code}.
 
 A questo punto possiamo fornire degli esempi di utilizzo diretto della nuova
-interfaccia, adottandola per rendere i nostri client 
+interfaccia, adottandola per le precedenti implementazioni del client e del
+server per il servizio \textit{echo}; dato che l'uso delle funzioni (in
+particolare di \func{getaddrinfo} è piuttosto complesso, prevedendo una
+impostazione manuale dell'argomento \param{hints}, provvederemo una
+interfaccia semplificata per i due casi visti finora, quello in cui si
+specifica nel client un indirizzo remoto per la connessione al server, e
+quello in cui si specifica nel server un indirizzo locale su cui porsi in
+ascolto.
+
+La prima funzione è allora \func{sockconn}, che richiede la risoluzione di un
+indirizzo e di un servizio per connettere un socket allo stesso. 
+
 
 
 \section{Le opzioni dei socket}
diff --git a/sources/sockconn.c b/sources/sockconn.c
new file mode 100644 (file)
index 0000000..c162474
--- /dev/null
@@ -0,0 +1,65 @@
+/* sockconn.c
+ * 
+ * Copyright (C) 2004 Simone Piccardi
+ * 
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or (at
+ * your option) any later version.
+ * 
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ * 
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+/****************************************************************
+ *
+ * Routine sockconn
+ * Return a connected socket given hostname, service, and socket type
+ *
+ * Author: Simone Piccardi
+ * Dec. 2004
+ *
+ * $Id$ 
+ *
+ ****************************************************************/
+#include <arpa/inet.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
+#include <errno.h>
+
+int sockconn(char *host, char *serv, int prot, int type) 
+{
+    struct addrinfo hint, *addr;
+    int res;
+    int sock
+    /* initialize hint */
+    memset(&hint, 0, sizeof(hint)); 
+    hint.ai_family = PF_UNSPEC;
+    hint.ai_protocol = prot;
+    hint.ai_socktype = type;
+    res = getaddrinfo(host, serv, &hint, &addr);
+    if (res != 0) {
+       printf("sockconn cannot resolve host %s, service %s,
+                protocol %d: %s\n", host, serv, prot, gai_strerror(res));
+       errno = 0;
+       return -1;
+    }
+    sock = socket(addr->ai_family, addr->ai_socktype, addr->ai_protocol);
+    if (sock < 0) {
+       perror("sockconn cannot create socket\n");
+       return sock;
+    }
+    res = connect(sock, addr->ai_addr, addr->ai_addrlen);
+    if (res < 0) {
+       perror("sockconn cannot connect socket\n");
+       return res;
+    }
+    freeaddrinfo(addr);
+    return sock;
+}
+