服务器,客户端都是父进程、子进程分别负责发送、接收字符串。
另外使用了信号函数来发送和接收处理信号,比如当子进程结束时,传递一个信号给父进程,然后父进程会执行信号处理函数。
服务器端:
1 #include2 #include 3 #include 4 #include 5 #include 6 #include 7 #include 8 #include 9 #include 10 11 void handler(int sig)//这是信号处理函数12 {13 printf("recv a sig:%d",sig);14 exit(EXIT_SUCCESS);15 }16 17 int main()18 {19 int sockfd=socket(AF_INET,SOCK_STREAM,0);20 if(sockfd<0) perror("socket!!!!");21 22 int on=1;23 int result=setsockopt(sockfd,SOL_SOCKET,SO_REUSEADDR,&on,sizeof(on));//启用套接字选项,必须在bind之前完成24 if(result<0) perror("setsockopt");25 26 struct sockaddr_in server_addr;27 memset(&server_addr,0,sizeof(server_addr));28 server_addr.sin_family=AF_INET;29 server_addr.sin_port=htons(888);30 server_addr.sin_addr.s_addr=htonl(INADDR_ANY);31 32 33 int res=bind(sockfd,(struct sockaddr*)&server_addr,sizeof(server_addr));34 if(res<0)perror("bind!!!");35 36 res=listen(sockfd,50);37 if(res<0) perror("listen!!");38 39 int conn_fd;40 struct sockaddr_in peeraddr;41 int addr_len=sizeof(peeraddr);42 pid_t pid;43 44 conn_fd=accept(sockfd,(struct sockaddr*)&peeraddr,&addr_len);45 if(conn_fd<0)perror("accept!!");46 printf(" the ip of client:%s,the port of client:%d\n",inet_ntoa(peeraddr.sin_addr),ntohs(peeraddr.sin_port));//打印对等方的ip与端口47 48 //signal(SIGUSR1,handler);49 pid=fork();50 if(pid<0)51 perror("fork failed");52 else if(pid==0)53 { //子进程54 char recvbuf[1024]={ 0};55 while(1)56 {57 memset(recvbuf,0,sizeof(recvbuf));58 int resu;59 resu=read(conn_fd,recvbuf,sizeof(recvbuf));60 if(resu<0)perror("read");61 else if(resu==0)62 { 63 printf("peer closed!!!!");64 //exit(EXIT_SUCCESS);65 kill(getppid(),SIGUSR1);//发送一个信号给父进程66 break;67 }68 fputs(recvbuf,stdout);69 }70 //close(conn_fd);71 //close(sockfd);72 exit(EXIT_SUCCESS);73 }74 else //父进程75 {76 signal(SIGUSR1,handler);//安装信号接收函数77 char sendbuf[1024]={ 0};78 while(fgets(sendbuf,sizeof(sendbuf),stdin)!=NULL)79 {80 write(conn_fd,sendbuf,strlen(sendbuf));81 memset(sendbuf,0,sizeof(sendbuf));82 }83 //close(conn_fd);84 //close(sockfd);85 exit(EXIT_SUCCESS);86 }87 return 0;88 }
客户端:
1 #include2 #include 3 #include 4 #include 5 #include 6 #include 7 #include 8 #include 9 int main()10 {11 int sockfd= socket(AF_INET,SOCK_STREAM,0);12 if(sockfd<0)perror("socket");13 14 struct sockaddr_in server_addr;15 memset(&server_addr,0,sizeof(server_addr));16 server_addr.sin_family=AF_INET;17 server_addr.sin_port=htons(888); //this port number is owned by server,and client's port number is appointed by random18 server_addr.sin_addr.s_addr=inet_addr("127.0.0.1");//服务器端的ip地址19 20 int res=connect(sockfd,(struct sockaddr*)&server_addr,sizeof(server_addr));21 if(res<0)perror("connect!!!!!!!");22 23 pid_t pid;24 pid=fork();25 if(pid<0)perror("fork");26 if(0==pid)//子进程27 {28 char recvbuf[1024];29 int ret;30 while(1)31 {32 memset(recvbuf,0,sizeof(recvbuf));//防止空间中的内容干涉,拖泥带水33 ret=read(sockfd,recvbuf,sizeof(recvbuf));34 if(ret<0)perror("read");35 if(ret==0)36 {37 printf("peer closed!!!!!!!");38 break;39 }40 fputs(recvbuf,stdout);41 }42 close(sockfd);43 }44 else45 {46 char sendbuf[1024];47 while(fgets(sendbuf,sizeof(sendbuf),stdin)!=NULL){48 write(sockfd,sendbuf,strlen(sendbuf));49 memset(sendbuf,0,sizeof(sendbuf));50 }51 //exit(EXIT_SUCCESS);}52 close(sockfd);53 }54 return 0;55 }