2222#include "stdlib/acl_iostuff.h"
2323#include "../../init/init.h"
2424
25- #if defined(LINUX2 ) && !defined(MINGW )
25+ #if defined(LINUX2 ) && !defined(MINGW ) && defined( USE_EPOLL )
2626
2727#include "init/acl_init.h"
2828#include "thread/acl_pthread.h"
2929#include <sys/epoll.h>
3030
31- static int * main_epoll_read_fd = NULL ;
31+ typedef struct EPOLL_CTX
32+ {
33+ acl_pthread_t tid ;
34+ int epfd ;
35+ } EPOLL_CTX ;
36+
37+ static EPOLL_CTX * main_epoll_ctx = NULL ;
3238
3339static void main_epoll_end (void )
3440{
35- if (main_epoll_read_fd != NULL ) {
36- close (* main_epoll_read_fd );
37- acl_myfree (main_epoll_read_fd );
41+ const char * myname = "main_epoll_end" ;
42+
43+ if (main_epoll_ctx != NULL ) {
44+ acl_msg_info ("%s(%d), %s: close epoll_fd: %d, tid: %lu, %lu" ,
45+ __FILE__ , __LINE__ , myname , main_epoll_ctx -> epfd ,
46+ main_epoll_ctx -> tid , acl_pthread_self ());
47+
48+ close (main_epoll_ctx -> epfd );
49+ acl_myfree (main_epoll_ctx );
50+ main_epoll_ctx = NULL ;
3851 }
3952}
4053
4154static acl_pthread_key_t epoll_key ;
4255static acl_pthread_once_t epoll_once = ACL_PTHREAD_ONCE_INIT ;
4356
44- static void thread_epoll_end (void * buf )
57+ static void thread_epoll_end (void * ctx )
4558{
46- int * epoll_fd = (int * ) buf ;
59+ const char * myname = "thread_epoll_end" ;
60+ EPOLL_CTX * epoll_ctx = (EPOLL_CTX * ) ctx ;
4761
48- close (* epoll_fd );
49- acl_myfree (epoll_fd );
62+ acl_msg_info ("%s(%d), %s: close epoll_fd: %d, tid: %lu, %lu" ,
63+ __FILE__ , __LINE__ , myname , epoll_ctx -> epfd ,
64+ epoll_ctx -> tid , acl_pthread_self ());
65+
66+ close (epoll_ctx -> epfd );
67+ acl_myfree (epoll_ctx );
5068}
5169
52- static void thread_epoll_init (void )
70+ static void thread_epoll_once (void )
5371{
5472 acl_assert (acl_pthread_key_create (& epoll_key , thread_epoll_end ) == 0 );
5573}
5674
75+ static EPOLL_CTX * thread_epoll_init (void )
76+ {
77+ const char * myname = "thread_epoll_init" ;
78+ EPOLL_CTX * epoll_ctx = (EPOLL_CTX * ) acl_mymalloc (sizeof (EPOLL_CTX ));
79+
80+ acl_assert (acl_pthread_setspecific (epoll_key , epoll_ctx ) == 0 );
81+
82+ epoll_ctx -> tid = acl_pthread_self ();
83+ epoll_ctx -> epfd = epoll_create (1 );
84+
85+ if (acl_pthread_self () == acl_main_thread_self ()) {
86+ main_epoll_ctx = epoll_ctx ;
87+ atexit (main_epoll_end );
88+ acl_msg_info ("%s(%d): %s, create epoll_fd: %d, tid: %lu, %lu" ,
89+ __FILE__ , __LINE__ , myname , epoll_ctx -> epfd ,
90+ epoll_ctx -> tid , acl_pthread_self ());
91+ } else {
92+ acl_msg_info ("%s(%d): %s, create epoll_fd: %d, tid: %lu, %lu" ,
93+ __FILE__ , __LINE__ , myname , epoll_ctx -> epfd ,
94+ epoll_ctx -> tid , acl_pthread_self ());
95+ }
96+
97+ return epoll_ctx ;
98+ }
99+
57100int acl_read_wait (ACL_SOCKET fd , int timeout )
58101{
59102 const char * myname = "acl_read_wait" ;
60- int op = EPOLL_CTL_ADD , delay = timeout * 1000 , * epoll_fd , ret ;
103+ int delay = timeout * 1000 , ret ;
104+ EPOLL_CTX * epoll_ctx ;
61105 struct epoll_event ee , events [1 ];
62106
63- acl_assert (acl_pthread_once (& epoll_once , thread_epoll_init ) == 0 );
64- epoll_fd = (int * ) acl_pthread_getspecific (epoll_key );
65- if (epoll_fd == NULL ) {
66- epoll_fd = (int * ) acl_mymalloc (sizeof (int ));
67- acl_assert (acl_pthread_setspecific (epoll_key , epoll_fd ) == 0 );
68- if ((unsigned long ) acl_pthread_self ()
69- == acl_main_thread_self ())
70- {
71- main_epoll_read_fd = epoll_fd ;
72- atexit (main_epoll_end );
73- }
74-
75- * epoll_fd = epoll_create (1 );
76- }
107+ acl_assert (acl_pthread_once (& epoll_once , thread_epoll_once ) == 0 );
108+ epoll_ctx = (EPOLL_CTX * ) acl_pthread_getspecific (epoll_key );
109+ if (epoll_ctx == NULL )
110+ epoll_ctx = thread_epoll_init ();
77111
78112 ee .events = EPOLLIN | EPOLLHUP | EPOLLERR ;
79113 ee .data .u64 = 0 ;
80114 ee .data .fd = fd ;
81- if (epoll_ctl (* epoll_fd , op , fd , & ee ) == -1
115+ if (epoll_ctl (epoll_ctx -> epfd , EPOLL_CTL_ADD , fd , & ee ) == -1
82116 && acl_last_error () != EEXIST )
83117 {
84- acl_msg_error ("%s(%d): epoll_ctl error: %s, fd: %d" ,
85- myname , __LINE__ , acl_last_serror (), fd );
118+ acl_msg_error ("%s(%d): epoll_ctl error: %s, fd: %d, epfd: %d,"
119+ " tid: %lu, %lu" , myname , __LINE__ , acl_last_serror (),
120+ fd , epoll_ctx -> epfd , epoll_ctx -> tid ,
121+ acl_pthread_self ());
86122 return -1 ;
87123 }
88124
89125 for (;;) {
90- ret = epoll_wait (* epoll_fd , events , 1 , delay );
126+ ret = epoll_wait (epoll_ctx -> epfd , events , 1 , delay );
91127
92128 if (ret == -1 ) {
93129 if (acl_last_error () == ACL_EINTR ) {
94130 acl_msg_warn (">>>>catch EINTR, try again<<<" );
95131 continue ;
96132 }
97133
98- acl_msg_error ("%s(%d): epoll_wait error: %s, fd: %d" ,
99- myname , __LINE__ , acl_last_serror (), fd );
134+ acl_msg_error ("%s(%d): epoll_wait error: %s, fd: %d,"
135+ " epfd: %d, tid: %lu, %lu" , myname , __LINE__ ,
136+ acl_last_serror (), fd , epoll_ctx -> epfd ,
137+ epoll_ctx -> tid , acl_pthread_self ());
100138 ret = -1 ;
101139 break ;
102140 } else if (ret == 0 ) {
@@ -118,9 +156,11 @@ int acl_read_wait(ACL_SOCKET fd, int timeout)
118156 ee .events = 0 ;
119157 ee .data .u64 = 0 ;
120158 ee .data .fd = fd ;
121- if (epoll_ctl (* epoll_fd , EPOLL_CTL_DEL , fd , & ee ) == -1 ) {
122- acl_msg_error ("%s(%d): epoll_ctl error: %s, fd: %d" ,
123- myname , __LINE__ , acl_last_serror (), fd );
159+ if (epoll_ctl (epoll_ctx -> epfd , EPOLL_CTL_DEL , fd , & ee ) == -1 ) {
160+ acl_msg_error ("%s(%d): epoll_ctl error: %s, fd: %d, epfd: %d,"
161+ " tid: %lu, %lu" , myname , __LINE__ , acl_last_serror (),
162+ fd , epoll_ctx -> epfd , epoll_ctx -> tid ,
163+ acl_pthread_self ());
124164 return -1 ;
125165 }
126166
0 commit comments