Una rete TCP/IP

Transcript

Una rete TCP/IP
Introduzione
alla programmazione C di socket
(testo di riferimento :
M. J. Donahoo, K. L. Calvert,
TCP/IP Sockets in C: Practical Guide for Programmers.
Morgan Kaufman Publishers. )
A.A. 2005/06
Dott.ssa Valeria Carofiglio
Una rete TCP/IP
Organizzazione a livelli:
relazione tra protocolli, applicazioni e API socket
Applicazione
Applicazione
Implementazione
dei protocolli
(S.O.)
Socket API
Socket API
TCP
IP
HOST
TCP
canale
IP
Es: ethernet
Router
canale
Dott.ssa Valeria Carofiglio
IP
HOST
1
Indirizzi
La comunicazione tra programmi è possibile se si conosce l’indirizzo dei
programmi che devono comunicare
Indirizzo Internet
Numero di porta
(usato da IP)
(interpretato da TCP o UDP)
• identificatori a 32 bit
• notazione: 193.204.187.194
• identifica una interfaccia
• identificatori a 16 bit (sempre in
relazione ad un IP)
• range:
•Well-Known: 0Æ1023
•Registered: 1024 Æ 49151
•Dynamic (private) 49152Æ65535
193.204.187.194
http://www.iana.org/assignments/port-numbers
209.134.xxx.xxx
Aplicazione www
Porta
• www.di.uniba.it Æ 193.204.1..
E-mail
80
23
193.204.187.194
Dott.ssa Valeria Carofiglio
Una Socket: una visione di insieme
• Una socket è un dispositivo che consente la comunicazione
(trasferimento di dati) tra due processi su internet, in una LAN, su
un singolo computer…
• Esistono varie famiglie di socket. Ogni famiglia riunisce i socket che utilizzano
gli stessi protocolli (Protocol Family) sottostanti, supporta un sottoinsieme di
stili di comunicazione e possiede un proprio formato di indirizzamento (Address
Family)
Alcuni esempi di famiglie
• Unix Domain sockets: file in una directory di un computer local host.
Consentono il trasferimento di dati tra processi sulla stessa macchina Unix
• Internet socket (AF_INET): consentono il trasferimento di dati tra processi
posti su macchine remote connesse tramite una LAN o Internet
Dott.ssa Valeria Carofiglio
2
Una Socket: una visione di insieme
(cont.)
• Il tipo di una socket definisce una modalità di
comunicazione che una socket usa per inviare dati:
– Streaming Socket (SOCK_STREAM): Fornisce una connessione
sequenziale, affidabile e full-duplex. Il protocollo TCP è basato su
questo tipo di socket.
– Datagram socket (SOCK_DGRAM): Supporta i datagrammi (privo di
connessione, messaggi inaffidabili di una lunghezza massima prefissata).
Il protocollo UDP è basato su questo tipo di socket
Osserviamo che:
AF_INET + SOCK_STREAM determineranno una connessione TCP,
AF_INET + SOCK_DGRAM determineranno una trasmissione UDP
Dott.ssa Valeria Carofiglio
Socket, Protocolli e Porte
su un singolo host
Una socket che usa la famiglia di protocolli TCP/IP è univocamente
determinata da un indirizzo internet, un protocollo di comunicazione (TCP o
UDP) e un numero di porta
Applicazioni
Applicazioni
…
Socket TCP
Porte TCP
1
2
…
……
65535 1
2
……
TCP
Socket UDP
Porte UDP
65535
UDP
IP
Host
Sockets bound to ports
Dott.ssa Valeria Carofiglio
Descriptor reference
3
Una Socket: una visione di insieme
(cont.)
• Nel gergo socket uno dei processi che comunicano è chiamato
Server e l’altro Client. Tra i due processi il server è quello che ha
controllo maggiore, poiché è il processo che inizialmente crea la
socket. Più client possono comunicare attraverso la stessa socket,
ma solo un server può essere associato ad una definita socket.
Il fatto che un programma agisca come client o come server
determina un differente uso delle API Socket
• Il client ha bisogno di conoscere l’indirizzo del server (ma non il
viceversa)
• Il Server può apprendere informazioni sull’indirizzo del client una
volta stabilita la connessione
Dott.ssa Valeria Carofiglio
Programmazione socket
Lo sviluppatore ha il controllo di tutto ciò che sta sul lato del livello
applicativo della socket, ma ha poco controllo sul lato a livello di trasporto
(alcuni parametri)
Livello di Applicazione
…
…
Livello di trasporto
1
2
……
65535 1
TCP
2
……
65535
UDP
IP
Host
Dott.ssa Valeria Carofiglio
4
Programmazione socket (cont.)
Il client deve contattare il server
• Il programma server deve essere
in esecuzione come processo
• Il programma server deve avere
una porta (socket) che dia il
benvenuto al contatto iniziale
stabilito da un processo client in
esecuzione
• Durante l’handshake a tre vie: il
TCP server crea un nuova socket
(dedicata a quel particolare client
– socket di connessione)
Il client contatta il server tramite:
• la creazione di una socket locale
• la specifica di un indirizzo del
processo server (IP, numero di
porta relativi al processo)
• Dopo la creazione della socket nel
client: TCP avvia un handshake a
tre vie e stabilisce una connessione
TCP con il server
Dott.ssa Valeria Carofiglio
Interazione TCP Client/Server
1.
2.
3.
4.
5.
1.
2.
3.
4.
5.
Server
(Inizializzare una WSA)
Creare una socket
Assegnare un local address alla
socket
Settare la socket all’ascolto
Iterativamente:
a. Accettare una nuova
connessione
b. Inviare e ricevere dati
c. Chiudere la connessione
Client
(Inizializzare una WSA)
Creare una Socket
Connettersi al server
Inviare e ricevere dati
Chiudere la connessione
Dott.ssa Valeria Carofiglio
5
Una astrazione di una socket:
Implementazione della socket Applicazione
Strutture dati associate ad una socket TCP
• L’applicazione
struttura di
descrittori
Descrittori
• differenti
riferimento
socket
fa
una
riferimento alla
socket tramite
processi possono fare
alla
stessa
struttura
• informazioni associate alla struttura
socket:
• code di ricezione e invio
Closed
• informazioni
dell’handshake
TCP)
Local port
Local IP
sullo
(per una
stato
socket
• indirizzi internet
Remote port
Remote IP
Struttura di una socket
Dott.ssa Valeria Carofiglio
Il ciclo di vita di una socket TCP
Implementazione della socket Applicazione
Notazione
Eventi all’interno dell’applicazione che causano il
cambiamento di stato di una struttura socket
connect()
blocca
Closed
Local port
Indirizzi:A.B.C.D = client W.X.Y.Z server
Connecting
Local port
P
Handshake
completato
Established
Local port
P
Local IP
Local IP
A.B.C.D
Local IP
A.B.C.D
Remote port
Remote port
Q
Remote port
Q
Remote IP
Remote IP
W.X.Y.Z
Remote IP
W.X.Y.Z
Q= porta del server
Eventi come l’arrivo di messaggi, ecc..
Dott.ssa Valeria Carofiglio
6
Interazione TCP Client/Server
1.
2.
3.
4.
5.
1.
2.
3.
4.
5.
Server
(Inizializzare una WSA)
Creare una socket
Assegnare un local address alla
socket
Settare la socket all’ascolto
Iterativamente:
a. Accettare una nuova
connessione
b. Inviare e ricevere dati
c. Chiudere la connessione
Client
(Inizializzare una WSA)
Creare una Socket
Connettersi al server
Inviare e ricevere dati
Chiudere la connessione
Dott.ssa Valeria Carofiglio
Il ciclo di vita di una socket TCP
Implementazione della socket Applicazione
client
Stabilire una connessione (lato client)
Una socket creata
fa riferimento ad
un protocollo
specifico ma non ha
indirizzo IP e
numero diporta
Closed
Local port
Local IP
Remote port
Remote IP
Dott.ssa Valeria Carofiglio
7
Il ciclo di vita di una socket TCP
Implementazione della socket Applicazione
client
Stabilire una connessione (lato client)
connect() con IP W.X.Y.Z e porta Q
blocca
P non in uso da
altre socket
Closed
Completa i
campi;
Invia
richiesta
di connes.
al server
Local port
Local IP
Connecting
Local port
P
Local IP
A.B.C.D
Remote port
Remote port
Q
Remote IP
Remote IP
W.X.Y.Z
indirizzo dell’interfaccia
attraverso cui vengono
inviati i pacchetti al server
Dott.ssa Valeria Carofiglio
Il ciclo di vita di una socket TCP
Implementazione della socket Applicazione
client
Stabilire una connessione (lato client)
connect() con IP W.X.Y.Z e porta Q
blocca
Closed
Local port
• una
richiesta di
connessione clientÆserver
• Un ack serverÆclient
• Un ack clientÆserver
Completa i
campi;
Invia
richiesta
di connes.
al server
Connecting
Local port
P
Local IP
A.B.C.D
Remote port
Remote port
Q
Remote IP
Remote IP
W.X.Y.Z
Local IP
Handshake
a tre vie
Dott.ssa Valeria Carofiglio
8
Il ciclo di vita di una socket TCP
Implementazione della socket Applicazione
client
Stabilire una connessione (lato client)
connect() con IP W.X.Y.Z e porta Q
blocca
Closed
Local port
Local IP
Completa i
campi;
Invia
richiesta
di connes.
al server
Handshake
a tre vie
Connecting
Local port
P
Local IP
completato
Established
Local port
P
A.B.C.D
Local IP
A.B.C.D
Remote port
Remote port
Q
Remote port
Q
Remote IP
Remote IP
W.X.Y.Z
Remote IP
W.X.Y.Z
Dott.ssa Valeria Carofiglio
Implementazione della socket Applicazione
client
• il client considera la
Il ciclo
di stabilita
vita nondi una socket TCP
connessione
appena
riceve una
l’ack connessione
dal server
Stabilire
• se il server non accetta una
connessione invia un
messaggio
(lato client)
connect() con IP W.X.Y.Z e porta Q
blocca
Closed
Local port
Completa i
campi;
Invia
richiesta
di connes.
al server
Connecting
Local port
P
Handshake
a tre vie
completato
Established
Local port
P
Local IP
A.B.C.D
Local IP
A.B.C.D
Remote port
Remote port
Q
Remote port
Q
Remote IP
Remote IP
W.X.Y.Z
Remote IP
W.X.Y.Z
Local IP
Dott.ssa Valeria Carofiglio
9
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket Applicazione
server
Setup della socket (lato server)
il server deve
legare la socket ad
una porta locale
nota al client
(Q)
Closed
Local port
Local IP
Remote port
Remote IP
Dott.ssa Valeria Carofiglio
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket Applicazione
server
Setup della socket (lato server)
nel caso in cui il
server ha più di un
IP, consente alla
socket di ricevere
connessioni indirizzate
da tutti i suoi IP
bind() con porta Q
returns
Closed
Closed
Local port
Setta
indirizzo
locale e
porta
Local port
Q
Local IP
INADDR_ANY
Remote port
Remote port
*
Remote IP
Remote IP
*
Local IP
Dott.ssa Valeria Carofiglio
10
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket Applicazione
server
Setup della socket (lato server)
Qualunque richiesta di connessione che avviene prima della listen()
verrà rigettata
bind() con porta Q
listen()
returns
Return
Closed
Closed
Setta
indirizzo
locale e
porta
Setta
all’ascolto
Listening
nuove conn.
Local port
Q
Local port
Q
Local IP
INADDR_ANY
Local IP
INADDR_ANY
Remote port
Remote port
*
Remote port
*
Remote IP
Remote IP
*
Remote IP
*
Local port
Local IP
Dott.ssa Valeria Carofiglio
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket Applicazione
Accettare la connessione (lato server)
accept()
Blocca sino alla connessione con un client
Listening
nuove conness.
Local port
Q
Local IP
*
Remote port
*
Remote IP
*
Dott.ssa Valeria Carofiglio
11
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket
Gestione della richiesta di connessione in entrata
Creare una nuova
socket per la
connessione,
Listening
settare gli indirizzi
e continuare
l’handshake
nuove connessi.
Richiesta
di connesQ
Local port
sione da
A.B.C.D/P
*
Local IP
Remote port
*
Remote IP
*
Processo trasparente
ack serverÆclient
IP di destinazione
Connecting
Local port
Q
Local IP
W.X.Y.Z
Remote port
P
IP e porta del
mittente
Remote IP A.B.C.D
Dott.ssa Valeria Carofiglio
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket
Gestione della richiesta di connessione in entrata
Creare una nuova
socket per la
connessione,
Listening
settare gli indirizzi
e continuare
l’handshake
nuove connessi.
Richiesta
di connesQ
Local port
sione da
A.B.C.D/P
*
Local IP
Remote port
*
Remote IP
*
Processo trasparente
• il numero di porta
locale è lo stesso
per le due socket
•La socket originale
non cambia stato
Connecting
Local port
Q
Local IP
W.X.Y.Z
Remote port
P
Remote IP A.B.C.D
Dott.ssa Valeria Carofiglio
12
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket
• il server non
Gestione della richiesta di connessione
in entrata
Listening
considera la
connessione stabilita
Creare una nuova
finchè non viene
socket per la
connessione,
inviato il terzo
settare gli indirizzi
messaggio
e continuare
l’handshake
nuove connessi.
Richiesta
di connesQ
Local port
sione da
A.B.C.D/P
*
Local IP
Remote port
*
Remote IP
*
Processo trasparente
Connecting
Handshake
completato
Established
Local port
Q
Local port
Q
Local IP
W.X.Y.Z
Local IP
W.X.Y.Z
Remote port
P
Remote port
P
Remote IP A.B.C.D
Remote IP A.B.C.D
Dott.ssa Valeria Carofiglio
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket Applicazione
Accettare la connessione (lato server)
accept()
Blocca sino alla connessione con un client
Listening
Ritorna il descrittore per questa
socket (socket di connessione)
Evento descritto in
Richiesta di connessione in entrata
Listening
nuove conness.
Local port
Q
Local IP
*
Remote port
*
Remote IP
*
Established
Local port
Q
Local IP W.X.Y.Z
Remote port
Dott.ssa Valeria Carofiglio
Rimuove
Nuove connessi.
la
socket
Q
Local port
dalla
lista di
*
Local
IP
nuove
conness.
Remote port
*
Remote IP
*
P
Remote IP A.B.C.D
13
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket Applicazione
Chiudere la connessione (indipendente dal lato)
close()
Returns immediately
Ha inizio un
handshake di
chiusura,
Established
Local port
P
Remote port
Q
• un msg di chiusura
viene inviato all’altra
parte (fine dati da
trasferire)
• un ack per questo
msg viene inviato
Il descrittore
Local IP A.B.C.D viene
deallocato
Remote IP W.X.Y.Z
Terminazione senza perdita di dati in transito
Dott.ssa Valeria Carofiglio
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket Applicazione
Chiudere la connessione (indipendente dal lato)
close()
Returns immediately
Ha inizio un
handshake di
chiusura,
Established
Local port
P
Remote port
Q
Il descrittore
Local IP A.B.C.D viene
deallocato
Remote IP W.X.Y.Z
• un msg di chiusura
viene inviato all’altra
parte (fine dati da
trasferire)
• un ack per questo
msg viene ricevuto
• La connessione
viene chiusa
completamente solo
quando un handshake
simile avviene in
direzione opposta
Terminazione senza perdita di dati in transito
Dott.ssa Valeria Carofiglio
14
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket Applicazione
Chiudere la connessione (indipendente dal lato)
close()
Returns immediately
Ha inizio un
handshake di
chiusura,
Established
Closed
Hs
msg
P
P
Local port
Il descrittore
Local IP A.B.C.D viene
Local IP A.B.C.D
deallocato
Local port
Remote port
Q
Remote port
Remote IP W.X.Y.Z
Half-Closed
Local port
P
Local IP A.B.C.D
Q
Remote port
Remote IP W.X.Y.Z
Q
Remote IP W.X.Y.Z
Terminazione senza perdita di dati in transito
Dott.ssa Valeria Carofiglio
Il ciclo di vita di una socket TCP(cont.)
Implementazione della socket Applicazione
Chiudere la connessione (indipendente dal lato)
close()
Returns immediately
Ha inizio un
handshake di
chiusura,
Established
Local port
P
Remote port
Q
Closed
P
Local port
Il descrittore
viene
Local IP A.B.C.D
Local IP A.B.C.D
deallocato
Remote port
Remote IP W.X.Y.Z
Q
Remote IP W.X.Y.Z
Hs
msg
Half-Closed
Local port
Hs
ack
P
Local IP A.B.C.D
Remote port
Q
Remote IP W.X.Y.Z
Time-wait
Local port
P
Local IP A.B.C.D
Remote port
Q
Remote IP W.X.Y.Z
Terminazione senza perdita di dati in transito
Dott.ssa Valeria Carofiglio
15
Funzione socket()
Crea una socket dedicata ad un fornitore di servizi specifico
SOCKET socket(
int af, int type, int protocol );
Address family
Tipo di socket
(AF_INET: Internet
Address Family)
Tipo
Significato
SOCK_STREAM
Fornisce una connessione sequenziale,
affidabile e full-duplex. Il protocollo TCP
è basato su questo tipo di socket.
SOCK_DGRAM
Supporta i datagrammi (privo di
connessione, messaggi inaffidabili di una
lunghezza massima prefissata). Il
protocollo UDP è basato su questo tipo di
socket.
Protocollo da usare
con la socket per
l’address family
indicata
(solitamente posto a 0
indica il protocollo derivato
dalla coppia [af, type])
Dott.ssa Valeria Carofiglio
Funzione socket(): valori di ritorno
Crea una socket dedicata ad un fornitore di servizi specifico
SOCKET socket(
int af, int type, int protocol );
La funzione restituisce un intero che è interpretato come un
descrittore che referenzia la nuova socket in caso di successo.
Altrimenti restituisce un codice di errore
Dott.ssa Valeria Carofiglio
16
Funzione socket(): valori di ritorno
Crea una socket dedicata ad un fornitore di servizi specifico
SOCKET socket(
int af, int type, int protocol );
La funzione restituisce un intero che è interpretato come un
descrittore che referenzia la nuova socket in caso di successo.
Altrimenti restituisce un codice di errore
ATTENZIONE!!!
Una applicazione client usa indirizzo IP e porta per connettersi
• Address Family
La funzione crea un socket senza nome
Bind()
• Indirizzo IP
• Porta che identifica
l’applicazione
Dott.ssa Valeria Carofiglio
Funzione bind()
Associa un nome alla socket creata in precedenza
int bind( SOCKET s, const struct sockaddr* name, int namelen);
Descrittore di
un socket
Indirizzo da
assegnare alla
socket
Lunghezza in byte
di name
Dott.ssa Valeria Carofiglio
17
Struttura sockaddr_in
La struttura sockaddr
è interpretata differentemente a seconda dei contesti determinati dalle
differenti address family (AF_XXXX).
Forma di
sockaddr
In AF_INET (con protocollo IPv4)
struct sockaddr_in {
short
sin_family;
u_short sin_port;
struct in_addr sin_addr;
char
sin_zero[8];
};
Un puntatore ad una
sockaddr
non è rigorosamente interpretato come tale
Le funzioni Winsock che fanno uso di un puntatore ad una struttura di tipo
sockaddr devono necessariamente effettuare una operazione di “cast”
bind( m_socket, (SOCKADDR*) &service, sizeof(service)
Dott.ssa Valeria Carofiglio
Funzione bind(): valori di ritorno
Associa un nome alla socket creata in precedenza
int bind( SOCKET s, const struct sockaddr* name, int namelen);
La funzione restituisce ‘O’ in caso di successo.
Altrimenti restituisce un codice di errore
Per il TCP/IP se la porta è specificata come zero, il fornitore di servizi
assegna una porta tra 1024 e 5000
L’applicazione può usare la funzione getsockname (dopo la bind) per
apprendere l’indirizzo IP e la porta assegnati
Dott.ssa Valeria Carofiglio
18
…un esempio di codice
#include <stdio.h>
#include "winsock2.h"
void main() {
// Initialize Winsock
WSADATA wsaData;
int iResult = WSAStartup(MAKEWORD(2,2), &wsaData);
if (iResult != NO_ERROR)
printf("Error at WSAStartup()\n");
// Create a SOCKET for listening for incoming connection requests
SOCKET ListenSocket;
ListenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (ListenSocket == INVALID_SOCKET) {
printf("Error at socket(): %ld\n", WSAGetLastError());
WSACleanup();
return;
}
// The sockaddr_in structure specifies the address family, IP address,
and port for the socket that //is being bound.
sockaddr_in service;
service.sin_family = AF_INET;
service.sin_addr.s_addr = inet_addr("127.0.0.1");
service.sin_port = htons(27015);
Dott.ssa Valeria Carofiglio
…un esempio di codice (cont.)
// Bind the socket.
if (bind( ListenSocket,
(SOCKADDR*) &service,
SOCKET_ERROR) {
printf("bind() failed.\n");
closesocket(ListenSocket);
return;
}
sizeof(service)) ==
WSACleanup();
return;
}
Dott.ssa Valeria Carofiglio
19
Funzione listen()
Setta la socket in uno stato in cui rimane in attesa di richiesta di
connessioni
int listen(
SOCKET s,
int backlog);
Descrittore di
un socket
Massima lungezza della
coda di connessioni
entranti
Dott.ssa Valeria Carofiglio
Funzione listen(): valori di ritorno
Setta la socket in uno stato in cui rimane in attesa di richiesta di
connessioni
int listen(
SOCKET s,
int backlog);
Descrittore di
un socket
Massima lungezza della
coda di connessioni
entranti
La funzione restituisce ‘O’ in caso di successo.
Altrimenti restituisce un codice di errore
Dott.ssa Valeria Carofiglio
20
Funzione accept()
Consente un tentativo di connessione in entrata su una socket
SOCKET accept(
SOCKET s,
Descrittore di
un socket
struct sockaddr* addr,
Puntatore opzionale ad
un buffer che riceve
l’indirizzo dell’entità
che fa richiesta di
connessione
int* addrlen);
Puntatore opzionale
che contiene la
lunghezza di addr
Dott.ssa Valeria Carofiglio
Funzione accept()
Consente un tentativo di connessione in entrata su una socket
SOCKET accept(
SOCKET s,
struct sockaddr* addr,
int* addrlen);
La funzione estrae la prima connessione dalla coda di pendenza delle
connessioni sul socket s.
Successivamente crea e restituisce un riferimento ad una nuova
socket.
Questa nuova socket è quella che abbiamo chiamato socket di
connessione.
Mantiene le stesse prorpieta della socket s
Dott.ssa Valeria Carofiglio
21
Funzione connect()
Stabilisce una connessione ad una socket specificata
int connect( SOCKET s, const struct sockaddr* name, int namelen);
Descrittore di
un socket non
connesso
Nome della socket con
cui dovrebbe essere
stabilita la connessione
lunghezza di name
Dott.ssa Valeria Carofiglio
Funzione connect()
Stabilisce una connessione ad una socket specificata
int connect( SOCKET s, const struct sockaddr* name, int namelen);
Per una socket di tipo “connectionless” (per esempio SOCK_DGRAM),
la connect() semplicemente stabilisce un indirizzo di destinazione di
default
Qualunque datagram ricevuto da un indirizzo diverso da quello di
destinazione verrà scaricato
Se il campo indirizzo della struttura che specifica il name è zero, la
socket verrà disconnessa
Dott.ssa Valeria Carofiglio
22
…un esempio di codice
#include <stdio.h>
#include "winsock2.h"
void main() {
// Initialize Winsock
WSADATA wsaData;
int iResult = WSAStartup(MAKEWORD(2,2), &wsaData);
if (iResult != NO_ERROR)
printf("Error at WSAStartup()\n");
// Create a SOCKET for connecting to server
SOCKET ConnectSocket;
ConnectSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (ConnectSocket == INVALID_SOCKET) {
printf("Error at socket(): %ld\n", WSAGetLastError());
WSACleanup();
return;
}
Dott.ssa Valeria Carofiglio
…un esempio di codice (cont.)
// The sockaddr_in structure specifies the address family,
// IP address, and port of the server to be connected to.
sockaddr_in clientService;
clientService.sin_family = AF_INET;
clientService.sin_addr.s_addr = inet_addr( "127.0.0.1" );
clientService.sin_port = htons( 27015 );
// Connect to server.
if ( connect( ConnectSocket, (SOCKADDR*) &clientService,
sizeof(clientService) ) == SOCKET_ERROR) {
printf( "Failed to connect.\n" );
WSACleanup();
return;
}
printf("Connected to server.\n");
WSACleanup();
return;
}
Dott.ssa Valeria Carofiglio
23
Funzione send()
Invia dati ad una socket connessa
int send( SOCKET s, const char* buf, int len, int flags );
Descrittore di
una socket
connessa
Puntatore al Buffer
contenente I dati da
trasmettere
Indicatore che
specifica il modo in cui
la chiamata è fatta
Lunghezza dei
dati in buf, in
byte
Il flag può essere usato per influenzare il comportamento della funzione
Dott.ssa Valeria Carofiglio
Funzione send(): valori di ritorno
Invia dati ad una socket connessa
int send( SOCKET s, const char* buf, int len, int flags );
Descrittore di
una socket
connessa
Buffer contenente I
dati da trasmettere
Indicatore che
specifica il modo in cui
la chiamata è fatta
Lunghezza dei
dati in buf, in
byte
Il flag può essere usato per influenzare il comportamento della funzione
La funzione restituisce il numero di byte trasmessi in caso di
successo. Un codice di errore, altrimenti
Dott.ssa Valeria Carofiglio
24
Funzione recev()
Riceve dati da una socket connessa (o “legata”)
int recev(SOCKET s, char* buf, int len, int flags );
Descrittore di
una socket
connessa
Puntatore al Buffer
contenente I dati da
ricevere
Indicatore che
specifica il modo in cui
la chiamata è fatta
Lunghezza dei
dati in buf, in
byte
Il flag può essere usato per influenzare il comportamento della funzione
Dott.ssa Valeria Carofiglio
Interazione UDP Client/Server
1.
2.
3.
4.
1.
2.
3.
4.
Server
(Inizializzare una WSA)
Creare una socket
Assegnare un local address alla
socket
Iterativamente:
a. Inviare e ricevere dati
b. Chiudere la connessione
Client
(Inizializzare una WSA)
Creare una Socket
Inviare e ricevere dati
Chiudere la connessione
Dott.ssa Valeria Carofiglio
25
Funzione recevfrom()
Riceve un datagram e memorizza l’indirizzo da cui i dati sono stati inviati
int recvfrom( SOCKET s, char* buf, int len, int flags, struct sockaddr* from, int* fromlen);
Descrittore di una
socket
(eventualmente)
connessa
Lunghezza dei
dati in buf, in
byte
Buffer contenente I dati in
ingresso
Puntatore opzionale
ad una struttura che
contiene l’indirizzo
della socket target
Indicatore che specifica il
modo in cui la chiamata è
Lunghezza dei
fatta
dati in from, in
byte
Il flag può essere usato per influenzare il comportamento della funzione
La funzione è normalmente usata per socket non orientate alla connessione.
L’indirizzo locale della socket deve essere noto
Per applicazioni Server, questo è fatto esplicitamente con la funzione bind()
Il binding esplicito è scoraggiato per applicazioni client (in tal caso la funxzione
effettua un binding implicito
Dott.ssa Valeria Carofiglio
…un esempio di codice
#include <stdio.h>
#include "winsock2.h"
void main() {
WSADATA wsaData;
SOCKET RecvSocket;
sockaddr_in RecvAddr;
int Port = 27015;
char RecvBuf[1024];
int BufLen = 1024;
sockaddr_in SenderAddr;
int SenderAddrSize = sizeof(SenderAddr);
//----------------------------------------------// Initialize Winsock
WSAStartup(MAKEWORD(2,2), &wsaData);
//----------------------------------------------// Create a receiver socket to receive datagrams
RecvSocket = socket(AF_INET, SOCK_DGRAM, 0);
//----------------------------------------------Dott.ssa Valeria Carofiglio
26
…un esempio di codice (cont.)
// Bind the socket to any address and the specified port.
RecvAddr.sin_family = AF_INET;
RecvAddr.sin_port = htons(Port);
RecvAddr.sin_addr.s_addr = htonl(INADDR_ANY);
bind(RecvSocket, (SOCKADDR *) &RecvAddr, sizeof(RecvAddr));
//----------------------------------------------// Call the recvfrom function to receive datagrams
// on the bound socket.
printf("Receiving datagrams...\n");
recvfrom(RecvSocket,RecvBuf,BufLen,0, (SOCKADDR*)&SenderAddr, &SenderAddrSize);
//----------------------------------------------// Close the socket when finished receiving datagrams
printf("Finished receiving. Closing socket.\n");
closesocket(RecvSocket);
//----------------------------------------------// Clean up and exit.
printf("Exiting.\n");
WSACleanup();
return;
}
Dott.ssa Valeria Carofiglio
Funzione sendto()
Invia dati ad una specifica destinazione
int sendto( SOCKET s, const char* buf, int len, int flags, const struct sockaddr* to, int tolen);
Descrittore di una
socket
(eventualmente)
connessa
Lunghezza dei
dati in buf, in
byte
Buffer contenente I dati da
trasmettere
Puntatore opzionale
ad una struttura che
contiene l’indirizzo
della socket target
Indicatore che specifica il
modo in cui la chiamata è
fatta
Lunghezza dei
dati in to, in
byte
Il flag può essere usato per influenzare il comportamento della funzione
La funzione è normalmente usata per socket non orientate alla connessione per
inviare datagram ad una specifica socket identificata dai parametri. I parametri
to e tolen vengono ignorati in caso di socket orientate alla connessione e la
funzione diventa equivalente ad una send()
Dott.ssa Valeria Carofiglio
27
Funzione sendto():valori di ritorno
Invia dati ad una specifica destinazione
int sendto( SOCKET s, const char* buf, int len, int flags, const struct sockaddr* to, int tolen);
Descrittore di una
socket
(eventualmente)
connessa
Lunghezza dei
dati in buf, in
byte
Buffer contenente I dati da
trasmettere
Puntatore opzionale
ad una struttura che
contiene l’indirizzo
della socket target
Indicatore che specifica il
modo in cui la chiamata è
fatta
Lunghezza dei
dati in to, in
byte
La funzione restituisce il numero di byte trasmessi in caso di successo.
Un codice di errore, altrimenti
Dott.ssa Valeria Carofiglio
…un esempio di codice
#include <stdio.h>
#include "winsock2.h"
void main() {
WSADATA wsaData;
SOCKET SendSocket;
sockaddr_in RecvAddr;
int Port = 27015;
char SendBuf[1024];
int BufLen = 1024;
//--------------------------------------------// Initialize Winsock
WSAStartup(MAKEWORD(2,2), &wsaData);
//--------------------------------------------// Create a socket for sending data
SendSocket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
Dott.ssa Valeria Carofiglio
28
…un esempio di codice (cont.)
//--------------------------------------------// Set up the RecvAddr structure with the IP address of
// the receiver (in this example case "123.456.789.1")
// and the specified port number.
RecvAddr.sin_family = AF_INET;
RecvAddr.sin_port = htons(Port);
RecvAddr.sin_addr.s_addr = inet_addr("123.456.789.1");
//--------------------------------------------// Send a datagram to the receiver
printf("Sending a datagram to the receiver...\n");
sendto(SendSocket,SendBuf,BufLen,0,(SOCKADDR *) &RecvAddr, sizeof(RecvAddr));
//--------------------------------------------// When the application is finished sending, close the socket.
printf("Finished sending. Closing socket.\n");
closesocket(SendSocket);
//--------------------------------------------// Clean up and quit.
printf("Exiting.\n");
WSACleanup();
return;
}
Dott.ssa Valeria Carofiglio
Cambiare una applicazione winsock in una
socket Unix
File header
windows
#include <stdio.h>
#include <stdlib.h>
Include tutti tutte le
definizioni e i prototipi
#include <winsock.h>
unix
Per socket(), connect(),
send(), recev()
Per sockaddrin
#include <stdio.h>
#include <stdlib.h>
#include < sys/socket.h >
#include <arpa/inet.h>
Dott.ssa Valeria Carofiglio
29
Setup dell’applicazione
Il codice è identico a meno del codice per inizializzare
l’applicazione
windows
WSADATA wsaData;
Int iResult = WSAStartup(MAKEWORD(2 ,2), &wsaData);
If (iResult != NO_ERROR)
printf(“error at WSASturtup\n”);
Codice di
inizializzazione
della libreria
winsock
comunicazione
Il codice è’ identico
Dott.ssa Valeria Carofiglio
Chiusura dell’applicazione
windows
Closesocket(m_socket);
WSAcleanup();
De-allocazione delle
risorse usate da winsock
Exit(0)
unix
Close(m_socket);
Exit(0)
Dott.ssa Valeria Carofiglio
30
Gestione dell’errore
windows
#include<stdio.h>
#include<stdlib.h>
#include<winsock.h>
void ErrorManagement(char* errorMessage) {
printf( "Error at socket(): %ld\n", WSAGetLastError() );
WSACleanup();
exit(1);
}
unix
#include<stdio.h>
#include<stdlib.h>
void ErrorManagement(char* errorMessage) {
perror(errorMessage);
exit(1);
}
Dott.ssa Valeria Carofiglio
31