[Visual C++] Problème TCP/IP

Résolu/Fermé
Stupeflip Messages postés 391 Date d'inscription jeudi 8 février 2007 Statut Membre Dernière intervention 4 décembre 2007 - 8 févr. 2007 à 11:36
 Mitch - 28 juin 2007 à 15:10
Bonjour,

Voilà je dois coder sous Visual C++ (Windows) un programme en C. Dans celui-ci je dois faire un server tout bête mais j'ai un problème à ce niveau -là, lors du accept(), le programme accepte directement une connection de l'adresse 204.204.204.204 alors que je n'ai lancé que le server (pas de client). Voici la partie du code concernée :

	int listenfd,connfd;
	struct sockaddr_in servaddr;
	int clilen;
	struct sockaddr_in cliaddr;

        listenfd=socket(AF_INET,SOCK_STREAM,0);

   	memset(&servaddr,0,sizeof(servaddr));
   	servaddr.sin_family=AF_INET;
   	servaddr.sin_addr.s_addr=htonl(INADDR_ANY);
   	servaddr.sin_port=htons(12000);

   	bind(listenfd,(struct sockaddr*)&servaddr,sizeof(servaddr));

	printf("Listening ...\n");
   	listen(listenfd,20);

   	printf("Waiting for connection ...\n");
    
        /* Beginning Client Loop */                                                                        
    	for(;;)
    	{
       	clilen=sizeof(cliaddr);
	connfd=accept(listenfd,(struct sockaddr*)&cliaddr,&clilen);
	printf("[TCP] Connection acquired from (%s)\n",inet_ntoa(cliaddr.sin_addr));
     	} /* Fin du For */
	
	/* Fermeture programme */
      	close(listenfd);



Je ne comprends pas vraiment pourquoi il n'est pas en attente bloquante en attendant une connexion ? Quel est le problème ? Je sais que le code n'est pas très propre mais bon !

Merci d'avance !
A voir également:

14 réponses

Stupeflip Messages postés 391 Date d'inscription jeudi 8 février 2007 Statut Membre Dernière intervention 4 décembre 2007 94
8 févr. 2007 à 12:00
J'ajoute que suite à un ajout de printf j'ai pu voir la valeur du nouveau descripteur connfd. Il vaut 0 ...

L'erreur se situe au niveau de la fonction socket(), elle renvoie -1. Mais je ne sais pas pourquoi ? Cette commande fonctionne très bien sous Linux, hélas le portage sous Windows a l'air de poser des soucis... Quelqu'un aurait-il une idée ?
0
Char Snipeur Messages postés 9696 Date d'inscription vendredi 23 avril 2004 Statut Contributeur Dernière intervention 3 octobre 2023 1 297
8 févr. 2007 à 13:02
J'ai peut être une idée, mais comme tu mes pas le code, c'est pas sur.
As tu bien penser à mettre les WSAStartup() et MAKEWord() nécessaire aux socket sous windows ?
ça peut être la cause de l'erreur.
Autre erreur possible, il y a une fonction qui bug chez moi, l'argument sizeof (le dernier) doit absolument être une variable (comme dans ton accept, mais pas comme dans ton bind)
bonne chance
0
Stupeflip Messages postés 391 Date d'inscription jeudi 8 février 2007 Statut Membre Dernière intervention 4 décembre 2007 94
8 févr. 2007 à 13:35
Tu peux me donner plus d'informations sur WSA ? En fait j'ai mis du code que je connais de Linux, et avec des librairies Linux. Donc le passage en Windows s'est fait un peu dans l'inconnu, je ne savais pas qu'il fallait autre chose que winsock2.h !

En tout cas merci ;)

PS : Le reste du code c'est surtout du thread donc je ne pense pas que ça soit la cause du problème, de plus cela fonctionnait avant que j'implémente la partie Client/Server :)
0
Stupeflip Messages postés 391 Date d'inscription jeudi 8 février 2007 Statut Membre Dernière intervention 4 décembre 2007 94
8 févr. 2007 à 13:42
En me documentant un peu, j'ai rajouté cela :
WSADATA	wsa;

en variable globale, et
WSAStartup(MAKEWORD(2,0),&wsa); 

dans l'initialisation. Cela resout en partie mon problème ! En effet le socket ne renvoie plus d'erreur (-1), cependant il renvoie 0... A quoi cela peut-il être dû ?
Autre chose, à l'origine il y a un bzero pour mettre à 0, mais Windows ne semblant pas connaître cette commande, j'ai dû remplacer par un memset à 0. Je pense que cela n'a pas d'incidence... Sinon si quelqu'un sait si on peut faire bzero sous Windows, qu'il n'hésite pas ;p
0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question
Char Snipeur Messages postés 9696 Date d'inscription vendredi 23 avril 2004 Statut Contributeur Dernière intervention 3 octobre 2023 1 297
8 févr. 2007 à 17:22
Vi, c'est bien ce que j'ai sur mes codes win en effet.
faire un : WSACleanup(); à la fin du code.
moi, j'ai que des strucures en majuscule pour mes variables réseau :
    // donnees local
    SOCKET local;
    SOCKADDR_IN sinlocal;
    // donnees distantes
    SOCKET dist;
    SOCKADDR_IN sindist;
    local=socket(AF_INET,SOCK_STREAM,0);
    sinlocal.sin_family		= AF_INET;
    sinlocal.sin_addr.s_addr= htonl(INADDR_ANY);//inet_addr(c);
    sinlocal.sin_port		= htons(port);
    bind(local, (SOCKADDR *)&sinlocal, sizeof(SOCKADDR_IN));
    listen(local, 5);
    int leng=sizeof(SOCKADDR_IN); //necessaire, sinon, accept plante et n'attend pas la connection 
    dist=accept(local, (SOCKADDR *)&sindist,&leng);
    if(dist!=SOCKET_ERROR) return 0;
Je ne sais pas si ça peux jouer.
tien moi au courant. (moi, c'est avec Linux que j'ai des problèmes, sockaddr_in n'est pas dans sys/socket.h)
EDIT : un truc viens de me sauter au yeux, le troisième paramètre de accept est légèrement différent.
Moi, je renvoie la longueur du type sock... toi la taille de la variable de type sock...
J'ai vu quelque part que c'est pas pareil .
exemple : double a=2; alors sizeof(a)!=sizeof(double) ! (à vérifier quand même)
0
Stupeflip Messages postés 391 Date d'inscription jeudi 8 février 2007 Statut Membre Dernière intervention 4 décembre 2007 94
8 févr. 2007 à 19:10
Je pense que la différence se situe au niveau des déclarations. J'ai tenté de mettre SOCKET à la place de int mais ça n'a rien changé, à savoir j'ai toujours la détection automatique d'une connexion venant de 204.204.204.204, et socket renvoie 0 en valeur de retour... Donc toujours bloqué !

Par contre pour sockaddr_in, il est décrit dans un de ces .h :
#include <netdb.h>
#include <sys/types.h>
#include <netinet/in.h>
#include <sys/socket.h>
#include <arpa/inet.h>

Personnellement je mets le tout à chaque fois héhé ! D'après mes souvenirs, on peut l'obtenir indirectement par la description de sockaddr. Voilà si je peux t'aider un peu pour te repasser l'ascenseur tant mieux ;)

En ce qui concerne le sizeof différent du accept(), ben comme ça déconne déjà au niveau du socket(), je vais d'abord tacher de résoudre cela ;)
0
Stupeflip Messages postés 391 Date d'inscription jeudi 8 février 2007 Statut Membre Dernière intervention 4 décembre 2007 94
9 févr. 2007 à 09:40
Nouvelle journée qui s'annonce ! Je viens de m'apercevoir dans ton code que tu ne mets pas à 0 ton sinlocal. Tu devrais ajouter un
bzero(&sinlocal,sizeof(sinlocal));

avant ton
sinlocal.sin_family		= AF_INET;
sinlocal.sin_addr.s_addr  = htonl(INADDR_ANY);//inet_addr(c);
sinlocal.sin_port		  = htons(port);

Sinon toujours ce problème de socket() qui renvoie 0 chez moi !
0
Char Snipeur Messages postés 9696 Date d'inscription vendredi 23 avril 2004 Statut Contributeur Dernière intervention 3 octobre 2023 1 297
9 févr. 2007 à 11:24
je comprend pas d'où viens ton problème...
Tu le met bien avant socket ton WSAStartup?
bzero(), je ne sais absolument pas à quoi ça sert, et je m'en passe très bien vu que le programme tourne nickel.
0 n'est pas une erreur de la fonction socket(), te focalise pas dessus. Il me semble que la variable socket est modifiée dans le bind().
essai le programme sur un autre PC au pire, voir si ça viens de là.
Au fait, quel compilateur utilise tu? Moi, gcc (possible problème ou option supplémentaire avec vcc ?)
autre problème déjà eu : est tu sur qu'aucun serveur n'écoute déjà par le port désigner?
0
Stupeflip Messages postés 391 Date d'inscription jeudi 8 février 2007 Statut Membre Dernière intervention 4 décembre 2007 94
9 févr. 2007 à 11:33
Le bzero() c'est juste pour mettre des zéros partout :) C'est comme une initialisation si tu veux.

Sinon j'ai essayé de voir si l'erreur venait d'un autre endroit, mais je ne trouve pas d'erreur ! Pour le sizeof, le bind() ne nécessite pas de &valeur, contrairement au accept(), c'est pourquoi je mets directement sizeof() sans passer par une variable intermédiaire.

En ce qui concerne les ports, ça ne doit pas être cela non plus, par ailleurs j'ai testé divers ports et cela me fait le même problème ! Pas d'attente bloquante sur le accept() ! Alors que je ne lance que le serveur !

Je vais continuer à regarder au niveau du bind !

Cela donne :
-> Valeur du descripteur listenfd après socket() : 0
-> Valeur du descripteur listenfd après bind() : 0
-> Valeur du descripteur listenfd après listen() : 0
-> Valeur du descripteur listenfd après accept() : 0
-> Valeur du nouveau descripteur connfd après accept() : 0

En ce qui concerne le compilateur, je n'en sais rien ! Mais c'est surement pas gcc qui me manque terriblement ! :p
0
Char Snipeur Messages postés 9696 Date d'inscription vendredi 23 avril 2004 Statut Contributeur Dernière intervention 3 octobre 2023 1 297
9 févr. 2007 à 17:34
tu as mal compris ce que j'ai dit pour le sizeof de bind et accept.
tu met :
clilen=sizeof(cliaddr);
J'ai mi :
clilen=sizeof(SOCKADDR_IN);
Tu peux avoir gcc pour windows, mais je ne pense pas que cela résoudra le problème.
Les problèmes que j'ai eu avec pas d'attente à l'accept, ça venait du troisième argument.
Je vais tenter de faire un prog simpl de serveur que tu test voir si il fonctionne chez toi.
0
Stupeflip Messages postés 391 Date d'inscription jeudi 8 février 2007 Statut Membre Dernière intervention 4 décembre 2007 94
12 févr. 2007 à 16:13
Désolé pour le retard mais retour de week end oblige !

Voilà j'ai testé de changer le type du sizeof() en sockaddr_in mais ça n'a rien changé hélas :(

Toujours cette connexion automatique sur 204.204.204.204 dont je n'arrive pas à déterminer l'origine (et donc je n'arrive pas à trouver le hib dans le programme voire dans le système)...

Sinon détail qui peut être important : comme je boucle pour les accept(), il fait sa connexion puis enchaîne sur une nouvelle connexion etc... Cela donne un log du genre :

Listening ...
Waiting for connection ...
[TCP] Connection acquired from (204.204.204.204)
[TCP] Connection acquired from (204.204.204.204)
[TCP] Connection acquired from (204.204.204.204)
[TCP] Connection acquired from (204.204.204.204)
[TCP] Connection acquired from (204.204.204.204)
[TCP] Connection acquired from (204.204.204.204)
[TCP] Connection acquired from (204.204.204.204)
[TCP] Connection acquired from (204.204.204.204)
...
etc

Jusqu'à ce que je mette fin manuellement au programme.
0
Hello :)

Je me permets de me joindre à la discussion si elle n'est pas terminée ^^
En effet j'ai a peut pres le même souci que Stupeflip, à savoir que mon client me retourne un "-1" sur le connect :

connect(sock_client, (SOCKADDR *)&add_client, sizeof(add_client));

J'ai tenté un cerr<<"connect a echoue avec l'erreur "<< WSAGetLastError()<< endl;

Mais je ne suis pas sur que cela fonctionne (à noter que ce rapport d'erreur fonctionne sur le bind) car il me retourne l'erreur 10049 : l'adresse de connexion n'existe pas...Ce qui est bizare puisque je tente de me connecter sur localhost (127.0.0.1) ^^

Si vous avez avancé dans le problème :)

Merci de m'en faire part!
0
Stupeflip Messages postés 391 Date d'inscription jeudi 8 février 2007 Statut Membre Dernière intervention 4 décembre 2007 94
5 mars 2007 à 11:01
Salut,

Oui j'ai réussi à passer ce problème en copiant une routine de connexion client serveur je sais plus où, codes-sources.com un truc dans le genre ;)

Ensuite j'l'ai mis dans mon programme et je n'ai plus d'erreur !

Bonne chance
0
Ok, tu es mon dernier espoire ^^

Pourrais tu faire un c/c de ton code pour la creation + connexion de la socket client s'il te plait?

Ou me trouver le lien du code source qui t'a aidé :D

Ca fait deux jours que je tourne sur google, choppant différentes sources qui sont sensiblement les même mais ça ne fonctionne pas =(

Merci :D
0
Stupeflip Messages postés 391 Date d'inscription jeudi 8 février 2007 Statut Membre Dernière intervention 4 décembre 2007 94
5 mars 2007 à 12:19
Voici le serveur :

// ********************************************
// Nom du code : ecoute_tcp.cpp
// Auteur : _SebF AT frameIP.com
// date de création : 10 juin 2004
// version : 1.0
// Licence : Ce code est libre de toute utilisation.
// La seule condition existante est de faire référence au site https://www.frameip.com/ afin de respecter le travail d'autrui.
// ********************************************

// ********************************************************
// Les includes
// ********************************************************
#include "stdafx.h"
#include <winsock2.h> // pour les fonctions socket
#include <cstdio> // Pour les Sprintf

// ********************************************************
// Les librairies
// ********************************************************
#pragma comment(lib,"ws2_32.lib")

// ********************************************************
// Définition des variables
// ********************************************************
WSADATA initialisation_win32; // Variable permettant de récupérer la structure d'information sur l'initialisation
int erreur; // Variable permettant de récupérer la valeur de retour des fonctions utilisées
int tempo; // Variable temporaire de type int
int nombre_de_caractere; // Indique le nombre de caractères qui a été reçu ou envoyé
char buffer[65535]; // Tampon contenant les données reçues ou envoyées
SOCKET id_de_la_socket; // Identifiant de la socket
SOCKET id_de_la_nouvelle_socket; // Identifiant de la nouvelle socket
SOCKADDR_IN information_sur_la_source; // Déclaration de la structure des informations lié à l'écoute

int main (int argc, char* argv[])
{
printf("\nTCP/IP Serveur module de communication np_2\n");

// ********************************************************
// Initialisation de Winsock
// ********************************************************
erreur=WSAStartup(MAKEWORD(2,2),&initialisation_win32);
if (erreur!=0)
printf("\nDesole, je ne peux pas initialiser Winsock du a l'erreur : %d %d",erreur,WSAGetLastError());
else
printf("\nWSAStartup : OK");

// ********************************************************
// Ouverture d'une Socket
// ********************************************************
id_de_la_socket=socket(AF_INET,SOCK_STREAM,0);
if (id_de_la_socket==INVALID_SOCKET)
printf("\nDesole, je ne peux pas creer la socket du a l'erreur : %d",WSAGetLastError());
else
printf("\nsocket : OK");

// ********************************************************
// Activation de l'option permettant d'activer l'algorithme de Nagle
// ********************************************************
tempo=1;
erreur=setsockopt(id_de_la_socket,IPPROTO_TCP,TCP_NODELAY,(char *)&tempo,sizeof(tempo));
if (erreur!=0)
printf("\nDesole, je ne peux pas configurer cette options du à l'erreur : %d %d",erreur,WSAGetLastError());
else
printf("\nsetsockopt : OK");

// ********************************************************
// Lie la socket à une ip et un port d'écoute
// ********************************************************
information_sur_la_source.sin_family=AF_INET;
information_sur_la_source.sin_addr.s_addr=INADDR_ANY; // Ecoute sur toutes les IP locales
information_sur_la_source.sin_port=htons(33333); // Ecoute sur le port 33333
erreur=bind(id_de_la_socket,(struct sockaddr*)&information_sur_la_source,sizeof(information_sur_la_source));
if (erreur!=0)
printf("\nDesole, je ne peux pas ecouter ce port : %d %d",erreur,WSAGetLastError());
else
printf("\nbind : OK");

// ********************************************************
// Attente d'ouverture de session
// ********************************************************
erreur=99; // Initiation de erreur pour être sur que l'on va rentrer dans la boucle
while(erreur!=0) // Boucle tant qu'une demande de session (SYN) tcp n'a pas été reçu
erreur=listen(id_de_la_socket,1);
printf("\nlisten : OK");

// ********************************************************
// Acceptation de la demande d'ouverture de session
// ********************************************************
printf("\nAttente de la reception de demande d'ouverture de session tcp (SYN)");
tempo=sizeof(information_sur_la_source); // Passe par une variable afin d'utiliser un pointeur
id_de_la_nouvelle_socket=accept(id_de_la_socket,(struct sockaddr*)&information_sur_la_source,&tempo);
if(id_de_la_nouvelle_socket==INVALID_SOCKET)
printf("\nDesole, je ne peux pas accepter la session TCP du a l'erreur : %d",WSAGetLastError());
else
printf("\naccept : OK");

// ********************************************************
// Reception des données
// ********************************************************
do{
nombre_de_caractere=recv(id_de_la_nouvelle_socket,buffer,1515,0);
if (nombre_de_caractere==SOCKET_ERROR)
printf("\nDesole, je n'ai pas recu de donnee");
else
{
buffer[nombre_de_caractere]=0; // Permet de fermer le tableau après le contenu des data, car la fonction recv ne le fait pas
printf("\nVoici les donnees : %s",buffer);
}
}while(strcmp(buffer,"quit")!=0);

// ********************************************************
// Fermeture de la session TCP Correspondant à la commande connect()
// ********************************************************
erreur=shutdown(id_de_la_nouvelle_socket,2); // 2 signifie socket d'émission et d'écoute
if (erreur!=0)
printf("\nDesole, je ne peux pas fermer la session TCP du a l'erreur : %d %d",erreur,WSAGetLastError());
else
printf("\nshutdown : OK");

// ********************************************************
// Fermeture des deux socket correspondant à la commande socket() et accept()
// ********************************************************
erreur=closesocket(id_de_la_nouvelle_socket);
if (erreur!=0)
printf("\nDesole, je ne peux pas liberer la socket du a l'erreur : %d %d",erreur,WSAGetLastError());
else
printf("\nclosesocket : OK");

erreur=closesocket(id_de_la_socket);
if (erreur!=0)
printf("\nDesole, je ne peux pas liberer la socket du a l'erreur : %d %d",erreur,WSAGetLastError());
else
printf("\nclosesocket : OK");

// ********************************************************
// Quitte proprement le winsock ouvert avec la commande WSAStartup
// ********************************************************
erreur=WSACleanup(); // A appeler autant de fois qu'il a été ouvert.
if (erreur!=0)
printf("\nDesole, je ne peux pas liberer winsock du a l'erreur : %d %d",erreur,WSAGetLastError());
else
printf("\nWSACleanup : OK");
return 0;
} 


Et voila le client :

// ********************************************
// Nom du code : envoi_tcp.cpp
// Auteur : _SebF AT frameIP.com
// date de création : 10 juin 2004
// version : 1.0
// Licence : Ce code est libre de toute utilisation.
// La seule condition existante est de faire référence au site https://www.frameip.com/ afin de respecter le travail d'autrui.
// ********************************************

// ********************************************************
// Les includes
// ********************************************************
#include "stdafx.h"
#include <winsock2.h> // pour les fonctions socket
#include <cstdio> // Pour les Sprintf

// ********************************************************
// Les librairies
// ********************************************************
#pragma comment(lib,"ws2_32.lib")

// ********************************************************
// Définition des variables
// ********************************************************

WSADATA initialisation_win32; // Variable permettant de récupérer la structure d'information sur l'initialisation
int erreur; // Variable permettant de récupérer la valeur de retour des fonctions utilisées
int tempo; // Variable temporaire de type int
int nombre_de_caractere; // Indique le nombre de caractères qui a été reçu ou envoyé
char buffer[65535]; // Tampon contennant les données reçues ou envoyées
SOCKET id_de_la_socket; // Identifiant de la socket
SOCKADDR_IN information_sur_la_destination; // Déclaration de la structure des informations lié au serveur

int main (int argc, char* argv[])
{
printf("\nTCP/IP Client Simulation Caisse\n");

// ********************************************************
// Initialisation de Winsock
// ********************************************************
erreur=WSAStartup(MAKEWORD(2,2),&initialisation_win32);
if (erreur!=0)
printf("\nDesole, je ne peux pas initialiser Winsock du a l'erreur : %d %d",erreur,WSAGetLastError());
else
printf("\nWSAStartup : OK");

// ********************************************************
// Ouverture d'une Socket
// ********************************************************
id_de_la_socket=socket(AF_INET,SOCK_STREAM,0);
if (id_de_la_socket==INVALID_SOCKET)
printf("\nDesole, je ne peux pas creer la socket du a l'erreur : %d",WSAGetLastError());
else
printf("\nsocket : OK");

// ********************************************************
// Activation de l'option permettant d'activer l'algorithme de Nagle
// ********************************************************
tempo=1;
erreur=setsockopt(id_de_la_socket,IPPROTO_TCP,TCP_NODELAY,(char *)&tempo,sizeof(tempo));
if (erreur!=0)
printf("\nDesole, je ne peux pas configurer cette options du à l'erreur : %d %d",erreur,WSAGetLastError());
else
printf("\nsetsockopt : OK");

// ********************************************************
// Etablissement de l'ouverture de session
// ********************************************************
information_sur_la_destination.sin_family=AF_INET;
information_sur_la_destination.sin_addr.s_addr=inet_addr("127.0.0.1"); // Indiquez l'adresse IP de votre serveur
information_sur_la_destination.sin_port=htons(33333); // Port écouté du serveur (33333)
erreur=connect(id_de_la_socket,(struct sockaddr*)&information_sur_la_destination,sizeof(information_sur_la_destination));
if (erreur!=0)
printf("\nDesole, je n'ai pas pu ouvrir la session TCP : %d %d",erreur,WSAGetLastError());
else
printf("\nsetsockopt : OK");

// ********************************************************
// Envoi des données
// ********************************************************
do{
printf("\nMessage a envoyer : ");
gets(buffer);
//strcpy(buffer,"Coucou, je suis les donnees. www.frameip.com"); // Copie la chaine de caractère dans buffer
nombre_de_caractere=send(id_de_la_socket,buffer,strlen(buffer),0);
if (nombre_de_caractere==SOCKET_ERROR)
printf("\nDesole, je n'ai pas envoyer les donnees du a l'erreur : %d",WSAGetLastError());
else
printf("\nsend : OK");
}while(strcmp(buffer,"quit")!=0);

// ********************************************************
// Fermeture de la session TCP Correspondant à la commande connect()
// ********************************************************
erreur=shutdown(id_de_la_socket,2); // 2 signifie socket d'émission et d'écoute
if (erreur!=0)
printf("\nDesole, je ne peux pas fermer la session TCP du a l'erreur : %d %d",erreur,WSAGetLastError());
else
printf("\nshutdown : OK");

// ********************************************************
// Fermeture de la socket correspondant à la commande socket()
// ********************************************************
erreur=closesocket(id_de_la_socket);
if (erreur!=0)
printf("\nDesole, je ne peux pas liberer la socket du a l'erreur : %d %d",erreur,WSAGetLastError());
else
printf("\nclosesocket : OK");

// ********************************************************
// Quitte proprement le winsock ouvert avec la commande WSAStartup
// ********************************************************
erreur=WSACleanup(); // A appeler autant de fois qu'il a été ouvert.
if (erreur!=0)
printf("\nDesole, je ne peux pas liberer winsock du a l'erreur : %d %d",erreur,WSAGetLastError());
else
printf("\nWSACleanup : OK");
return 0;
} 
0
The_Moye > Stupeflip Messages postés 391 Date d'inscription jeudi 8 février 2007 Statut Membre Dernière intervention 4 décembre 2007
5 mars 2007 à 15:28
Merci beaucoup Stupeflip :)

J'ai reussi à comprendre mes erreurs et ça marche nikel :D

A moi les joies des sockets xD
0
moi ce code ne marche pas chez moi. j'utilise dev C++. les erreurs sont du genre multiple definition of... et le problème est ke j'en ais pleins des erreurs comme ca. je débute en prog C/C++ et j'aurais voulus savoir pourquoi ca marche pas. si il y a des manip ou autre a faire. merci d'avance de prendre le tps de me lire et peu etre de me répondre.
0