-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathmainepoller.cpp
87 lines (70 loc) · 2.21 KB
/
mainepoller.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
#include "mainepoller.h"
#include<iostream>
void mainepoller::addevent(int fd,int eve)
{
ev.data.fd = fd;
ev.events = eve;
if(epoll_ctl(epollfd_,EPOLL_CTL_ADD,fd,&ev) < 0)
{
//fixme
}
events_.reserve(16);
}
//主线程等待新连接
void mainepoller::pool()
{
while(1)
{
int nfds = epoll_wait(epollfd_,&(*(events_.begin())),events_.capacity(),10000);
if(nfds < 0)
{
//fixme;
std::cout << "epollerror" << std::endl;
}
else if(nfds == 0)
{
//没有新连接到来什么都不做
}
else
{
for(int i = 0;i < nfds;++i)
{
makenewconection(events_[i].data.fd);
}
if(nfds == events_.size())
{
events_.resize(events_.size()*2);
}
}
events_.clear();
}
}
//当新的连接三次握手完毕后,将新的连接的文件描述符放入子线程
//优雅关闭处理文件描述符不足
void mainepoller::makenewconection(int fd)
{
int newfd = accept4(fd,(sockaddr*)&client_addr,&client_len,SOCK_NONBLOCK|SOCK_CLOEXEC);
// std::cout << "newfd = " << newfd <<std::endl;
if(newfd < 0)
{
if(errno == EMFILE || errno == ENFILE)
{
std::cout << "run out of fd" << std::endl;
close(backupfd);
newfd = accept4(fd,(sockaddr*)&client_addr,&client_len,SOCK_NONBLOCK|SOCK_CLOEXEC);
close(newfd);
backupfd = open("/dev/null",O_RDONLY);
}
}
else
{
inet_ntop(AF_INET,&client_addr,clinet_addr_string,100);
// printf("conniction ready ip = %s port = %d \n",clinet_addr_string,ntohs(client_addr.sin_port));
subepoller* subepoller_ = pool_.getnextpoller();
if(subepoller_ == nullptr)
std::cerr << "subepoller = nullptr" << std::endl;
// std::cout << "already get poller" << std::endl;
subepoller_->addevent(newfd,EPOLLIN);
// close(newfd);
}
}