Linux网络编程的发展

Linux平台基于C++ socket实现TCP 网络通信

tcp的超时时间设置​​​​​​​ 

D:\011-Applying\Linux网络编程\源码-写博客

原始玩具

#include <unistd.h>
#include <sys/socket.h>
#include <stdlib.h>
#include <stdio.h>
#include <arpa/inet.h>
#include <ctype.h>
#include <strings.h>//bzero'h
#define SERV_IP "127.0.0.1"
#define SERV_PORT 6666
#include "wrap.h"
int main()
{
	  int sfd,cfd;
      struct sockaddr_in serv_addr,clie_addr;
      socklen_t clie_addr_len,client_IP_len;
      char buf[BUFSIZ],cli_IP[BUFSIZ];
      int i,n;
      sfd = Socket(AF_INET,SOCK_STREAM,0);
      bzero(&serv_addr,sizeof(serv_addr));
      serv_addr.sin_family = AF_INET;
      serv_addr.sin_port = htons(SERV_PORT);
      serv_addr.sin_addr.s_addr = htonl(INADDR_ANY);  
      Bind(sfd,(struct sockaddr*)&serv_addr,sizeof(serv_addr));
      Listen(sfd,128);
      clie_addr_len = sizeof(clie_addr);
      cfd = Accept(sfd,(struct sockaddr*)&clie_addr,&clie_addr_len);
	  while(1)
     {
         n = Read(cfd,buf,sizeof(buf));
         for(i= 0;i<n;i++)
	     buf[i] = toupper(buf[i]);
	     Write(cfd,buf,n);
     }   
     close(sfd);
     close(cfd);
     return 0;
}

epoll玩具

#include <stdio.h>
#include <sys/socket.h>
#include <sys/epoll.h>
#include <arpa/inet.h>
#include <fcntl.h>
#include <unistd.h>
#include <errno.h>
#include <stdlib.h>
#include <ctype.h>
#include <string.h>//bzero'h
#include <time.h>
#include "wrap.h"
#include <sys/wait.h>

#define SERV_IP "127.0.0.1"
#define SERV_PORT 6666
#define MAXLINE 8192
#define OPEN_MAX 5000


int main()
{
	  
	  int i,listenfd,connfd,sockfd;
	  struct sockaddr_in serv_addr,clie_addr;
	  int n,num = 0;
	  ssize_t nready,efd,res;
	  char buf[MAXLINE],str[INET_ADDRSTRLEN];
	  socklen_t clilen;
	  struct sockaddr_in cliaddr,servaddr;
	  struct epoll_event tep,ep[OPEN_MAX];// tep:epoll_ctl 参数,ep[]:epoll_wait 参数
	  
	  listenfd = Socket(AF_INET,SOCK_STREAM,0);
	  int opt = 1;
	  setsockopt(listenfd,SOL_SOCKET,SO_REUSEADDR,&opt,sizeof(opt)); //端口复用
	  bzero(&serv_addr,sizeof(serv_addr));
	  

      serv_addr.sin_family = AF_INET;
      serv_addr.sin_port = htons(SERV_PORT);
      serv_addr.sin_addr.s_addr = htonl(INADDR_ANY);//也可以写成inet_ntop(AF_INET,'127.0.0.1',&serv_addr.sin_addr.s_addr);
        
	  
	  
      Bind(listenfd,(struct sockaddr*)&serv_addr,sizeof(serv_addr));
      Listen(listenfd,128);//同时与服务器发起三次握手的数量上限,最大是128,超过128也没有用,操作系统限定
      printf("wait for client connect...\n");
	  efd = epoll_create(10);     //创建epoll模型,efd指向红黑树根节点
	  if(efd == -1)
		  perr_exit("epoll_create error");
	  tep.events = EPOLLIN;
	  tep.data.fd = listenfd; // 指定lfd的监听事件是读事件
	  printf("成功创建epoll.\n");
	  res = epoll_ctl(efd,EPOLL_CTL_ADD,listenfd,&tep); //将lfd及对应的结构体设置到树上,efd可以找到该树
	  
	  
	  for(;;)
	  {
		  /*epoll为阻塞监听事件,ep为struct epoo_event类型数组,OPEN_MAX为数组容量,-1表示永久阻塞*/
		 printf("epoll_wait.\n");
		 nready = epoll_wait(efd,ep,OPEN_MAX,-1);
		 printf("nready is %d.\n",nready);
		 if(nready == -1)
		     perr_exit("epoll_wait error");
		 
		 for(i = 0;i<nready;i++)
		 {
			 if(!(ep[i].events & EPOLLIN))
				 continue;//如果不是读事件,继续循环
			 if(ep[i].data.fd == listenfd)//判断满足事件的fd是不是lfd(listen fd)
			 {
				 clilen = sizeof(cliaddr); 
				 connfd = Accept(listenfd,(struct sockaddr*)&cliaddr,&clilen);//接受连接
				 printf("client-IP:%s,client port:%d.\n",inet_ntop(AF_INET,&clie_addr.sin_addr.s_addr,str,sizeof(str)),ntohs(clie_addr.sin_port));
                 printf("cfd is %d,client is %d.\n",connfd,++num);
				 tep.events = EPOLLIN;
				 tep.data.fd = connfd;
				 res = epoll_ctl(efd,EPOLL_CTL_ADD,connfd,&tep);
				 if(res == -1)
			          perr_exit("epoll_ctl error");
			 }
			 else //不是listenfd
			 {
				 sockfd = ep[i].data.fd;
				 n = Read(sockfd,buf,MAXLINE);
				 if(n == 0)//读到0,说明客户端关闭连接,将该文件描述符从红黑树摘除
				 {
					res = epoll_ctl(efd,EPOLL_CTL_DEL,connfd,NULL);
					if(res == -1)
				         perr_exit("epoll_ctl error");
					Close(sockfd);
					printf("client [%d] closed connection.\n",sockfd);
				 }
				 else if(n<0) // 出错
				 {
					 perror("read n < 0 error:");
					 res = epoll_ctl(efd,EPOLL_CTL_DEL,connfd,NULL);
					 close(sockfd);
				 }
				 else //实际读到了字节数
				 {
					 for(i = 0;i<n;i++)
						 buf[i] = toupper(buf[i]);//转大写,写回给客户端
					 Write(STDOUT_FILENO,buf,n);
					 Writen(sockfd,buf,n);
				 }
			 }
			 
		 }
		  
	  }
	  
	  
	 Close(listenfd);
	 Close(efd);
     return 0;
}




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值