/* * * Wed May 2 18:55:37 DST 2001 * Sample tcp server using fork() * * :set tabstop=4 * */ static char __ident[] = "@(#)SPDsoft, Wed May 2 18:55:37 DST 2001"; #include #include /* atoi */ #include /* getpid */ #include #include #include #include #include #include #include #include int s; int kids=0; int done; void clean( int i ); void do_wait(int signal); int main(int argc, char *argv[]) { double n; long n_p,nbytes; int len; int sockfd; int clientlen; int queue; struct sockaddr_in server, client; FILE *fd; char buf[10000]; char *myname; char *host; char *user; char hostname[256]; struct hostent *hp; unsigned int port; int pid; if (argc!=2) { printf( "use: %s port\n", argv[0] ); exit(1); } port = (unsigned int) atoi(argv[1]); memset(&server,0,sizeof(server)); if (gethostname(hostname,sizeof(hostname)) < 0) { perror("gethostname: who am I ?"); exit(1); } if ( (hp=gethostbyname(hostname)) == NULL) { perror("gethostbyname: can't get an address"); exit(2); } server.sin_family = AF_INET; /* server.sin_port=atoi(buf);*/ server.sin_port = htons(port); /* server.sin_addr.s_addr = htonl(INADDR_ANY);*/ /* server.sin_addr.s_addr =inet_addr(argv[1]);*/ server.sin_addr.s_addr = htonl( ((struct in_addr *)(hp->h_addr_list[0]))->s_addr ); queue=3; if (( SIG_ERR == sigset(SIGTERM, clean)) || ( SIG_ERR == sigset(SIGINT, clean)) || ( SIG_ERR == sigset(SIGCHLD, do_wait)) ) perror("signal"); if ( (s=socket(AF_INET,SOCK_STREAM,0)) == -1 ) { perror("socket"); exit(1); } if( bind( s, (struct sockaddr *)&server, sizeof(server)) != 0 ) { perror("bind"); exit(1); } if ( listen( s, queue ) != 0 ) { perror("listen"); exit(1); } for(done=0; !done; ) { fprintf(stderr,"%d accepting\n", getpid()); if( ( sockfd = accept( s, 0, 0 ) ) < 0 ) if ( errno != EINTR ) { perror("accept"); break; } else continue; switch( pid = fork()) { case -1: perror("fork"); break; case 0: n = 0; n_p = 0; nbytes = recv(sockfd,buf,sizeof(buf),0); buf[nbytes]=0x00; write(sockfd,"ack\r\n",5); while(nbytes>0) { fprintf(stdout,"MSG: \"%s\"\n",buf); fflush(stdout); n += nbytes; n_p += 1; nbytes = recv(sockfd,buf,sizeof(buf),0); buf[nbytes]=0x00; write(s,"ack\r\n",5); } printf("Rec: %.0f bytes %.0ld packets\n",n,n_p); fprintf(stderr,"die %d\n", getpid()); close( s ); exit(0); break; default: fprintf(stderr, "%d spawned %d\n", ++kids, pid ); fflush(stderr); break; } } while ( kids > 0 ) { sigpause(SIGCLD); sighold(SIGCLD); } if ( s != 0 ) { if ( -1 == close(s)) perror("close"); } exit(errno); } /************************************************************************/ void clean( int sig ) { if ( SIG_ERR == sigset(sig, clean)) perror("clean:signal"); fprintf(stderr,"%d a escaparrar (%d)\n", getpid(), sig); done=1; } void do_wait(int sig) { int st; int wpid; wpid = wait ( &st ); fprintf(stderr, "wait: died %d\n", wpid); if (WIFSTOPPED(st)) { fprintf(stderr,"stoped %d\n", WSTOPSIG(st)); } else if(WIFEXITED(st)) { fprintf(stderr, "do_wait: %d exit with %d\n", wpid, WEXITSTATUS(st)); } else if(WIFSIGNALED(st)) { fprintf(stderr,"signaled %d\n", WTERMSIG(st)); } if(st&0200) fprintf(stderr, "core dumped\n"); fprintf(stderr, "do_wait: died %d\n", wpid); fprintf(stderr, "nkids %d\n", --kids); fflush(stderr); sigset(SIGCHLD, do_wait); }