linux网络通信并发程序设计(一)

在Linux网络编程中,一般建立在两端之间,服务器端和客户端。客户端是面向用户的应用,而服务器端要处理客户端所提出的请求。通常一个服务器要面向多个客户端,保证对每个客户端都能高效的处理,这时候需要并发操作。实现并发控制的方法有两个,一个是并发服务器,另一个是多路复用I/O,现在就给大家介绍一下这两种方法。

方法一:并发服务器

这个方法可以通过进程(线程)来实现,主要根据子进程(子线程)之间并行运行的特点。将对客户端请求的处理工作,交于子进程(子线程)来处理,达到一个服务器同时处理多个客户端的效果。

1、这是通过(子)进程来实现的。

------------------------- server.c -------------------------
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 


int main(){
	int sockfd, newfd, r;
  	struct sockaddr_in myaddr;
  	struct sockaddr_in fromaddr;
  	socklen_t len = 16;
  	char buf[100] = {0};
  	pid_t pid;
  	sockfd = socket(AF_INET, SOCK_STREAM, 0);
  	
	myaddr.sin_family = AF_INET;
  	myaddr.sin_port = htons(5666);
  	myaddr.sin_addr.s_addr = inet_addr("192.168.80.128");

  	r = bind(sockfd, (struct sockaddr *)&myaddr, sizeof(myaddr));
  	if(listen(sockfd, 10) < 0){
    	perror("listen");
    	return -1;
  	}
  
  	while(1){
    	printf("the server is listenning..................\n");
    	newfd = accept(sockfd, &fromaddr, &len);
    	
    	if(newfd > 0){
    		printf("accept done! newfd = %d\n",newfd);
		}
    	pid = fork();
    	if(pid == 0){
      		while(1){
				r = recv(newfd, buf, 100, 0);
				if(r < 0){
	  				perror("recv")
      	  			break;
				}	
				printf("%d: %s\n", newfd, buf);
				bzero(buf, strlen(buf));
      		}
      		close(newfd);
      		bzero(&fromaddr, strlen(fromaddr));
			exit(0);
    	}else if(pid < 0)
      		exit(0);
  	}
}
2、这是通过线程实现的
------------------------- server.c -------------------------
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include void *fun(void *p){int fd = *((int *)p);char buf[100] = {0};int r;printf("pthread fd = %d start\n", fd);while(1){r = recv(fd, buf, 100, 0);if(r <= 0){printf("客户端已退出 %d\n", fd);break;}printf("%d: %s\n", fd, buf);bzero(buf, strlen(buf));}close(fd);}int main(){int sockfd, newfd, r;struct sockaddr_in myaddr;struct sockaddr fromaddr;socklen_t len=16;char buf[100] = {0};pthread_t tid;sockfd = socket(AF_INET, SOCK_STREAM, 0);myaddr.sin_family = AF_INET;myaddr.sin_port = htons(5666);myaddr.sin_addr.s_addr = inet_addr(192.168.80.128);r = bind(sockfd, (struct sockaddr *)&myaddr, sizeof(myaddr));if(listen(sockfd, 10) < 0){perror("listen");return -1;}while(1){newfd = accept(sockfd, &fromaddr, &len);printf("newfd = %d \n", newfd);pthread_creat(&tid, NULL, fun, &newfd);}close(sockfd);}
 
   
注意:由于pthread并非Linux系统的默认库,而是POSIX线程库。在Linux中将其作为一个库来使用,因此加上 -lpthread(或-pthread)以显式链接该库。
#gcc server_xian.c -o server_xian -pthread

3、客户端代码相同,如下:
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
int main(){

  int sockfd,r;
  char buf[100] = {0};
  struct sockaddr_in toaddr;
  sockfd = socket(AF_INET, SOCK_STREAM, 0); 
  printf("sockfd = %d\n", sockfd);

  toaddr.sin_family = AF_INET; 
  toaddr.sin_port = htons(5666); 
  toaddr.sin_addr.s_addr = inet_addr("192.168.80.128"); 

  r = connect(sockfd, (struct sockaddr *)&toaddr, sizeof(toaddr));
  if(r == -1){ perror("connect "); return -1; }
  printf("connect OK\n"); 
  while(1){ 
    scanf("%s", buf);
    send(sockfd, buf, strlen(buf), 0);
  }
  close(sockfd);
}


你可能感兴趣的:(linux基础)