Merge branch 'defer-accept' into devel
This commit is contained in:
commit
61fe2694df
|
@ -136,6 +136,13 @@ class "server" {
|
||||||
};
|
};
|
||||||
|
|
||||||
listen {
|
listen {
|
||||||
|
/* defer_accept: wait for clients to send IRC handshake data before
|
||||||
|
* accepting them. if you intend to use software which depends on the
|
||||||
|
* server replying first, such as BOPM, you should disable this feature.
|
||||||
|
* otherwise, you probably want to leave it on.
|
||||||
|
*/
|
||||||
|
defer_accept = yes;
|
||||||
|
|
||||||
/* If you want to listen on a specific IP only, specify host.
|
/* If you want to listen on a specific IP only, specify host.
|
||||||
* host definitions apply only to the following port line.
|
* host definitions apply only to the following port line.
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -304,6 +304,13 @@ class "server" {
|
||||||
|
|
||||||
/* listen {}: contain information about the ports ircd listens on (OLD P:) */
|
/* listen {}: contain information about the ports ircd listens on (OLD P:) */
|
||||||
listen {
|
listen {
|
||||||
|
/* defer_accept: wait for clients to send IRC handshake data before
|
||||||
|
* accepting them. if you intend to use software which depends on the
|
||||||
|
* server replying first, such as BOPM, you should disable this feature.
|
||||||
|
* otherwise, you probably want to leave it on.
|
||||||
|
*/
|
||||||
|
defer_accept = yes;
|
||||||
|
|
||||||
/* port: the specific port to listen on. if no host is specified
|
/* port: the specific port to listen on. if no host is specified
|
||||||
* before, it will listen on all available IPs.
|
* before, it will listen on all available IPs.
|
||||||
*
|
*
|
||||||
|
|
|
@ -38,12 +38,13 @@ struct Listener
|
||||||
int ref_count; /* number of connection references */
|
int ref_count; /* number of connection references */
|
||||||
int active; /* current state of listener */
|
int active; /* current state of listener */
|
||||||
int ssl; /* ssl listener */
|
int ssl; /* ssl listener */
|
||||||
|
int defer_accept; /* use TCP_DEFER_ACCEPT */
|
||||||
struct rb_sockaddr_storage addr;
|
struct rb_sockaddr_storage addr;
|
||||||
struct DNSQuery *dns_query;
|
struct DNSQuery *dns_query;
|
||||||
char vhost[HOSTLEN + 1]; /* virtual name of listener */
|
char vhost[HOSTLEN + 1]; /* virtual name of listener */
|
||||||
};
|
};
|
||||||
|
|
||||||
extern void add_listener(int port, const char *vaddr_ip, int family, int ssl);
|
extern void add_listener(int port, const char *vaddr_ip, int family, int ssl, int defer_accept);
|
||||||
extern void close_listener(struct Listener *listener);
|
extern void close_listener(struct Listener *listener);
|
||||||
extern void close_listeners(void);
|
extern void close_listeners(void);
|
||||||
extern const char *get_listener_name(const struct Listener *listener);
|
extern const char *get_listener_name(const struct Listener *listener);
|
||||||
|
|
|
@ -12838,7 +12838,7 @@ $as_echo "#define STDC_HEADERS 1" >>confdefs.h
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
|
||||||
for ac_header in crypt.h unistd.h sys/socket.h sys/stat.h sys/time.h time.h netinet/in.h arpa/inet.h errno.h sys/uio.h spawn.h sys/poll.h sys/epoll.h sys/select.h sys/devpoll.h sys/event.h port.h signal.h sys/signalfd.h sys/timerfd.h
|
for ac_header in crypt.h unistd.h sys/socket.h sys/stat.h sys/time.h time.h netinet/in.h arpa/inet.h errno.h sys/uio.h spawn.h sys/poll.h sys/epoll.h sys/select.h sys/devpoll.h sys/event.h port.h signal.h sys/signalfd.h sys/timerfd.h linux/tcp.h
|
||||||
do :
|
do :
|
||||||
as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh`
|
as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh`
|
||||||
ac_fn_c_check_header_mongrel "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default"
|
ac_fn_c_check_header_mongrel "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default"
|
||||||
|
|
|
@ -105,7 +105,7 @@ AC_TYPE_UID_T
|
||||||
dnl Checks for header files.
|
dnl Checks for header files.
|
||||||
AC_HEADER_STDC
|
AC_HEADER_STDC
|
||||||
|
|
||||||
AC_CHECK_HEADERS([crypt.h unistd.h sys/socket.h sys/stat.h sys/time.h time.h netinet/in.h arpa/inet.h errno.h sys/uio.h spawn.h sys/poll.h sys/epoll.h sys/select.h sys/devpoll.h sys/event.h port.h signal.h sys/signalfd.h sys/timerfd.h])
|
AC_CHECK_HEADERS([crypt.h unistd.h sys/socket.h sys/stat.h sys/time.h time.h netinet/in.h arpa/inet.h errno.h sys/uio.h spawn.h sys/poll.h sys/epoll.h sys/select.h sys/devpoll.h sys/event.h port.h signal.h sys/signalfd.h sys/timerfd.h linux/tcp.h])
|
||||||
AC_HEADER_TIME
|
AC_HEADER_TIME
|
||||||
|
|
||||||
dnl Networking Functions
|
dnl Networking Functions
|
||||||
|
|
|
@ -27,7 +27,7 @@
|
||||||
int rb_setup_ssl_server(const char *cert, const char *keyfile, const char *dhfile);
|
int rb_setup_ssl_server(const char *cert, const char *keyfile, const char *dhfile);
|
||||||
int rb_init_ssl(void);
|
int rb_init_ssl(void);
|
||||||
|
|
||||||
int rb_ssl_listen(rb_fde_t *F, int backlog);
|
int rb_ssl_listen(rb_fde_t *F, int backlog, int defer_accept);
|
||||||
int rb_init_prng(const char *path, prng_seed_t seed_type);
|
int rb_init_prng(const char *path, prng_seed_t seed_type);
|
||||||
|
|
||||||
int rb_get_random(void *buf, size_t length);
|
int rb_get_random(void *buf, size_t length);
|
||||||
|
|
|
@ -60,15 +60,15 @@
|
||||||
/* Define to 1 if you have the `gmtime_r' function. */
|
/* Define to 1 if you have the `gmtime_r' function. */
|
||||||
#undef HAVE_GMTIME_R
|
#undef HAVE_GMTIME_R
|
||||||
|
|
||||||
/* Has GnuTLS */
|
|
||||||
#undef HAVE_GNUTLS
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <inttypes.h> header file. */
|
/* Define to 1 if you have the <inttypes.h> header file. */
|
||||||
#undef HAVE_INTTYPES_H
|
#undef HAVE_INTTYPES_H
|
||||||
|
|
||||||
/* Define to 1 if you have the `kevent' function. */
|
/* Define to 1 if you have the `kevent' function. */
|
||||||
#undef HAVE_KEVENT
|
#undef HAVE_KEVENT
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <linux/tcp.h> header file. */
|
||||||
|
#undef HAVE_LINUX_TCP_H
|
||||||
|
|
||||||
/* Define to 1 if you have the <memory.h> header file. */
|
/* Define to 1 if you have the <memory.h> header file. */
|
||||||
#undef HAVE_MEMORY_H
|
#undef HAVE_MEMORY_H
|
||||||
|
|
||||||
|
|
|
@ -13,6 +13,10 @@
|
||||||
#include <signal.h>
|
#include <signal.h>
|
||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
|
|
||||||
|
#ifdef HAVE_LINUX_TCP_H
|
||||||
|
# include <linux/tcp.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
#ifdef __GNUC__
|
#ifdef __GNUC__
|
||||||
#undef alloca
|
#undef alloca
|
||||||
#define alloca __builtin_alloca
|
#define alloca __builtin_alloca
|
||||||
|
|
|
@ -125,8 +125,8 @@ ssize_t rb_read(rb_fde_t *, void *buf, int count);
|
||||||
int rb_pipe(rb_fde_t **, rb_fde_t **, const char *desc);
|
int rb_pipe(rb_fde_t **, rb_fde_t **, const char *desc);
|
||||||
|
|
||||||
int rb_setup_ssl_server(const char *cert, const char *keyfile, const char *dhfile);
|
int rb_setup_ssl_server(const char *cert, const char *keyfile, const char *dhfile);
|
||||||
int rb_ssl_listen(rb_fde_t *, int backlog);
|
int rb_ssl_listen(rb_fde_t *, int backlog, int defer_accept);
|
||||||
int rb_listen(rb_fde_t *, int backlog);
|
int rb_listen(rb_fde_t *, int backlog, int defer_accept);
|
||||||
|
|
||||||
const char *rb_inet_ntop(int af, const void *src, char *dst, unsigned int size);
|
const char *rb_inet_ntop(int af, const void *src, char *dst, unsigned int size);
|
||||||
int rb_inet_pton(int af, const char *src, void *dst);
|
int rb_inet_pton(int af, const char *src, void *dst);
|
||||||
|
|
|
@ -760,11 +760,33 @@ mangle_mapped_sockaddr(struct sockaddr *in)
|
||||||
* rb_listen() - listen on a port
|
* rb_listen() - listen on a port
|
||||||
*/
|
*/
|
||||||
int
|
int
|
||||||
rb_listen(rb_fde_t *F, int backlog)
|
rb_listen(rb_fde_t *F, int backlog, int defer_accept)
|
||||||
{
|
{
|
||||||
|
int result;
|
||||||
|
|
||||||
F->type = RB_FD_SOCKET | RB_FD_LISTEN;
|
F->type = RB_FD_SOCKET | RB_FD_LISTEN;
|
||||||
/* Currently just a simple wrapper for the sake of being complete */
|
|
||||||
return listen(F->fd, backlog);
|
result = listen(F->fd, backlog);
|
||||||
|
|
||||||
|
#ifdef TCP_DEFER_ACCEPT
|
||||||
|
if (defer_accept && !result)
|
||||||
|
{
|
||||||
|
setsockopt(F->fd, IPPROTO_TCP, TCP_DEFER_ACCEPT, &backlog, sizeof(int));
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
#ifdef SO_ACCEPTFILTER
|
||||||
|
if (defer_accept && !result)
|
||||||
|
{
|
||||||
|
struct accept_filter_arg afa;
|
||||||
|
|
||||||
|
memset(&afa, '\0', sizeof afa);
|
||||||
|
rb_strlcpy(afa.af_name, "dataready", sizeof afa.af_name);
|
||||||
|
(void)setsockopt(F->fd, SOL_SOCKET, SO_ACCEPTFILTER, &afa,
|
||||||
|
sizeof afa);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
|
|
@ -347,10 +347,14 @@ rb_setup_ssl_server(const char *cert, const char *keyfile, const char *dhfile)
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
rb_ssl_listen(rb_fde_t *F, int backlog)
|
rb_ssl_listen(rb_fde_t *F, int backlog, int defer_accept)
|
||||||
{
|
{
|
||||||
|
int result;
|
||||||
|
|
||||||
|
result = listen(F->fd, backlog, defer_accept);
|
||||||
F->type = RB_FD_SOCKET | RB_FD_LISTEN | RB_FD_SSL;
|
F->type = RB_FD_SOCKET | RB_FD_LISTEN | RB_FD_SSL;
|
||||||
return listen(F->fd, backlog);
|
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct ssl_connect
|
struct ssl_connect
|
||||||
|
|
|
@ -48,7 +48,7 @@ rb_init_ssl(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
rb_ssl_listen(rb_fde_t *F, int backlog)
|
rb_ssl_listen(rb_fde_t *F, int backlog, int defer_accept)
|
||||||
{
|
{
|
||||||
errno = ENOSYS;
|
errno = ENOSYS;
|
||||||
return -1;
|
return -1;
|
||||||
|
|
|
@ -389,10 +389,14 @@ rb_setup_ssl_server(const char *cert, const char *keyfile, const char *dhfile)
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
rb_ssl_listen(rb_fde_t *F, int backlog)
|
rb_ssl_listen(rb_fde_t *F, int backlog, int defer_accept)
|
||||||
{
|
{
|
||||||
|
int result;
|
||||||
|
|
||||||
|
result = rb_listen(F, backlog, defer_accept);
|
||||||
F->type = RB_FD_SOCKET | RB_FD_LISTEN | RB_FD_SSL;
|
F->type = RB_FD_SOCKET | RB_FD_LISTEN | RB_FD_SSL;
|
||||||
return listen(F->fd, backlog);
|
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct ssl_connect
|
struct ssl_connect
|
||||||
|
|
|
@ -230,7 +230,7 @@ inetport(struct Listener *listener)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(rb_listen(F, RATBOX_SOMAXCONN))
|
if(rb_listen(F, RATBOX_SOMAXCONN, listener->defer_accept))
|
||||||
{
|
{
|
||||||
ilog_error("listen()");
|
ilog_error("listen()");
|
||||||
rb_close(F);
|
rb_close(F);
|
||||||
|
@ -303,7 +303,7 @@ find_listener(struct rb_sockaddr_storage *addr)
|
||||||
* the format "255.255.255.255"
|
* the format "255.255.255.255"
|
||||||
*/
|
*/
|
||||||
void
|
void
|
||||||
add_listener(int port, const char *vhost_ip, int family, int ssl)
|
add_listener(int port, const char *vhost_ip, int family, int ssl, int defer_accept)
|
||||||
{
|
{
|
||||||
struct Listener *listener;
|
struct Listener *listener;
|
||||||
struct rb_sockaddr_storage vaddr;
|
struct rb_sockaddr_storage vaddr;
|
||||||
|
@ -376,6 +376,7 @@ add_listener(int port, const char *vhost_ip, int family, int ssl)
|
||||||
|
|
||||||
listener->F = NULL;
|
listener->F = NULL;
|
||||||
listener->ssl = ssl;
|
listener->ssl = ssl;
|
||||||
|
listener->defer_accept = defer_accept;
|
||||||
|
|
||||||
if(inetport(listener))
|
if(inetport(listener))
|
||||||
listener->active = 1;
|
listener->active = 1;
|
||||||
|
|
|
@ -31,6 +31,8 @@
|
||||||
|
|
||||||
#define CF_TYPE(x) ((x) & CF_MTYPE)
|
#define CF_TYPE(x) ((x) & CF_MTYPE)
|
||||||
|
|
||||||
|
static int yy_defer_accept = 1;
|
||||||
|
|
||||||
struct TopConf *conf_cur_block;
|
struct TopConf *conf_cur_block;
|
||||||
static char *conf_cur_block_name;
|
static char *conf_cur_block_name;
|
||||||
|
|
||||||
|
@ -871,7 +873,11 @@ conf_end_listen(struct TopConf *tc)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
conf_set_listen_defer_accept(void *data)
|
||||||
|
{
|
||||||
|
yy_defer_accept = *(unsigned int *) data;
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
conf_set_listen_port_both(void *data, int ssl)
|
conf_set_listen_port_both(void *data, int ssl)
|
||||||
|
@ -887,9 +893,9 @@ conf_set_listen_port_both(void *data, int ssl)
|
||||||
}
|
}
|
||||||
if(listener_address == NULL)
|
if(listener_address == NULL)
|
||||||
{
|
{
|
||||||
add_listener(args->v.number, listener_address, AF_INET, ssl);
|
add_listener(args->v.number, listener_address, AF_INET, ssl, yy_defer_accept);
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
add_listener(args->v.number, listener_address, AF_INET6, ssl);
|
add_listener(args->v.number, listener_address, AF_INET6, ssl, yy_defer_accept);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -902,7 +908,7 @@ conf_set_listen_port_both(void *data, int ssl)
|
||||||
#endif
|
#endif
|
||||||
family = AF_INET;
|
family = AF_INET;
|
||||||
|
|
||||||
add_listener(args->v.number, listener_address, family, ssl);
|
add_listener(args->v.number, listener_address, family, ssl, yy_defer_accept);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2344,6 +2350,7 @@ newconf_init()
|
||||||
add_top_conf("privset", NULL, NULL, conf_privset_table);
|
add_top_conf("privset", NULL, NULL, conf_privset_table);
|
||||||
|
|
||||||
add_top_conf("listen", conf_begin_listen, conf_end_listen, NULL);
|
add_top_conf("listen", conf_begin_listen, conf_end_listen, NULL);
|
||||||
|
add_conf_item("listen", "defer_accept", CF_YESNO, conf_set_listen_defer_accept);
|
||||||
add_conf_item("listen", "port", CF_INT | CF_FLIST, conf_set_listen_port);
|
add_conf_item("listen", "port", CF_INT | CF_FLIST, conf_set_listen_port);
|
||||||
add_conf_item("listen", "sslport", CF_INT | CF_FLIST, conf_set_listen_sslport);
|
add_conf_item("listen", "sslport", CF_INT | CF_FLIST, conf_set_listen_sslport);
|
||||||
add_conf_item("listen", "ip", CF_QSTRING, conf_set_listen_address);
|
add_conf_item("listen", "ip", CF_QSTRING, conf_set_listen_address);
|
||||||
|
|
Loading…
Reference in New Issue