[C] chat socket/fork/pipe

Résolu/Fermé
cedricdd Messages postés 1 Date d'inscription jeudi 8 mars 2007 Statut Membre Dernière intervention 8 mars 2007 - 8 mars 2007 à 02:27
 besla - 26 mars 2008 à 17:31
Voila j'ai comme projet de réaliser un chat en C,en utilisant les sockets, fork et des pipes, mais j'ai des erreurs dans mon serveur, pourtant je ne vois pas ou j'ai faux

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <netinet/in.h>
#include <fcntl.h>
#include <unistd.h>
#define maxclient 10
 
 
typedef struct{
 int envoie[2];
 int recep[2];
 int libre;
}t_fils;
       
int main()
 
{
 system("clear" );
 printf("Lancement du serveur\n\n" );
 
 t_fils tabFils[maxclient];
 int i=0,nbrclient=0,client=0,traite=1,test,test2,sock,sock2,duplication,placeclient=0,clientok=0,placeclientenvoie;
 int sizet= sizeof(struct sockaddr);
 struct sockaddr_in sin,csin;
 char bufferR[1024]="",bufferE[1024]="",buffer[1024]="",temp[10]="";
       
 if ( (sock=socket ( AF_INET, SOCK_STREAM, 6)) == -1)
 {
  printf("Socket creation erreur" );
 }
 
   
 memset ( &sin, 0, sizeof(struct sockaddr));
 memset ( &csin, 0, sizeof(struct sockaddr));
 
 sin.sin_family= AF_INET;
 sin.sin_port=htons( 6222);    
 sin.sin_addr.s_addr=htonl(INADDR_ANY);
 
 
 if ( bind( sock,(struct sockaddr *)&sin, sizeof(struct sockaddr) ) == -1 )
 {
  printf("Impossible lier socket" );
 }
 else
 {        
  printf("Serveur ok, en attente de client, nombre maximun de client %i\n\n",maxclient);
 }  
 
 listen(sock, 1);
 
 for(i=0;i<maxclient;i++)
  {
   tabFils[i].libre=0;
  }
 
   
 fcntl(sock, F_SETFL, fcntl ( sock, F_GETFL ) | O_NONBLOCK);
 
 while(nbrclient<10)  //Boucle plusieurs clients
 {
 
 
  client=0;
   
   
   
   
     if( (sock2 = accept(sock ,(struct sockaddr *)&csin, (socklen_t *)&sizet ) ) == -1 )
  {
   //printf("Impossible d'accepter" );
  }
      else  
  {
   printf("\nCLIENT ENTRANT\n\n" );
   client=1;
  }
   
   
  if ( client == 1)
  {
   nbrclient+=1; //Un nouveau client
   
 
   do //Le nouveau client prendra la premiere place libre
   {
    if(tabFils[placeclient].libre == 0) //La place est libre
    {
     if (  pipe(tabFils[placeclient].recep) == -1 || pipe(tabFils[placeclient].envoie) == -1 )  //Pour communiquer entre le pere et le fils
     {
      printf("Erreur lors de la déclaration des tubes" );
     }
     clientok=1;
    }
    else //Un client occupe déjà cette place
    {
     placeclient++;
    }
   }while(clientok !=1); //Le client à trouvé une place
 
 
   duplication=fork();
 
   if( duplication == -1)
   {
    printf("Erreur dans la duplication du processus" );
    exit(0);
   }
 
   if( duplication !=0)  //Processus pere
   {
    close(sock2);
    close(tabFils[placeclient].envoie[0]);
    close(tabFils[placeclient].recep[1]);
    fcntl(tabFils[placeclient].recep[0], F_SETFL, fcntl (tabFils[placeclient].recep[0], F_GETFL ) | O_NONBLOCK);
    tabFils[placeclient].libre=1;
   }
 
   else // Processus fils
   {
 
    close(tabFils[placeclient].envoie[1]);
    close(tabFils[placeclient].recep[0]);
 
    fcntl(sock2, F_SETFL, fcntl ( sock2, F_GETFL ) | O_NONBLOCK);
    fcntl(tabFils[placeclient].envoie[0], F_SETFL, fcntl (tabFils[placeclient].envoie[0],  F_GETFL ) | O_NONBLOCK);
     
 
    while(1)
    {
           
       
     memset(bufferR, 0, sizeof(bufferR));
     memset(buffer, 0, sizeof(buffer));
     
     if ( read(sock2, bufferR, 255) > 0 )
     {
      if ( strlen( bufferR ) !=0) //Pour eviter les messages fantomes
      {
       strncpy(temp, bufferR, 4);
       
       if( strcmp( temp, "exit" ) == 0 )
       {
        write(tabFils[placeclient].recep[1], temp, sizeof(temp));
        close(tabFils[placeclient].envoie[0]);
        close(tabFils[placeclient].recep[1]);
       }
       else
       {
       
        write(tabFils[placeclient].recep[1], bufferR, sizeof(bufferR));
       
       }
      }      
     }
 
 
     memset(bufferE, 0, sizeof(bufferE));
     if ( read (tabFils[placeclient].envoie[0],  bufferE, 1024) > 0 )
     {
      if ( strlen ( bufferE ) != 0 )
      {
       write(sock2, bufferE, sizeof(bufferE));
       printf("J'envoie au client %s",bufferE);
      }
     }
 
    }  
 
   }   //Fin du fils
 
   
 
  }
         //Traitement dans le père
     
    for(test=0;test<nbrclient;test++)
    {
     if( read( tabFils[test].recep[0], bufferR, 1024) > 0)
     {
      if( strlen ( bufferR) !=0 )
      {
       
 
       placeclientenvoie=test;
     
       strncpy(temp, bufferR, 4);
       if( strcmp( temp, "exit" ) == 0 )
       {
        printf("Un client vient de partir, il en reste %i\n",nbrclient-1);
        traite=0;
        nbrclient--;
        tabFils[test].libre=0;
       }
 
 
       if ( traite == 1) //Si se n'est un message de deconnection
       {
        printf("le pere affiche:  %s\n",bufferR);
        if( nbrclient==1)
        {
         write(tabFils[0].envoie[1], "Vous êtes le seul client\r\n", sizeof("Vous êtes le seul client\r\n" ));
        }
 
        else
        {
         for(test2=0;test<nbrclient;test2++)
         {
          if(placeclientenvoie != test2) //On ne renvoie pas a celui qui vient d'écrire
          {
           write(tabFils[test2].envoie[1], bufferR, sizeof(bufferR));
          }
         }
        }
       }
       
       else //De base on retraite le suivant
       {
        traite=1;
       }
      }
     }
    }
     
 
         
 
 }    //Fin boucle plusieurs clients
 
 
close(sock);
close(sock2);  
 
} 
A voir également:

5 réponses

Bonjour,
"
salut cedric, g exactement le même projet ke toi a realiser, pourrais-tu m'envoyer le tien afin ke je puisse ajouter des ameliorations sur le mien ou voir ce que je pourrais modifier... please.
je te laisse mon adresse: kaliyah78@hotmail.fr
"

j'adore :)
0
bonjour,

est ce que tu peux m expliquer un peut ce que tu fais avec fcntl parce que je vois pas trop ce que tu veux faire avec !
"
fcntl(sock2, F_SETFL, fcntl ( sock2, F_GETFL ) | O_NONBLOCK);
fcntl(tabFils[placeclient].envoie[0], F_SETFL, fcntl (tabFils[placeclient].envoie[0], F_GETFL ) | O_NONBLOCK);

"
0
Ben alors CDD, tu as des petits prob de C !!!!!
Utilise les listes chainées sa te fera du bien !!!!!

a demain ! ++
-1
Char Snipeur Messages postés 9813 Date d'inscription vendredi 23 avril 2004 Statut Contributeur Dernière intervention 3 octobre 2023 1 298
13 mars 2007 à 08:46
Salut.
ça doit être un problème de libération de socket sur la boucle.
-1

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

Posez votre question
salut cedric, g exactement le même projet ke toi a realiser, pourrais-tu m'envoyer le tien afin ke je puisse ajouter des ameliorations sur le mien ou voir ce que je pourrais modifier... please.
je te laisse mon adresse: kaliyah78@hotmail.fr
merci
-1