ソケットネットワークプログラミング--チャットプログラム(2)
28236 ワード
前の節は簡単ですが、どうやってソケットで接続を作成して通信しますか?ただ、人は一言しか話せません。しかも、話をしないと情報を受信できません。とにかく不便なことです。だから、この小節は前回のプログラムを修正して、一人一人が多く話すことができるように修正します。主にLinuxの下で多プロセスforkを通じて実現します。
対一で、serverとclientはそれぞれの人が多くの話をすることができます。
台湾のデータを制御する関数fgetsはブロック関数ですので、一人一人が多く話をすることができます。ここで使っているのは読み取りと送信が別々のプロセスの中にあります。お互いに影響がないようにします。
fork関数
ヽoo。ツ。ツ。ツ。ツ。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。
pid_t fork(void) //リターン値:子プロセスでは0を返し、親プロセスでは子プロセスIDを返します。エラーは-1を返します。
client.
この記事のアドレス: http://www.cnblogs.com/wunaozai/p/3870194.html
対一で、serverとclientはそれぞれの人が多くの話をすることができます。
台湾のデータを制御する関数fgetsはブロック関数ですので、一人一人が多く話をすることができます。ここで使っているのは読み取りと送信が別々のプロセスの中にあります。お互いに影響がないようにします。
fork関数
ヽoo。ツ。ツ。ツ。ツ。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。
pid_t fork(void) //リターン値:子プロセスでは0を返し、親プロセスでは子プロセスIDを返します。エラーは-1を返します。
client.
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <errno.h>
4 #include <string.h>
5 #include <netdb.h> //for gethostbyname
6 #include <sys/types.h>
7 #include <sys/socket.h>
8 #include <netinet/in.h>
9 #include <arpa/inet.h>
10
11 #define MAX_BUF 4096
12 #define SERVER_PORT 12138
13
14
15 int main(int argc,char *argv[])
16 {
17 int sockfd;//socket
18 char sendBuf[MAX_BUF],recvBuf[MAX_BUF];
19 int sendSize,recvSize;//
20 struct hostent * host;
21 struct sockaddr_in servAddr;
22 char username[32];
23 char * p;
24 int pid;
25
26 if(argc != 3)
27 {
28 perror("use: ./client [hostname] [username]");
29 exit(-1);
30 }
31 p=username;
32 strcpy(p,argv[2]);
33 printf("username:%s
",username);
34 host=gethostbyname(argv[1]);
35 if(host==NULL)
36 {
37 perror("fail to get host by name.");
38 exit(-1);
39 }
40 printf("Success to get host by name ...
");
41
42 // socket
43 if((sockfd=socket(AF_INET,SOCK_STREAM,0))==-1)
44 {
45 perror("fail to establish a socket");
46 exit(1);
47 }
48 printf("Success to establish a socket...
");
49
50 /*init sockaddr_in*/
51 servAddr.sin_family=AF_INET;
52 servAddr.sin_port=htons(SERVER_PORT);
53 servAddr.sin_addr=*((struct in_addr *)host->h_addr);
54 bzero(&(servAddr.sin_zero),8);
55
56 /*connect the socket*/
57 if(connect(sockfd,(struct sockaddr *)&servAddr,sizeof(struct sockaddr_in))==-1)
58 {
59 perror("fail to connect the socket");
60 exit(1);
61 }
62 printf("Success to connect the socket...
");
63
64 //send-recv , server.c
65 if((pid=fork())<0)
66 {
67 perror("fork error
");
68 }
69 else if(pid>0)/*child*/
70 {
71 while(1)
72 {
73 fgets(sendBuf,MAX_BUF,stdin);
74 send(sockfd,sendBuf,strlen(sendBuf),0);
75 memset(sendBuf,0,sizeof(sendBuf));
76 }
77 }
78 else
79 {
80 while(1)
81 {
82 recv(sockfd,recvBuf,MAX_BUF,0);
83 printf("Server:%s
",recvBuf);
84 memset(recvBuf,0,sizeof(recvBuf));
85 }
86 }
87
88 return 0;
89 }
server. 1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <errno.h>
4 #include <string.h>
5 #include <netdb.h>
6 #include <sys/types.h>
7 #include <sys/socket.h>
8 #include <sys/time.h>
9 #include <sys/un.h>
10 #include <sys/ioctl.h>
11 #include <sys/wait.h>
12 #include <netinet/in.h>
13 #include <arpa/inet.h>
14
15
16 #define SERVER_PORT 12138
17 #define BACKLOG 20
18 #define MAX_CON_NO 10
19 #define MAX_DATA_SIZE 4096
20
21 int main(int argc,char *argv[])
22 {
23 struct sockaddr_in serverSockaddr,clientSockaddr;
24 char sendBuf[MAX_DATA_SIZE],recvBuf[MAX_DATA_SIZE];
25 int sendSize,recvSize;
26 int sockfd,clientfd;
27 int on=1;
28 int sinSize=0;
29 char username[32];
30 int pid;
31
32 if(argc != 2)
33 {
34 printf("usage: ./server [username]
");
35 exit(1);
36 }
37 strcpy(username,argv[1]);
38 printf("username:%s
",username);
39
40 /*establish a socket*/
41 if((sockfd = socket(AF_INET,SOCK_STREAM,0))==-1)
42 {
43 perror("fail to establish a socket");
44 exit(1);
45 }
46 printf("Success to establish a socket...
");
47
48 /*init sockaddr_in*/
49 serverSockaddr.sin_family=AF_INET;
50 serverSockaddr.sin_port=htons(SERVER_PORT);
51 serverSockaddr.sin_addr.s_addr=htonl(INADDR_ANY);
52 bzero(&(serverSockaddr.sin_zero),8);
53
54 setsockopt(sockfd,SOL_SOCKET,SO_REUSEADDR,&on,sizeof(on));
55
56 /*bind socket*/
57 if(bind(sockfd,(struct sockaddr *)&serverSockaddr,sizeof(struct sockaddr))==-1)
58 {
59 perror("fail to bind");
60 exit(1);
61 }
62 printf("Success to bind the socket...
");
63
64 /*listen on the socket*/
65 if(listen(sockfd,BACKLOG)==-1)
66 {
67 perror("fail to listen");
68 exit(1);
69 }
70
71 /*accept a client's request*/ // sinSize ,
72 if((clientfd=accept(sockfd,(struct sockaddr *)&clientSockaddr, &sinSize))==-1)
73 {
74 perror("fail to accept");
75 exit(1);
76 }
77 printf("Success to accpet a connection request...
");
78 printf(" %s join in!
",inet_ntoa(clientSockaddr.sin_addr));
79
80 if((pid=fork())<0)
81 {
82 perror("fork error
");
83 }
84 else if(pid>0)/*child*/
85 {
86 /*send datas to client*/
87 while(1)
88 {
89 fgets(sendBuf,MAX_DATA_SIZE,stdin);
90 if((sendSize=send(clientfd,sendBuf,strlen(sendBuf),0))!=strlen(sendBuf))
91 {
92 perror("fail to send datas");
93 exit(1);
94 }
95 printf("Success to send datas
");
96 memset(sendBuf,0,MAX_DATA_SIZE);
97 }
98 }
99 else
100 {
101 while(1)
102 {
103 /*receive datas from client*/
104 if((recvSize=recv(clientfd,recvBuf,MAX_DATA_SIZE,0))==-1)
105 {
106 perror("fail to receive datas");
107 exit(1);
108 }
109 printf("Client:%s
",recvBuf);
110 memset(recvBuf,0,MAX_DATA_SIZE);
111 }
112
113 }
114
115 return 0;
116 }
この記事のアドレス: http://www.cnblogs.com/wunaozai/p/3870194.html