Compare commits
6 Commits
master
...
ahc_fix_se
Author | SHA1 | Date | |
---|---|---|---|
|
6510cdb4db | ||
|
84f4376c6c | ||
|
18db423b1d | ||
|
1e5e8d1bc2 | ||
|
c62cdb51b9 | ||
|
f62f1c0bda |
135
src/core.c
135
src/core.c
@ -49,6 +49,10 @@
|
|||||||
#include <sys/socket.h>
|
#include <sys/socket.h>
|
||||||
#include <sys/time.h>
|
#include <sys/time.h>
|
||||||
#ifdef HAVE_SYS_SELECT_H
|
#ifdef HAVE_SYS_SELECT_H
|
||||||
|
|
||||||
|
// You may need to override this!
|
||||||
|
// #define FD_SETSIZE 2048
|
||||||
|
|
||||||
#include <sys/select.h>
|
#include <sys/select.h>
|
||||||
#endif
|
#endif
|
||||||
#ifdef HAVE_KEVENT
|
#ifdef HAVE_KEVENT
|
||||||
@ -1076,6 +1080,15 @@ core_connect(Conn * s)
|
|||||||
goto failure;
|
goto failure;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (sd > FD_SETSIZE) {
|
||||||
|
fprintf(stderr,
|
||||||
|
"%s.core_connect.socket: sd > FD_SETSIZE (%d)\n",
|
||||||
|
prog_name,
|
||||||
|
FD_SETSIZE);
|
||||||
|
close(sd);
|
||||||
|
goto failure;
|
||||||
|
}
|
||||||
|
|
||||||
if (fcntl(sd, F_SETFL, O_NONBLOCK) < 0) {
|
if (fcntl(sd, F_SETFL, O_NONBLOCK) < 0) {
|
||||||
fprintf(stderr, "%s.core_connect.fcntl: %s\n",
|
fprintf(stderr, "%s.core_connect.fcntl: %s\n",
|
||||||
prog_name, strerror(errno));
|
prog_name, strerror(errno));
|
||||||
@ -1445,14 +1458,57 @@ core_loop(void)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
|
|
||||||
|
static void
|
||||||
|
check_conn(int sd, int is_readable, int is_writable)
|
||||||
|
{
|
||||||
|
Conn *conn;
|
||||||
|
Any_Type arg;
|
||||||
|
|
||||||
|
/* Don't bother doing anything if we're not ready */
|
||||||
|
if ((is_readable || is_writable) == 0) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* only handle sockets that
|
||||||
|
* haven't timed out yet
|
||||||
|
*/
|
||||||
|
conn = sd_to_conn[sd];
|
||||||
|
conn_inc_ref(conn);
|
||||||
|
|
||||||
|
if (conn->watchdog) {
|
||||||
|
timer_cancel(conn->watchdog);
|
||||||
|
conn->watchdog = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (conn->state == S_CONNECTING) {
|
||||||
|
#ifdef HAVE_SSL
|
||||||
|
if (param.use_ssl)
|
||||||
|
core_ssl_connect(conn);
|
||||||
|
else
|
||||||
|
#endif
|
||||||
|
if (is_writable) {
|
||||||
|
clear_active(conn, WRITE);
|
||||||
|
conn->state = S_CONNECTED;
|
||||||
|
arg.l = 0;
|
||||||
|
event_signal(EV_CONN_CONNECTED, (Object*)conn, arg);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (is_writable && conn->sendq)
|
||||||
|
do_send(conn);
|
||||||
|
if (is_readable && conn->recvq)
|
||||||
|
do_recv(conn);
|
||||||
|
}
|
||||||
|
conn_dec_ref(conn);
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
core_loop(void)
|
core_loop(void)
|
||||||
{
|
{
|
||||||
int is_readable, is_writable, n, sd, bit, min_i, max_i, i = 0;
|
int is_readable, is_writable, n, sd;
|
||||||
fd_set readable, writable;
|
fd_set readable, writable;
|
||||||
fd_mask mask;
|
fd_mask mask;
|
||||||
Any_Type arg;
|
|
||||||
Conn *conn;
|
|
||||||
|
|
||||||
while (running) {
|
while (running) {
|
||||||
struct timeval tv = select_timeout;
|
struct timeval tv = select_timeout;
|
||||||
@ -1461,8 +1517,6 @@ core_loop(void)
|
|||||||
|
|
||||||
readable = rdfds;
|
readable = rdfds;
|
||||||
writable = wrfds;
|
writable = wrfds;
|
||||||
min_i = min_sd / NFDBITS;
|
|
||||||
max_i = max_sd / NFDBITS;
|
|
||||||
|
|
||||||
SYSCALL(SELECT, n = select(max_sd + 1, &readable, &writable, 0, &tv));
|
SYSCALL(SELECT, n = select(max_sd + 1, &readable, &writable, 0, &tv));
|
||||||
|
|
||||||
@ -1476,68 +1530,19 @@ core_loop(void)
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
while (n > 0) {
|
/* XXX totally suboptimal loop, but less potentially problematic */
|
||||||
/*
|
|
||||||
* find the index of the fdmask that has something
|
|
||||||
* going on:
|
|
||||||
*/
|
|
||||||
do {
|
|
||||||
++i;
|
|
||||||
if (i > max_i)
|
|
||||||
i = min_i;
|
|
||||||
|
|
||||||
assert(i <= max_i);
|
for (sd = 0; sd <= max_sd; sd++) {
|
||||||
mask = readable.fds_bits[i] | writable.fds_bits[i];
|
is_readable = (FD_ISSET(sd, &readable) && FD_ISSET(sd, &rdfds));
|
||||||
} while (!mask);
|
is_writable = (FD_ISSET(sd, &writable) && FD_ISSET(sd, &wrfds));
|
||||||
bit = 0;
|
if (is_readable || is_writable)
|
||||||
sd = i * NFDBITS + bit;
|
check_conn(sd, is_readable, is_writable);
|
||||||
do {
|
|
||||||
if (mask & 1) {
|
|
||||||
--n;
|
|
||||||
is_readable = (FD_ISSET(sd, &readable) && FD_ISSET(sd, &rdfds));
|
|
||||||
is_writable = (FD_ISSET(sd, &writable) && FD_ISSET(sd, &wrfds));
|
|
||||||
|
|
||||||
if (is_readable || is_writable) {
|
|
||||||
/*
|
|
||||||
* only handle sockets that
|
|
||||||
* haven't timed out yet
|
|
||||||
*/
|
|
||||||
conn = sd_to_conn[sd];
|
|
||||||
conn_inc_ref(conn);
|
|
||||||
|
|
||||||
if (conn->watchdog) {
|
/* XXX TODO: totally can bail out if we've seen 'n' FDs */
|
||||||
timer_cancel(conn->watchdog);
|
}
|
||||||
conn->watchdog = 0;
|
|
||||||
}
|
/* Do timer tick at the end of the connection check */
|
||||||
if (conn->state == S_CONNECTING) {
|
timer_tick();
|
||||||
#ifdef HAVE_SSL
|
|
||||||
if (param.use_ssl)
|
|
||||||
core_ssl_connect(conn);
|
|
||||||
else
|
|
||||||
#endif
|
|
||||||
if (is_writable) {
|
|
||||||
clear_active(conn, WRITE);
|
|
||||||
conn->state = S_CONNECTED;
|
|
||||||
arg.l = 0;
|
|
||||||
event_signal(EV_CONN_CONNECTED, (Object*)conn, arg);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (is_writable && conn->sendq)
|
|
||||||
do_send(conn);
|
|
||||||
if (is_readable && conn->recvq)
|
|
||||||
do_recv(conn);
|
|
||||||
}
|
|
||||||
|
|
||||||
conn_dec_ref(conn);
|
|
||||||
|
|
||||||
if (n > 0)
|
|
||||||
timer_tick();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
mask = ((u_long) mask) >> 1;
|
|
||||||
++sd;
|
|
||||||
} while (mask);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
Loading…
Reference in New Issue
Block a user