2012-12-15 35 views
2

我一直在努力编写一些套接字编程在Linux中,我试图做一个并发代理服务器。基本上我希望连接到代理服务器的每个客户端遇到2个问题。第一个是介绍命运的IP,第二个是它的端口号。在发送这些信息之后,代理服务器将把每个客户端连接到他们选择的IP(这是和回显服务器)。C Linux的tcp代理服务器套接字

我的问题是如何以及将在哪里保存每个用户回答的2个问题,然后将它们连接到他们选择的回显服务器。

这里的,我认为我们必须在工作的部分代码:

/*============ WARNS THAT SERVER IS READY TO ACCEPT REQUESTS ==================*/ 
if(listen(sockfd,5)==-1) Abort("Impossible to accept requests"); 

/*========== STARTS ANSWERING CLIENTS BY CONCURRENT FORM =============*/ 
cliaddr_len=sizeof(cli_addr); 
while(1){ 

    FD_ZERO(&fd_read); 
    FD_SET(STDIN_FILENO, &fd_read); 
    FD_SET(sockfd, &fd_read); 

    fflush(stdin); 

    n=select(32, &fd_read, NULL, NULL, NULL); 

    if(n<0) 
     if(errno!=EINTR){ 
      close(sockfd); 
      Abort("Error on select"); 
     }else 
      continue; 


    if(FD_ISSET(STDIN_FILENO, &fd_read)){ 
     gets(comando); 
     if(strcmp(comand, "exit")==0){ 
      close(sockfd); 
      printf("Goodbye...\n"); 
      exit(0); 
     } 
    } 

    if(FD_ISSET(sockfd, &fd_read)) 
     if((newsockfd=accept(sockfd,(struct sockaddr *)&cli_addr,&cliaddr_len)) 
         ==-1) 
      fprintf(stderr,"<SERV>Impossible to accept clients...\n"); 
     else{ 
      switch(fork()){/*Goes to backgroud*/ 
       case -1:fprintf(stderr,"Impossible to answer..."); 
        close(newsockfd); 
        break; 
       case 0:close(sockfd); /* SON */ 
        AnswerClient(newsockfd); 
        exit(EXIT_SUCCESS); 
       default:close(newsockfd); /* DAD */ 
      } 
     } 
} 
} 


/*___________________________ AnswerClient ____________________________________ 

______________________________________________________________________________*/ 

void AnswerClient(int sockfd){ 
static char buffer[BUFFERSIZE]; 
static unsigned int cont=0U; 
int nbytes; 
pid_t pid=getpid(); 


while(1){ 
    /*==================== PROCESS REQUEST ==========================*/ 
    cont++; 

    switch((nbytes=ReadLine(sockfd,buffer,BUFFERSIZE))){ 
     case -1:fprintf(stderr,"Error receiving data...\n"); 
       return; 
     case 0:fprintf(stderr,"Client didnt sent data...\n"); 
       return; 
     default:printf("\n<%d>Message received: %s\n",pid,buffer); 
       if(!strncmp(buffer,"exit",4)){ 
        printf("<%d>Going shutdown...\n",pid); 
        close(sockfd); 
        return; 
       } 
       /*============ Sends Confirmation =============*/ 
       sprintf(buffer,"<%d>",pid); 
       nbytes=strlen(buffer); 
       if(WriteN(sockfd,buffer,nbytes)!=nbytes) 
        fprintf(stderr,"Impossible to confirm.\n"); 

    } 
} 
} 

/*_____________________________ ReadLine _______________________________________ 
Reads a line (until find the caracter '\n') of a socket. 
Returns: 
-1 : if error 
0 : EOF 
!= : if read some bytes 
______________________________________________________________________________*/ 

int ReadLine(int sockfd,char* buffer,int maxlen){ 
int n,rc; 
char c; 

for(n=0;n<maxlen-1;n++){ 
    if((rc=read(sockfd,&c,1))==1){ 
     *buffer++=c; 
     if(c=='\n') break; 
    }else if (rc==0) { 
     if(n==0) return(0); /*EOF*/ 
     else break; /*EOF but has already read some bytes*/ 
    } else return(-1); /*Error*/ 
} 
*buffer=0; 
return(n); 
} 

/*______________________________ WriteN _______________________________________ 
Writes n bytes on socket in case. Returns the number of bytes writen. 
______________________________________________________________________________*/ 
int WriteN(int sockfd,char * buffer,int nbytes){ 

int nleft,nwritten; 

nleft=nbytes; 
while(nleft>0){ 
    if((nwritten=write(sockfd,buffer,nleft))<=0) return(nwritten); 
    nleft-=nwritten; 
    buffer+=nwritten; 
} 
return(nbytes-nleft); 
} 

void Abort(char *msg){ 
fprintf(stderr,"\a<SER1>Fatal error: <%s>\n",msg); 
perror("Erro do sistema"); 
exit(EXIT_FAILURE); 
} 

void buryZombie() 
{ 
static int status; 
wait(&status); 

} 

可有人请给我一个提示或只是告诉我正确的方法是什么?

RicardoCosta

回答

1

要通过TCP连接,一方将不得不连接到另一方。代理可以决定哪一个连接,并通知一个客户端是服务器而另一个客户端是客户端。