PDA

View Full Version : [C] Problema con le socket


eldivino
30-09-2009, 10:39
Ciao a tutti, avrei un problemuccio:
uso code::blocks 8.02 per compilare i miei script in C..ultimamente ho deciso di mettermi alla prova con la programmazione di socket..cosa per cui sono necessarie delle librerie, appunto le winsock.
volevo sapere come "aggiungerle" in modo tale da poter far funzionare i miei algoritmi.

Questi sono i codici del client e del server (semplice algoritmo riguardante la "comunicazione" tra cliente e cameriere di una pizzeria)


#include <windows.h>
#include <fcntl.h>
#include <stdio.h> // Libreria STANDARD INPUT/OUTPUT //
#include <winsock.h> // Libreria per la gestione delle socket sotto Windows //
#include <string.h> // Libreria per la gestione delle stringhe //

void crea_socket ();
void invia_pizze (SOCKET remoteSocket, int ordinazione);
void invia_bibite (SOCKET remoteSocket, int ordinazione, double prezzo_pizza_scelta);

int main()
{
crea_socket();
return 0;
}

void crea_socket ()
/* Questa function crea le socket di ascolto e ricezione e gestisce la scelta effettuata dall'utente nel menų principale
del client */
{
SOCKET listenSocket; // Creazione della socket di ascolto. //
SOCKET remoteSocket; // Creazione della socket di ricezione. //

SOCKADDR_IN Server_addr;
SOCKADDR_IN Client_addr;
// Per assegnare una porta ed un indirizzo IP alle socket si creano queste variabili strutturate //

int sin_size, scelta_effettuata, ordinazione;
/* La variabile "ordinazione" viene usata come un flag. Se č impostata su zero, significa che l'utente non ha deciso di
effettuare un'ordinazione, altrimenti assume il valore uno. */

short port; // La porta da utilizzare per la comunicazione con il server. //
int wsastartup; // Variabile di controllo per il successo della WSAStartup //
int ls_result, prezzo_pizza_scelta; // "ls_result" = variabile di controllo per il successo della listen //

WORD wVersionRequested = MAKEWORD(2,2);
/* Il parametro MAKEWORD(2,2) della WSAStartup ricerca nel sistema la versione 2.2 della Winsock e setta la versione che
gli viene passata come quella pių alta che il chiamante puō usare. */

WSADATA wsaData;

wsastartup = WSAStartup(wVersionRequested, &wsaData);
/* Inizializzazione della libreria Socket.
wVersionRequested (param. di input) = indica la versione pių alta delle socket di Windows che il chiamante puō usare.
WSAData (param. di output) = un puntatore alla struct WSADATA, che deve ricevere i dettagli sulle socket di Windows. */

if (wsastartup != NO_ERROR)
printf("Errore WSAStartup()\n");
// Rilevamento dell'eventuale errore all'avvio della libreria per la gestione delle socket. //

listenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
/* Creazione della Socket che si porrā in ascolto di richieste del Client

AF_INET = utilizzo della classe IP4
SOCK_STREAM = socket di tipo full-duplex. Si possono leggere e scrivere flussi di byte contemporaneamente e
indipendentemente nel canale. I dati non vengono mai perduti o ricevuti in modo duplicato.
IPPROTO_TCP = utilizzo del protocollo TCP/IP */

if (listenSocket < 0)
printf("Server: errore nella creazione della socket.\n");
else
printf("La Listening Socket e' partita\n");
// Rilevamento dell'eventuale errore nella creazione della socket //

port = 4000;

/* La struttura SOCKADDR_IN (Server_addr) specifica l'indirizzo famiglia, l'indirizzo ip e la porta del server con cui
connettersi */

Server_addr.sin_family = AF_INET; // Utilizzo della classe IP4 //
Server_addr.sin_addr.s_addr = inet_addr ("127.0.0.1");
// La funzione "inet_addr" converte una stringa contenente un indirizzo IP4 nel formato adatto per la struct SOCKADDR_IN //
Server_addr.sin_port = htons(port);
// La funzione "htons" prende un numero a 16 bit e lo converte in un numero a 16 bit nel formato IP4. //

/* La seguente porzione di codice effettua la bind sull’indirizzo e porta ora specificati. La bind richiede il descrittore di
socket,indirizzo da assegnare alla socket,lunghezza in byte di Server_addr */
if (bind(listenSocket,(SOCKADDR*)&Server_addr,sizeof(struct sockaddr_in)) < 0)
printf("Server: errore durante la bind.\n"); //Rilevamento dell'eventuale errore durante la bind //

ls_result = listen(listenSocket, SOMAXCONN);
/* La socket si pone in "ascolto" tramite la listen(). La listen richiede il descrittore socket, la massima lunghezza della
coda di connessioni entranti */

if (ls_result < 0)
printf("Server: errore durante la listen.\n"); // La listen non č riuscita //
else
printf("La Socket e' in Ascolto\n"); // La socket accetta la richiesta di connessione del Client //

sin_size = sizeof(struct sockaddr_in);
ordinazione = 0;

remoteSocket = accept(listenSocket, (struct sockaddr *)&Client_addr,&sin_size);
/* La funzione accept indica la socket su cui il server ha accettato la connessione, l’indirizzo del client che ha effettuato
la richiesta di connessione che č stata accettata e la lunghezza di questo indirizzo. */

printf("Accettata Connessione con Client: %s\n",inet_ntoa(Client_addr.sin_addr));
// Il Server accetta il messaggio dal Client //

recv(remoteSocket, (char *)&scelta_effettuata, sizeof(int), 0);
/* Ricezione dal client dell'opzione selezionata dall'utente, memorizzata all'interno della variabile "scelta_effettuata".
Nella recv vengono indicati la socket utilizzata, la variabile in cui viene salvato il messaggio e la sua dimensione in byte.
Eseguo un cast per trattare "scelta_effettuata" come una stringa, parametro standard della recv. */

printf("Messaggio Arrivato: %d \n", scelta_effettuata);
prezzo_pizza_scelta = 0;

if (scelta_effettuata == 1) // Il cliente vuole vedere il menų delle pizze //
invia_pizze (remoteSocket, ordinazione);

if (scelta_effettuata == 2) // Il cliente vuole vedere il menų delle bibite //
invia_bibite (remoteSocket, ordinazione, prezzo_pizza_scelta);

if (scelta_effettuata == 3) /* L'utente ha deciso di effettuare un'ordinazione. La variabile "ordinazione" viene
impostata su uno. */
{
ordinazione = 1;
invia_pizze (remoteSocket, ordinazione);
}

}
void invia_pizze (SOCKET remoteSocket, int ordinazione)
/* Questa funzione invia al client il menų delle pizze e, nel caso in cui la variabile "ordinazione" sia impostata su uno,
gestisce l'ordinazione delle stesse */
{
int i,pizza_scelta;
double prezzo_pizza_scelta;
char pizze [6][50] = {"01. Margherita \t\t\t3,10 Euro\n", "02. Olio e pomodoro \t\t2,80 Euro\n", "03. Ripieno \t\t\t4,20 Euro\n",
"04. Quattro stagioni \t\t4,50 Euro\n", "05. Capricciosa \t\t4,50 Euro\n", "06. Filetto di pomodoro \t4,20 Euro\n"};
double prezzi_pizze [] = {3.10,2.80,4.20,4.50,4.50,4.20};

printf ("Sto inviando:\n");

for (i=0; i<6; i++)
{
send(remoteSocket,pizze[i], strlen(pizze[i]),0);
/* Al passo i-simo, invio al client l'i-sima stringa. Nella send vengono indicati la socket da utilizzare, la fonte del
messaggio e la sua dimensione.*/
printf ("%s", pizze[i]); // Stampo a video la stringa che sto inviando //
}

if (ordinazione == 0) /* L'utente vuole solo visualizzare il menų delle pizze */
{
printf("Chiudo il Server\n");
close(remoteSocket); // Chiudo la socket utilizzata //
WSACleanup(); // Questa istruzione termina l'utilizzo della libreria per la gestione delle socket. //

crea_socket ();
}

if (ordinazione == 1) // L'utente vuole ordinare //
{
printf ("Aspetto il codice pizza.\n");
recv (remoteSocket, (char *)&pizza_scelta, sizeof(int), 0);
/* Ricezione dal client della pizza scelta dall'utente, memorizzata all'interno della variabile "pizza_scelta". Nella recv
vengono indicati la socket utilizzata, la variabile in cui viene salvato il messaggio e la sua dimensione in byte. Eseguo
un cast per trattare "pizza_scelta" come una stringa, parametro standard della recv. */

printf ("Ho ricevuto il cod pizza %d\n", pizza_scelta);
printf ("Sto inviando:\n");
send(remoteSocket,pizze[pizza_scelta-1], strlen(pizze[pizza_scelta-1]),0);
/* Invio al client la pizza selezionata dall'utente, il cui codice č contenuto in "pizza_scelta". Nella send vengono
indicati la socket da utilizzare, la fonte del messaggio e la sua dimensione. Lo spiazzamento dell'indice č necessario in
quanto lo shape di un array di size n nel linguaggio C č di tipo (0, n-1) */

printf ("%s", pizze[pizza_scelta-1]); // Stampo a video la stringa che sto inviando //
prezzo_pizza_scelta= prezzi_pizze[pizza_scelta-1]; // Salvo il prezzo della pizza nella variabile "prezzo_pizza_scelta" //
invia_bibite (remoteSocket, ordinazione, prezzo_pizza_scelta);
// Chiamo la function "invia_bibite", passando la socket attualmente in uso //
}
}

void invia_bibite (SOCKET remoteSocket, int ordinazione, double prezzo_pizza_scelta)
/* Questa funzione invia al client il menų delle bibite e, nel caso in cui la variabile "ordinazione" sia impostata su uno,
gestisce l'ordinazione delle stesse */
{
int i, bibita_scelta;

char bibite [4][50] = {"01. Coca cola \t\t\t1,00 Euro\n", "02. Birra \t\t\t1,50 Euro\n", "03. Aranciata \t\t\t1,00 Euro\n",
"04. Minerale \t\t\t0,50 Euro\n"};
double prezzi_bibite [] = {1.00,1.50,1.00,0.50};
double prezzo_bibita_scelta;

printf ("Sto inviando:\n");
for (i=0; i<4; i++)
{
send(remoteSocket, bibite[i], strlen(bibite[i]),0);
/* Al passo i-simo, invio al client l'i-sima stringa. Nella send vengono indicati la socket da utilizzare, la fonte
del messaggio e la sua dimensione.*/

printf ("%s", bibite[i]); // Stampo a video la stringa che sto inviando //
}

if (ordinazione == 0)
{
printf("Chiudo il Server\n"); // L'utente vuole solo visualizzare il menų delle pizze //
close(remoteSocket);
WSACleanup(); // Questa istruzione termina l'utilizzo della libreria per la gestione delle socket. //

crea_socket ();
}

if (ordinazione == 1) // L'utente vuole ordinare //
{
printf ("Aspetto il codice bibita.\n");
recv (remoteSocket, (char *)&bibita_scelta, sizeof(int), 0);
/* Ricezione dal client della bibita scelta dall'utente, memorizzata all'interno della variabile "bibita_scelta".
Nella recv vengono indicati la socket utilizzata, la variabile in cui viene salvato il messaggio e la sua dimensione
in byte. Eseguo un cast per trattare "bibita_scelta" come una stringa, parametro standard della recv. */

printf ("Ho ricevuto il cod bibita %d\n", bibita_scelta);
printf ("Sto inviando:\n");
send(remoteSocket,bibite[bibita_scelta-1], strlen(bibite[bibita_scelta-1]),0);
/* Invio al client la bibita selezionata dall'utente, il cui codice č contenuto in "bibita_scelta". Nella send vengono
indicati la socket da utilizzare, la fonte del messaggio e la sua dimensione. Lo spiazzamento dell'indice č necessario
in quanto lo shape di un array di size n nel linguaggio C č di tipo (0, n-1) */

printf ("%s", bibite[bibita_scelta-1]); // Stampo a video la stringa che sto inviando //

prezzo_bibita_scelta = prezzi_bibite[bibita_scelta-1] + prezzo_pizza_scelta; // Calcolo il totale //

send(remoteSocket,(char *)&prezzo_bibita_scelta, sizeof(double),0);
/* Invio al client il totale dell'ordinazione effettuata dall'utente, memorizzato all'interno della variabile
"prezzo_bibita_scelta". Nella send vengono indicati la socket da utilizzare, la fonte del messaggio e la sua
dimensione in byte. Eseguo un cast per trattare "prezzo_bibita_scelta" come una stringa, parametro standard della send. */

printf ("Invio al client la somma di %.2f e %.2f che fa %.2f\n", prezzi_bibite[bibita_scelta-1],prezzo_pizza_scelta, prezzo_bibita_scelta);
// Stampo a video il totale che invio al client //

printf("Chiudo il Server\n");
close(remoteSocket);
WSACleanup(); // Questa istruzione termina l'utilizzo della libreria per la gestione delle socket. //

crea_socket ();
}
}





#include <windows.h>
#include <fcntl.h>
#include <stdio.h> // Libreria STANDARD INPUT/OUTPUT //
#include <winsock.h> // Libreria per la gestione delle socket sotto Windows //
#include <string.h> // Libreria per la gestione delle stringhe //

void stampa_inizio ();
void scelta ();
void menu_pizze (int scelta, int ordinazione);
void menu_bibite (int scelta);
void ordine (SOCKET clientsocket);
void menu_bibite_ordinazione (SOCKET clientsocket);

int main()
{
stampa_inizio ();
return 0;
}

void stampa_inizio ()
// Void function che stampa a video il menų principale //
{
printf ("\t\t\t* PIZZERIA BELLA NAPOLI *\n\t\t\t Viale Dei Giardini, 121\n\t\t\t Tel. 081-102030\n\n\n\t\t\t MENU' PRINCIPALE\n");
printf ("1. Visualizza menu' pizze\n2. Visualizza bibite\n3. Effettua ordinazione\n4. Esci\n\n");
printf ("Digita la tua scelta: ");
scelta ();
}

void scelta ()
// Void function che gestisce la scelta effettuata dall'utente nel menų principale del programma //
{
int scelta, ordinazione;
ordinazione = 0;
/* La variabile "ordinazione" viene usata come un flag. Se č impostata su zero, significa che l'utente non ha deciso di
effettuare un'ordinazione, altrimenti assume il valore uno. */

scanf ("%d", &scelta);

while ((scelta <1) || (scelta>4))
// Ciclo while che rileva l'eventuale digitazione errata da parte dell'utente di un'opzione inesistente nel menų principale. //
{
scelta = 0;
printf ("Hai digitato un valore non valido. Riprova.\n");
printf ("Digita la tua scelta: ");
scanf ("%d", &scelta);
}

if (scelta == 1) /* L'utente ha deciso di vedere il menų delle pizze */
menu_pizze (scelta, ordinazione);

if (scelta == 2) /* L'utente ha deciso di vedere il menų delle bibite */
menu_bibite (scelta);

if (scelta == 3) /* L'utente ha deciso di effettuare un'ordinazione. La variabile "ordinazione" viene impostata su uno. */
{
ordinazione = 1;
menu_pizze (scelta, ordinazione);
}

WSACleanup(); /* L'utente ha deciso di uscire dal programma. Questa istruzione termina l'utilizzo della libreria per la
gestione delle socket. */

}

void menu_pizze (int scelta, int ordinazione)
/* Questa funzione gestisce il menų delle pizze e, nel caso in cui la variabile "ordinazione" sia impostata su uno, l'ordinazione
delle stesse, chiamando la funzione "ordine" */
{
SOCKET clientsocket; // Definizione della socket per il client //
SOCKADDR_IN addr; // Per assegnare una porta ed un indirizzo IP alla socket si crea questa variabile strutturata. //

WORD wVersionRequested = MAKEWORD(2,2);
/* Il parametro MAKEWORD(2,2) della WSAStartup ricerca nel sistema la versione 2.2 della Winsock e setta la versione che
gli viene passata come quella pių alta che il chiamante puō usare. */

WSADATA wsaData;

int i, p;
short port; // La porta da utilizzare per la comunicazione con il server. //
char pizze [100]; // Buffer per le varie stringhe del menų delle pizze. //

WSAStartup(wVersionRequested, &wsaData);
/* Inizializzazione della libreria Socket.
wVersionRequested (param. di input) = indica la versione pių alta delle socket di Windows che il chiamante puō usare.
WSAData (param. di output) = un puntatore alla struct WSADATA, che deve ricevere i dettagli sulle socket di Windows.*/

port = 4000;

// La struttura SOCKADDR_IN (addr) specifica l'indirizzo famiglia, l'indirizzo ip e la porta del server con cui connettersi //

addr.sin_family = AF_INET; // Utilizzo della classe IP4 //
addr.sin_addr.s_addr = inet_addr("127.0.0.1");
// La funzione "inet_addr" converte una stringa contenente un indirizzo IP4 nel formato adatto per la struct SOCKADDR_IN //
addr.sin_port = htons(port);
// La funzione "htons" prende un numero a 16 bit e lo converte in un numero a 16 bit nel formato IP4. //

clientsocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
/*Inizializzazione della socket per il client.

AF_INET = utilizzo della classe IP4
SOCK_STREAM = socket di tipo full-duplex. Si possono leggere e scrivere flussi di byte contemporaneamente e
indipendentemente nel canale. I dati non vengono mai perduti o ricevuti in modo duplicato.
IPPROTO_TCP = utilizzo del protocollo TCP/IP */

if (connect(clientsocket, (LPSOCKADDR)&addr, sizeof(addr)) < 0)
printf("Errore nella connessione con il Server");
//Connessione al server e, eventualmente, rilevamento dell'errore //

send(clientsocket,(char *)&scelta, sizeof(int),0);
/* Invio al server dell'opzione selezionata dall'utente, memorizzata all'interno della variabile "scelta". Nella send vengono
indicati la socket da utilizzare, la fonte del messaggio e la sua dimensione in byte. Eseguo un cast per trattare "scelta"
come una stringa, parametro standard della send. */

for (i=0; i<6; i++)
{
p = recv (clientsocket, pizze, 100,0); // Al passo i-simo, ricevo dal server l'i-sima stringa del menų delle pizze //
pizze[p]='\0'; // Aggiunge il carattere terminatore alla fine di ogni stringa ricevuta dal server. //
printf ("%s", pizze); // Stampa a video la stringa //
}

if (ordinazione == 0) // L'utente vuole solo visualizzare il menų delle pizze //
{
system ("PAUSE");
system ("CLS");
stampa_inizio();
}
else
ordine (clientsocket); // L'utente vuole ordinare. Viene passata alla function la socket attualmente in uso. //
}

void menu_bibite (int scelta)
// Questa funzione gestisce il menų delle bibite //
{
SOCKET clientsocket; // Definizione della socket per il client //
SOCKADDR_IN addr; // Per assegnare una porta ed un indirizzo IP alla socket si crea questa variabile strutturata. //

WORD wVersionRequested = MAKEWORD(2,2);
/* Il parametro MAKEWORD(2,2) della WSAStartup ricerca nel sistema la versione 2.2 della Winsock e setta la versione che
gli viene passata come quella pių alta che il chiamante puō usare. */

WSADATA wsaData;

int i, p;
short port; // La porta da utilizzare per la comunicazione con il server. //
char bibite [100]; // Buffer per le varie stringhe del menų delle bibite. //

WSAStartup(wVersionRequested, &wsaData);
/* Inizializzazione della libreria Socket.
wVersionRequested (param. di input) = indica la versione pių alta delle socket di Windows che il chiamante puō usare.
WSAData (param. di output) = un puntatore alla struct WSADATA, che deve ricevere i dettagli sulle socket di Windows.*/

port = 4000;

// La struttura SOCKADDR_IN (addr) specifica l'indirizzo famiglia, l'indirizzo ip e la porta del server con cui connettersi //

addr.sin_family = AF_INET; // Utilizzo della classe IP4 //
addr.sin_addr.s_addr = inet_addr("127.0.0.1");
/* La funzione "inet_addr" converte una stringa contenente un indirizzo IP4 nel formato adatto per la struct SOCKADDR_IN */
addr.sin_port = htons(port);
/* La funzione "htons" prende un numero a 16 bit e lo converte in un numero a 16 bit nel formato IP4. */

clientsocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
/* Inizializzazione della socket per il client.

AF_INET = utilizzo della classe IP4
SOCK_STREAM = socket di tipo full-duplex. Si possono leggere e scrivere flussi di byte contemporaneamente e
indipendentemente nel canale. I dati non vengono mai perduti o ricevuti in modo duplicato.
IPPROTO_TCP = utilizzo del protocollo TCP/IP */

if (connect(clientsocket, (LPSOCKADDR)&addr, sizeof(addr)) < 0)
printf("Errore nella connessione con il Server");
// Connessione al server e, eventualmente, rilevamento dell'errore //

send(clientsocket,(char *)&scelta, sizeof(int),0);
/* Invio al server dell'opzione selezionata dall'utente, memorizzata all'interno della variabile "scelta". Nella send vengono
indicati la socket da utilizzare, la fonte del messaggio e la sua dimensione in byte. Eseguo un cast per trattare "scelta"
come una stringa, parametro standard della send. */

for (i=0; i<4; i++)
{
p = recv (clientsocket, bibite, 100,0); // Al passo i-simo, ricevo dal server l'i-sima stringa del menų delle bibite //
bibite[p]='\0'; // Aggiunge il carattere terminatore alla fine di ogni stringa ricevuta dal server. //
printf ("%s", bibite); // Stampa a video la stringa //
}
system ("PAUSE");
system ("CLS");
stampa_inizio();
}

void menu_bibite_ordinazione (SOCKET clientsocket)
/* Questa function stampa a video il menų delle bibite nel corso dell'ordinazione. Riceve come parametro di input la socket che č
giā in uso durante l'intera procedura dell'ordine. */
{
int i, p;
char bibite [100];

for (i=0; i<4; i++)
{
p = recv (clientsocket, bibite, 100,0); // Al passo i-simo, ricevo dal server l'i-sima stringa del menų delle bibite //
bibite[p]='\0'; // Aggiunge il carattere terminatore alla fine di ogni stringa ricevuta dal server. //
printf ("%s", bibite); // Stampa a video la stringa //
}
}

void ordine (SOCKET clientsocket)
// Questa function si occupa dell'ordinazione vera e propria. //
{
int cod_pizza, cod_bibita, p;
double totale;
char pizza_scelta [50]; // Buffer per la pizza ordinata //
char bibita_scelta [50]; // Buffer per la bibita ordinata //

totale = 0;

printf ("Inserire il codice della pizza desiderata: ");
scanf ("%d", &cod_pizza);

while ((cod_pizza < 1) || (cod_pizza> 6))
// Ciclo while che rileva l'eventuale digitazione errata da parte dell'utente di una pizza inesistente //
{
cod_pizza = 0;
printf ("Codice errato. Riprova.\n");
printf ("Inserire il codice della pizza desiderata: ");
scanf ("%d", &cod_pizza);
}

send(clientsocket,(char *)&cod_pizza, sizeof(int),0);
/* Invio al server della pizza ordinata dall'utente, memorizzata all'interno della variabile "cod_pizza". Nella send vengono
indicati la socket da utilizzare, la fonte del messaggio e la sua dimensione in byte. Eseguo un cast per trattare "cod_pizza"
come una stringa, parametro standard della send. */

p = recv (clientsocket, pizza_scelta, 50,0); // Ricevo dal server la stringa relativa alla pizza ordinata.//
pizza_scelta[p]='\0'; // Aggiunge il carattere terminatore alla fine della stringa ricevuta dal server. //
printf ("%s\n", pizza_scelta); // Stampo a video la stringa //

menu_bibite_ordinazione (clientsocket);
/* Chiamata alla function "menu_bibite_ordinazione" per stampare a video il menų delle bibite, passando la socket attualmente
in uso */

printf ("Inserire il codice della bibita desiderata: ");
scanf ("%d", &cod_bibita);

while ((cod_bibita < 1) || (cod_bibita> 4))
// Ciclo while che rileva l'eventuale digitazione errata da parte dell'utente di una bibita inesistente //
{
cod_bibita = 0;
printf ("Codice errato. Riprova.\n");
printf ("Inserire il codice della bibita desiderata: ");
scanf ("%d", &cod_bibita);
}

send(clientsocket,(char *)&cod_bibita, sizeof(int),0);
/* Invio al server della bibita ordinata dall'utente, memorizzata all'interno della variabile "cod_bibita". Nella send vengono
indicati la socket da utilizzare, la fonte del messaggio e la sua dimensione in byte. Eseguo un cast per trattare "cod_bibita"
come una stringa, parametro standard della send. */

p = recv (clientsocket, bibita_scelta, 50,0); // Ricevo dal server la stringa relativa alla pizza ordinata.//
bibita_scelta[p]='\0'; // Aggiunge il carattere terminatore alla fine della stringa ricevuta dal server. //
printf ("%s\n", bibita_scelta); // Stampo a video la stringa //

recv (clientsocket, (char *)&totale, sizeof(double), 0); // Ricevo dal server il conto //

printf ("ORDINAZIONE:\nPizza: %s\nBibita: %s\nTotale: %.2f Euro\n",pizza_scelta, bibita_scelta, totale);
system ("PAUSE");
system ("CLS");

stampa_inizio();
}




Comer errori mi da una serie di undefined reference (_recv@16, _send@16, _wsastartup@8, ecc..)

Come posso risolvere?

tomminno
30-09-2009, 10:46
Aggiungi ws2_32.lib tra le dipendenze del progetto