39 #include "blocxx/BLOCXX_config.h"
47 #if defined(BLOCXX_WIN32)
55 #ifdef BLOCXX_HAVE_SYS_EPOLL_H
56 #include <sys/epoll.h>
58 #if defined (BLOCXX_HAVE_SYS_POLL_H)
61 #if defined (BLOCXX_HAVE_SYS_SELECT_H)
62 #include <sys/select.h>
66 #ifdef BLOCXX_HAVE_SYS_TIME_H
70 #include <sys/types.h>
72 #ifdef BLOCXX_HAVE_UNISTD_H
79 namespace BLOCXX_NAMESPACE
87 const float LOOP_TIMEOUT = 10.0;
97 #if defined(BLOCXX_WIN32)
103 size_t hcount =
static_cast<DWORD
>(selarray.size());
106 size_t handleidx = 0;
107 for (
size_t i = 0;
i < selarray.size();
i++, handleidx++)
109 if(selarray[
i].s.isSocket && selarray[
i].s.networkevents)
111 ::WSAEventSelect(selarray[i].s.sockfd,
112 selarray[i].s.event, selarray[i].s.networkevents);
115 hdls[handleidx] = selarray[
i].s.event;
118 TimeoutTimer timer(timeout);
120 DWORD cc = ::WaitForMultipleObjects(hcount, hdls.get(), FALSE, timer.asDWORDMs());
122 assert(cc != WAIT_ABANDONED);
133 rc = cc - WAIT_OBJECT_0;
137 if(selarray[rc].s.isSocket)
139 if(selarray[rc].s.networkevents
140 && selarray[rc].s.doreset ==
false)
142 ::WSAEventSelect(selarray[rc].s.sockfd,
143 selarray[rc].s.event, selarray[rc].s.networkevents);
148 ::WSAEventSelect(selarray[rc].s.sockfd,
149 selarray[rc].s.event, 0);
151 ::ioctlsocket(selarray[rc].s.sockfd, FIONBIO, &ioctlarg);
160 int availableCount = 0;
161 for (
size_t i = 0;
i < selarray.size();
i++)
163 if( WaitForSingleObject(selarray[
i].s.event, 0) == WAIT_OBJECT_0 )
165 if( selarray[i].waitForRead )
166 selarray[
i].readAvailable =
true;
167 if( selarray[i].waitForWrite )
168 selarray[
i].writeAvailable =
true;
173 selarray[
i].readAvailable =
false;
174 selarray[
i].writeAvailable =
false;
177 return availableCount;
188 #ifdef BLOCXX_HAVE_SYS_EPOLL_H
202 UInt32
const read_events = EPOLLIN | EPOLLPRI | EPOLLERR | EPOLLHUP;
203 UInt32
const write_events = EPOLLOUT | EPOLLERR | EPOLLHUP;
204 for (
size_t i = 0; i < selarray.
size(); i++)
207 selarray[
i].readAvailable =
false;
208 selarray[
i].writeAvailable =
false;
209 selarray[
i].wasError =
false;
210 events[
i].data = epoll_data_t();
211 events[
i].data.u32 =
i;
212 events[
i].events = 0;
213 if(selarray[i].waitForRead)
215 events[
i].events |= read_events;
217 if(selarray[i].waitForWrite)
219 events[
i].events |= write_events;
222 if(epoll_ctl(epfd.
get(), EPOLL_CTL_ADD, selarray[
i].s, &events[
i]) != 0)
236 const float maxWaitSec = LOOP_TIMEOUT;
237 ecc = epoll_wait(epfd.
get(), events.get(), selarray.
size(), timer.
asIntMs(maxWaitSec));
239 if (ecc < 0 && errno == EINTR)
246 }
while ((ecc == 0) && !timer.
expired());
258 for(
int i = 0; i < ecc; i++)
276 #if defined (BLOCXX_HAVE_SYS_POLL_H)
288 for (
size_t i = 0; i < selarray.
size(); i++)
291 selarray[
i].readAvailable =
false;
292 selarray[
i].writeAvailable =
false;
293 selarray[
i].wasError =
false;
295 pfds[
i].fd = selarray[
i].s;
296 pfds[
i].events = selarray[
i].waitForRead ? (POLLIN | POLLPRI) : 0;
297 if(selarray[i].waitForWrite)
298 pfds[
i].events |= POLLOUT;
302 const float maxWaitSec = LOOP_TIMEOUT;
303 rc = ::poll(pfds.get(), selarray.
size(), timer.asIntMs(maxWaitSec));
305 if (rc < 0 && errno == EINTR)
310 #ifdef BLOCXX_NETWARE
320 }
while ((rc == 0) && !timer.expired());
331 for (
size_t i = 0; i < selarray.
size(); i++)
333 if (pfds[i].revents & (POLLERR | POLLNVAL))
335 selarray[
i].wasError =
true;
338 if(selarray[i].waitForRead)
340 selarray[
i].readAvailable = (pfds[
i].revents &
341 (POLLIN | POLLPRI | POLLHUP));
344 if(selarray[i].waitForWrite)
346 selarray[
i].writeAvailable = (pfds[
i].revents &
347 (POLLOUT | POLLHUP));
361 #if defined (BLOCXX_HAVE_SYS_SELECT_H)
376 for (
size_t i = 0; i < selarray.
size(); ++
i)
378 int fd = selarray[
i].s;
384 if (fd < 0 || fd >= FD_SETSIZE)
389 if (selarray[i].waitForRead)
393 if (selarray[i].waitForWrite)
401 const float maxWaitSec = LOOP_TIMEOUT;
402 rc =
::select(maxfd+1, &ifds, &ofds, NULL, timer.asTimeval(tv, maxWaitSec));
404 if (rc < 0 && errno == EINTR)
409 #ifdef BLOCXX_NETWARE
419 }
while ((rc == 0) && !timer.
expired());
430 int availableCount = 0;
432 for (
size_t i = 0; i < selarray.
size(); i++)
434 selarray[
i].wasError =
false;
436 if (FD_ISSET(selarray[i].s, &ifds))
438 selarray[
i].readAvailable =
true;
443 selarray[
i].readAvailable =
false;
446 if (FD_ISSET(selarray[i].s, &ofds))
448 selarray[
i].writeAvailable =
true;
453 selarray[
i].writeAvailable =
false;
456 availableCount += cval;
460 return availableCount;
487 #endif // #else BLOCXX_WIN32
501 for (
size_t i = 0; i < selarray.
size(); ++
i)
514 for (
size_t i = 0; i < soa.
size(); ++
i)
516 if (soa[i].readAvailable)