Probleme socket + API ( +thread ?) [Résolu]

Signaler
Messages postés
71
Date d'inscription
lundi 24 mai 2004
Statut
Membre
Dernière intervention
13 septembre 2006
-
Messages postés
1403
Date d'inscription
lundi 23 février 2004
Statut
Membre
Dernière intervention
11 janvier 2009
-
Bonjour à tous,

Voila j'avais deja poster dans un précédent sujet mais comme j'ai revu tout mon code cela va etre plus simple de répondre. J'ai donc créer une application réseau (graphique) qui créer une socket et qui se met en écoute en attente d'une connexion.

Mon probleme est que lorsque je clique sur mon bouton pour que l'appli se mette en écoute, la fenetre se fige et ensuite plante.  Le problème vient du fait que j'ai une boucle pour actualiser l'affichage dans "WinMain" ce qui est logique, et une autre qui permet au prog d'etre en écoute (dans la procedure "create_connexion"). Donc lorsque le prog se met en écoute il se bloque dans la boucle d'ecoute et l'affichage ne se fait plus et tout plante.
J'ai entendu vaguement parler des "thread" d'ou le ? dans le titre du sujet mais je ne sais pas du tout m'en servir et je ne suis pas sur non plus que cela règle mon problème.

Si quelqu'un a une idée... Merci d'avance et désolé pour le roman :)

Voila mon code:

/****************BOUCLE PRINCIPALE**************************/
int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow){

        MSG msg; //récupère les messages de windows

        //crée la fenetre
        hwnd = CreateWnd(hInstance);
        ShowWindow (hwnd, iCmdShow);
        //crée un bouton Connexion
        hBoutonConnect = CreateWindow("button", "Lancer", WS_CHILD | WS_BORDER, 95, 30, 90, 20, hwnd, 0, hInstance, 0);
        ShowWindow(hBoutonConnect, iCmdShow);
        //crée un bouton Quitter
        hBoutonQuit = CreateWindow("button", "Quitter", WS_CHILD | WS_BORDER, 10, 60, 175, 20, hwnd, 0, hInstance, 0);
        ShowWindow(hBoutonQuit, iCmdShow);
        //raffraichit la fenetre
        UpdateWindow (hwnd);
    
    //---------Boucle d'affichage---------------------
     while (GetMessage (&msg, NULL, 0, 0)){
          TranslateMessage (&msg);
          DispatchMessage (&msg);
     }
     return msg.wParam;
}
/************FIN DE LA BOUCLE PRINCIPALE*****************/

/******************CREATION DE LA FENETRE*******************/
HWND CreateWnd(HINSTANCE hInst){
 code ........
}
/***************FIN CREATION DE LA FENETRE*****************/

/*********************CLIENT***************************/
void create_connexion(){

    int port=0,erreur;
 
    WSADATA wsa;
    /* initialisation */
    WSAStartup(MAKEWORD(2,0), &wsa);
       
        //variables pour la connexion réseau
        SOCKET serveur;
        SOCKET client;
        SOCKADDR_IN sin;
        SOCKADDR_IN clientsin;
 
    /* creation de la socket serveur */
    serveur  = socket(AF_INET,SOCK_STREAM,0);
    if(serveur == INVALID_SOCKET){
        MessageBox (NULL, "Impossible de créer la socket", "Client", MB_OK | MB_ICONEXCLAMATION);
        exit(-1);
    }
    /* configuration de la socket */
    sin.sin_addr.s_addr = INADDR_ANY;
    sin.sin_family = AF_INET;
    sin.sin_port = htons(port);
 
    /* attacher le socket au n° de port*/
    erreur=bind(serveur,(SOCKADDR *)&sin, sizeof(sin));
    if(erreur == INVALID_SOCKET){
        MessageBox (NULL, "Impossible d'ouvrir le port", "Client", MB_OK | MB_ICONEXCLAMATION);
        exit(-1);
    }
    /* creation d'une file d'attente de demande de connexion */
    listen(serveur,0);
    MessageBox (NULL, "Client en écoute", "Client", MB_OK | MB_ICONEXCLAMATION);

        int val = sizeof(clientsin);

        //---------Boucle d'écoute---------------------
        while (client = accept(serveur,(SOCKADDR *)&clientsin,&val)){
       
            /* accepter une connexion */   
            if(client == INVALID_SOCKET)
                MessageBox (NULL, "Erreur de connexion", "Client", MB_OK | MB_ICONEXCLAMATION);
            else
                MessageBox (NULL, "Serveur connecter", "Client", MB_OK | MB_ICONEXCLAMATION);
                /* fonction qui utilise la socket */
                traitement(client);
        }
 
}
/*********************FIN CLIENT*************************/

/*********************TRAITEMENT**********************/
void traitement(SOCKET client){
    code .......
}
/*********************FIN DU TRAITEMENT*******************/

/************************************************************/
/****CONTROLE DES RETOURS DE MESSAGES DE WINDOWS*****/
LRESULT CALLBACK WndProc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam){
         code .............
}
/***FIN DU CONTROLE DES RETOURS DE MESSAGES DE WINDOWS****/
/************************************************************/

4 réponses

Messages postés
71
Date d'inscription
lundi 24 mai 2004
Statut
Membre
Dernière intervention
13 septembre 2006
2
C'est bon j'ai trouver la solution. Il fallait bien que je crée un thread pour mettre ma boucle d'ecoute dedans. Pour ceux qui ont le meme probleme il faut utiliser la fonction CreateThread. Google vous aidera ;-)
Messages postés
1403
Date d'inscription
lundi 23 février 2004
Statut
Membre
Dernière intervention
11 janvier 2009
3
Houla !!!
Pas besoin de boucle d'écoute. Mais une boucle d'attente de connexion plutôt.
pour ça il faut que tu utilises un thread pour que ton prog ne se fige pas.

YOYO, @+.
[font= Comic Sans MS][size=3] [green][:D] YOYO [;)]/green =3Sans MS
Messages postés
694
Date d'inscription
lundi 5 décembre 2005
Statut
Membre
Dernière intervention
8 janvier 2014
15
lut,

Communication par socket en mode connecté (SOCK_STREAM)

Organisation du serveur :

1) Création et attachement de la socket d'écoute socket()/bind()
2) Ouverture du service listen()
3) Attente de demande de connexion accept()
4) Traitement direct ou création d'un processus fork()
5) Parent -> Retour 3)
5) Enfant -> Traitement de la demande

Organisation du client :

1) Création (et attachement possible) d'une socket socket()/bind()
2) Construction de l'adresse serveur
3) Demande de connexion connect()
4) Si Echec(3) -> Retour 3)
4) Sinon : Dialogue avec le serveur

Il y a 2 unités de traitement au moins -> 2 process (2 programmes) ou 2 threads. Sinon, je ne vois pas d'autres solutions.
Messages postés
1403
Date d'inscription
lundi 23 février 2004
Statut
Membre
Dernière intervention
11 janvier 2009
3
C'est vrai que j'aurai dû te préciser la fonction, désolé !

YOYO, @+.
 YOYO
"L'intelligence c'est comme un parachute, quand on en n'a pas...on s'écrase !!!"