From: Michael Poole Date: Thu, 19 Aug 2004 04:00:54 +0000 (+0000) Subject: IPv6 support (hopefully with fewer future transition pains) X-Git-Url: http://git.pk910.de/?p=ircu2.10.12-pk.git;a=commitdiff_plain;h=9b1f5beca29ec78141f19a19d689f0f7cc3fe3ac IPv6 support (hopefully with fewer future transition pains) git-svn-id: file:///home/klmitch/undernet-ircu/undernet-ircu-svn/ircu2/trunk@1094 c9e4aea6-c8fd-4c43-8297-357d70d61c8c --- diff --git a/ChangeLog b/ChangeLog index b961627..39ffb29 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,76 @@ +2004-08-17 Michael Poole + + IPv6 support, with lots of code and design borrowed from a patch + by Alex Badea. + + * config.h.in: Add place to #define IPV6 support. + + * configure.in: Check for struct sockaddr_in6, and use that as + the default choice for IPv6 support. + + * configure: Regenerate. + + * include/IPcheck.h, include/client.h, include/gline.h, + include/ircd_string.h, include/listener.h, include/match.h, + include/res.h, include/s_bsd.h: Convert from struct in_addr (from + ) to struct irc_in_addr (from "res.h"). + + * include/ircd_osdep.h, include/s_conf.h, include/uping.h: Convert + from struct sockaddr_in (from ) to struct + irc_sockaddr (from "res.h"). Add new functions os_socket(), + os_accept(), os_sendto_nonb() to help abstract away actual + sockaddr types. + + * include/ircd_chattr.h, ircd/table_gen.c: Define new bit to mark + characters valid in IPv6 addresses. + + * include/numnicks.h, ircd/numnicks.c: New functions iptobase64() + and base64toip() to convert from base64 to struct irc_in_addr. + + * ircd/IPcheck.c, ircd/channel.c, ircd/m_nick.c, ircd/m_oper.c, + ircd/m_userip.c, ircd/m_who.c, ircd/m_whois.c, ircd/s_misc.c, + ircd/s_serv.c, ircd/s_user.c, ircd/whocmds.c: Use struct + irc_in_addr instead of unsigned int or struct in_addr. + + * ircd/gline.c: Use new more-generic ipmask functions. + + * ircd/ircd.c: Use struct irc_sockaddr instead of separate port + fields. + + * ircd/ircd_reslib.c: Use struct irc_sockaddr and ircd_aton() + instead of irc_ssaddr and irc_getaddrinfo(). + + * ircd/ircd_string.c: Implement new functions: IPv6-capable + ircd_ntoa_r(), ircd_aton_ip4(), ircd_aton(). + + * ircd/match.c: Delete IPv4-only matchcompIP(). Replace with + IPv6-capable ipmask_parse() and ipmask_check(). + + * ircd/numnicks.c: Implement new functions: iptobase64() and + base64toip(). + + * ircd/os_generic: Convert external parameters to be struct + irc_addrinfo. When using IPv6 support, sockaddr_in6 is native. + Implement new functions os_sendto_nonb(), os_socket() and + os_accept(). + + * ircd/ircd_auth.c, ircd/ircd_parser.y, ircd/ircd_res.c, + ircd/listener.c, ircd/m_connect.c, ircd/s_auth.c, ircd/s_bsd.c, + ircd/s_conf.c, ircd/s_stats.c, ircd/uping.c: Use struct + irc_sockaddr instead of separate in_addr and port fields and new + OS support functions. + + * include/ircd_addrinfo.h, ircd/ircd_getaddrinfo.c, + ircd/ircd_getnameinfo.c: Remove, since these functions are no + longer used. + + * ircd/os_bsd.c, ircd/os_linux.c, ircd/os_openbsd.c, + ircd/os_solaris.c, ircd/res_adns.c, ircd/res_libresolv.c: Remove, + since these are unused and not compatible with IPv6 support. + + * ircd/Makefile.in: Remove references to ircd_getXxxxinfo.c. + Regenerate dependencies. + 2004-08-17 Michael Poole * ircd/ircd_lexer.l: Change tokenizer to reduce number of lexer diff --git a/config.h.in b/config.h.in index 9d48472..ab779ae 100644 --- a/config.h.in +++ b/config.h.in @@ -19,7 +19,7 @@ * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. * - * $Id: config.h.in,v 1.6 2004-08-16 16:32:05 entrope Exp $ + * $Id: config.h.in,v 1.7 2004-08-19 04:00:43 entrope Exp $ */ /* Define if you have the setrlimit function */ @@ -262,4 +262,7 @@ /* Define to `unsigned int' if does not define. */ #undef socklen_t +/* Define if you want IPv6 support. */ +#undef IPV6 + #endif /* INCLUDED_config_h */ diff --git a/configure b/configure index 9b8428f..ed7c59e 100755 --- a/configure +++ b/configure @@ -862,6 +862,7 @@ Optional Packages: --with-PACKAGE[=ARG] use PACKAGE [ARG=yes] --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no) --with-leak-detect Turn on the leak detector(requires patched boehm) + --without-ipv6 disable IPv6 support (default is autodetect) --with-symlink=name Name to give the symlink; if name is "no," no symlink will be created. --with-mode=mode Permissions (in octal) to give the binary @@ -6713,6 +6714,69 @@ _ACEOF fi +echo "$as_me:$LINENO: checking for struct sockaddr_in6" >&5 +echo $ECHO_N "checking for struct sockaddr_in6... $ECHO_C" >&6 +if test "${ac_cv_type_struct_sockaddr_in6+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include +#include + +int +main () +{ +if ((struct sockaddr_in6 *) 0) + return 0; +if (sizeof (struct sockaddr_in6)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_struct_sockaddr_in6=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_struct_sockaddr_in6=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_struct_sockaddr_in6" >&5 +echo "${ECHO_T}$ac_cv_type_struct_sockaddr_in6" >&6 +if test $ac_cv_type_struct_sockaddr_in6 = yes; then + unet_have_sockaddr_in6="yes" +else + unet_have_sockaddr_in6="no" +fi + @@ -8191,6 +8255,31 @@ if test x"$unet_cv_with_leak_detect" != xno; then fi fi + +# Check whether --with-ipv6 or --without-ipv6 was given. +if test "${with_ipv6+set}" = set; then + withval="$with_ipv6" + ac_cv_use_ipv6=$withval +else + ac_cv_use_ipv6=$unet_have_sockaddr_in6 +fi; +echo "$as_me:$LINENO: checking whether to use IPv6" >&5 +echo $ECHO_N "checking whether to use IPv6... $ECHO_C" >&6 +if test "${ac_cv_use_ipv6+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_use_ipv6=no +fi +echo "$as_me:$LINENO: result: $ac_cv_use_ipv6" >&5 +echo "${ECHO_T}$ac_cv_use_ipv6" >&6 +if test x"$ac_cv_use_ipv6" != "xno" ; then + +cat >>confdefs.h <<\_ACEOF +#define IPV6 +_ACEOF + +fi + echo "$as_me:$LINENO: checking whether to enable asserts" >&5 echo $ECHO_N "checking whether to enable asserts... $ECHO_C" >&6 # Check whether --enable-asserts or --disable-asserts was given. diff --git a/configure.in b/configure.in index 298eab7..7c5e5b7 100644 --- a/configure.in +++ b/configure.in @@ -119,6 +119,8 @@ AC_STRUCT_TM AC_TYPE_UID_T unet_CHECK_TYPE_SIZES AC_CHECK_TYPE(socklen_t, unsigned int) +AC_CHECK_TYPE(struct sockaddr_in6, [unet_have_sockaddr_in6="yes"], [unet_have_sockaddr_in6="no"], [#include +#include ]) dnl Checks for library functions. AC_CHECK_FUNCS([kqueue setrlimit getrusage times]) @@ -255,6 +257,15 @@ if test x"$unet_cv_with_leak_detect" != xno; then fi fi +AC_ARG_WITH([ipv6], + AS_HELP_STRING([--without-ipv6], [disable IPv6 support (default is autodetect)]), + [ac_cv_use_ipv6=$withval], + [ac_cv_use_ipv6=$unet_have_sockaddr_in6]) +AC_CACHE_CHECK([whether to use IPv6], [ac_cv_use_ipv6], [ac_cv_use_ipv6=no]) +if test x"$ac_cv_use_ipv6" != "xno" ; then + AC_DEFINE([IPV6], , [Enable IPv6 support]) +fi + dnl And now for --disable-asserts AC_MSG_CHECKING([whether to enable asserts]) AC_ARG_ENABLE([asserts], diff --git a/include/IPcheck.h b/include/IPcheck.h index 4062a90..c5eb32d 100644 --- a/include/IPcheck.h +++ b/include/IPcheck.h @@ -10,19 +10,16 @@ #include /* time_t, size_t */ #define INCLUDED_sys_types_h #endif -#ifndef INCLUDED_netinet_in_h -#include /* in_addr */ -#define INCLUDED_netinet_in_h -#endif struct Client; +struct irc_in_addr; /* * Prototypes */ extern void IPcheck_init(void); -extern int IPcheck_local_connect(struct in_addr ip, time_t* next_target_out); -extern void IPcheck_connect_fail(struct in_addr ip); +extern int IPcheck_local_connect(const struct irc_in_addr *ip, time_t *next_target_out); +extern void IPcheck_connect_fail(const struct irc_in_addr *ip); extern void IPcheck_connect_succeeded(struct Client *cptr); extern int IPcheck_remote_connect(struct Client *cptr, int is_burst); extern void IPcheck_disconnect(struct Client *cptr); diff --git a/include/client.h b/include/client.h index e5aa4a2..1496791 100644 --- a/include/client.h +++ b/include/client.h @@ -37,14 +37,13 @@ #ifndef INCLUDED_ircd_handler_h #include "ircd_handler.h" #endif +#ifndef INCLUDED_res_h +#include "res.h" +#endif #ifndef INCLUDED_sys_types_h #include /* time_t, size_t */ #define INCLUDED_sys_types_h #endif -#ifndef INCLUDED_netinet_in_h -#include /* in_addr */ -#define INCLUDED_netinet_in_h -#endif struct ConfItem; struct Listener; @@ -234,13 +233,13 @@ struct Client { */ time_t cli_lasttime; /* last time data read from socket */ time_t cli_since; /* last time we parsed something, flood control */ - + time_t cli_firsttime; /* time client was created */ time_t cli_lastnick; /* TimeStamp on nick */ int cli_marker; /* /who processing marker */ struct Flags cli_flags; /* client flags */ unsigned int cli_hopcount; /* number of servers to this 0 = local */ - struct in_addr cli_ip; /* Real ip# NOT defined for remote servers! */ + struct irc_in_addr cli_ip; /* Real IP of client */ short cli_status; /* Client type */ unsigned char cli_local; /* local or remote client */ struct Privs cli_privs; /* Oper privileges */ diff --git a/include/gline.h b/include/gline.h index a8e3913..50ef608 100644 --- a/include/gline.h +++ b/include/gline.h @@ -27,7 +27,9 @@ #define INCLUDED_sys_types_h #endif -#include +#ifndef INCLUDED_res_h +#include "res.h" +#endif struct Client; struct StatDesc; @@ -42,8 +44,8 @@ struct Gline { char *gl_reason; time_t gl_expire; time_t gl_lastmod; - struct in_addr ipnum; /* We store the IP in binary for ip glines */ - char bits; + struct irc_in_addr gl_addr; /* We store the IP in binary for ip glines */ + unsigned char gl_bits; unsigned int gl_flags; }; diff --git a/include/ircd_addrinfo.h b/include/ircd_addrinfo.h deleted file mode 100644 index d297dcb..0000000 --- a/include/ircd_addrinfo.h +++ /dev/null @@ -1,33 +0,0 @@ -#ifndef INCLUDED_config_h -#include "config.h" -#endif - -#ifndef INCLUDED_sys_types_h -#include -#define INCLUDED_sys_types_h -#endif - -#ifndef INCLUDED_sys_socket_h -#include -#define INCLUDED_sys_socket_h -#endif - -#include - -#ifndef INCLUDED_netinet_in_h -#include -#define INCLUDED_netinet_in_h -#endif - -#ifdef HAVE_STDINT_H -#ifndef INCLUDED_stdint_h -#include -#define INCLUDED_stdint_h -#endif -#endif - -int irc_getaddrinfo(const char *hostname, const char *servname, - const struct addrinfo *hints, struct addrinfo **res); -int irc_getnameinfo(const struct sockaddr *sa, socklen_t salen, char *host, - size_t hostlen, char *serv, size_t servlen, int flags); -void irc_freeaddrinfo(struct addrinfo *ai); diff --git a/include/ircd_chattr.h b/include/ircd_chattr.h index 3421fb6..31b8b98 100644 --- a/include/ircd_chattr.h +++ b/include/ircd_chattr.h @@ -61,6 +61,7 @@ #define NTL_EOL 0x10000 /* \r\n */ #define NTL_KTIME 0x20000 /* Valid character for a k:line time */ #define NTL_CHPFX 0x40000 /* channel prefix char # & + */ +#define NTL_IRCIP6 0x80000 /* Numeric IPv6 character (hex or colon) */ /* * Tables used for translation and classification macros @@ -98,6 +99,7 @@ extern const unsigned int IRCD_CharAttrTab[]; #define IsUserChar(c) (IRCD_CharAttrTab[(c) - CHAR_MIN] & NTL_IRCUI) #define IsHostChar(c) (IRCD_CharAttrTab[(c) - CHAR_MIN] & NTL_IRCHN) #define IsIPChar(c) (IRCD_CharAttrTab[(c) - CHAR_MIN] & NTL_IRCIP) +#define IsIP6Char(c) (IRCD_CharAttrTab[(c) - CHAR_MIN] & NTL_IRCIP6) #define IsEol(c) (IRCD_CharAttrTab[(c) - CHAR_MIN] & NTL_EOL) #define IsKTimeChar(c) (IRCD_CharAttrTab[(c) - CHAR_MIN] & NTL_KTIME) diff --git a/include/ircd_osdep.h b/include/ircd_osdep.h index 8639e72..87a443a 100644 --- a/include/ircd_osdep.h +++ b/include/ircd_osdep.h @@ -7,7 +7,7 @@ #define INCLUDED_ircd_osdep_h struct Client; -struct sockaddr_in; +struct irc_sockaddr; struct MsgQ; typedef enum IOResult { @@ -26,8 +26,13 @@ typedef void (*EnumFn)(struct Client*, const char* msg); extern int os_disable_options(int fd); extern int os_get_rusage(struct Client* cptr, int uptime, EnumFn enumerator); extern int os_get_sockerr(int fd); -extern int os_get_sockname(int fd, struct sockaddr_in* sin_out); -extern int os_get_peername(int fd, struct sockaddr_in* sin_out); +extern int os_get_sockname(int fd, struct irc_sockaddr* sin_out); +extern int os_get_peername(int fd, struct irc_sockaddr* sin_out); +extern int os_socket(const struct irc_sockaddr* local, int type, const char* port_name); +extern int os_accept(int fd, struct irc_sockaddr* peer); +extern IOResult os_sendto_nonb(int fd, const char* buf, unsigned int length, + unsigned int* length_out, unsigned int flags, + const struct irc_sockaddr* peer); extern IOResult os_recv_nonb(int fd, char* buf, unsigned int length, unsigned int* length_out); extern IOResult os_send_nonb(int fd, const char* buf, unsigned int length, @@ -36,8 +41,8 @@ extern IOResult os_sendv_nonb(int fd, struct MsgQ* buf, unsigned int* len_in, unsigned int* len_out); extern IOResult os_recvfrom_nonb(int fd, char* buf, unsigned int len, unsigned int* length_out, - struct sockaddr_in* from_out); -extern IOResult os_connect_nonb(int fd, const struct sockaddr_in* sin); + struct irc_sockaddr* from_out); +extern IOResult os_connect_nonb(int fd, const struct irc_sockaddr* sin); extern int os_set_fdlimit(unsigned int max_descriptors); extern int os_set_listen(int fd, int backlog); extern int os_set_nonblocking(int fd); diff --git a/include/ircd_string.h b/include/ircd_string.h index af2584e..b98c7e5 100644 --- a/include/ircd_string.h +++ b/include/ircd_string.h @@ -9,6 +9,8 @@ #include "ircd_chattr.h" #endif +struct irc_in_addr; + /* * Macros */ @@ -32,8 +34,9 @@ extern int unique_name_vector(char* names, char token, char** vector, int size); extern int token_vector(char* names, char token, char** vector, int size); -extern const char* ircd_ntoa(const char* addr); -extern const char* ircd_ntoa_r(char* buf, const char* addr); +extern const char* ircd_ntoa(const struct irc_in_addr* addr); +extern const char* ircd_ntoa_r(char* buf, const struct irc_in_addr* addr); +extern int ircd_aton(struct irc_in_addr *addr, const char *str); extern char* host_from_uh(char* buf, const char* userhost, size_t len); extern char* ircd_strtok(char** save, char* str, char* fs); diff --git a/include/listener.h b/include/listener.h index ec03e16..f33564e 100644 --- a/include/listener.h +++ b/include/listener.h @@ -26,14 +26,13 @@ #ifndef INCLUDED_ircd_events_h #include "ircd_events.h" #endif +#ifndef INCLUDED_res_h +#include "res.h" +#endif #ifndef INCLUDED_sys_types_h #include /* size_t, broken BSD system headers */ #define INCLUDED_sys_types_h #endif -#ifndef INCLUDED_netinet_in_h -#include /* in_addr */ -#define INCLUDED_netinet_in_h -#endif struct Client; struct StatDesc; @@ -41,15 +40,15 @@ struct StatDesc; struct Listener { struct Listener* next; /* list node pointer */ int fd; /* file descriptor */ - int port; /* listener IP port */ int ref_count; /* number of connection references */ unsigned char active; /* current state of listener */ unsigned char hidden; /* hidden in stats output for clients */ unsigned char server; /* 1 if port is a server listener */ + unsigned char mask_bits; /* number of bits in mask address */ int index; /* index into poll array */ time_t last_accept; /* last time listener accepted */ - struct in_addr addr; /* virtual address or INADDR_ANY */ - struct in_addr mask; /* listener hostmask */ + struct irc_sockaddr addr; /* virtual address and port */ + struct irc_in_addr mask; /* listener hostmask */ struct Socket socket; /* describe socket to event system */ }; diff --git a/include/match.h b/include/match.h index 22a95b5..5cb7f3c 100644 --- a/include/match.h +++ b/include/match.h @@ -9,20 +9,10 @@ #include /* XXX - broken BSD system headers */ #define INCLUDED_sys_types_h #endif -#ifndef INCLUDED_netinet_in_h -#include /* struct in_addr */ -#define INCLUDED_netinet_in_h +#ifndef INCLUDED_res_h +#include "res.h" #endif -/* - * Structures - */ -struct in_mask { - struct in_addr bits; - struct in_addr mask; - int fall; -}; - /* * Prototypes */ @@ -39,6 +29,8 @@ extern int matchcomp(char *cmask, int *minlen, int *charset, const char *mask); extern int matchexec(const char *string, const char *cmask, int minlen); extern int matchdecomp(char *mask, const char *cmask); extern int mmexec(const char *wcm, int wminlen, const char *rcm, int rminlen); -extern int matchcompIP(struct in_mask *imask, const char *mask); + +extern int ipmask_parse(const char *in, struct irc_in_addr *mask, unsigned char *bits_ptr); +extern int ipmask_check(const struct irc_in_addr *addr, const struct irc_in_addr *mask, unsigned char bits); #endif /* INCLUDED_match_h */ diff --git a/include/numnicks.h b/include/numnicks.h index cb812c3..78851ee 100644 --- a/include/numnicks.h +++ b/include/numnicks.h @@ -81,6 +81,8 @@ extern struct Client* FindNServer(const char* numeric); extern unsigned int base64toint(const char* str); extern const char* inttobase64(char* buf, unsigned int v, unsigned int count); +extern const char* iptobase64(char* buf, const struct irc_in_addr* addr, unsigned int count); +extern void base64toip(const char* s, struct irc_in_addr* addr); #endif /* INCLUDED_numnicks_h */ diff --git a/include/res.h b/include/res.h index 6ca91ce..7582f22 100644 --- a/include/res.h +++ b/include/res.h @@ -7,13 +7,35 @@ #ifndef INCLUDED_res_h #define INCLUDED_res_h -#include "listener.h" -#include "ircd_addrinfo.h" +#ifndef INCLUDED_config_h +#include "config.h" +#endif + +#ifndef INCLUDED_sys_types_h +#include +#define INCLUDED_sys_types_h +#endif + +#ifndef INCLUDED_sys_socket_h +#include +#define INCLUDED_sys_socket_h +#endif + +#include -#ifndef INADDR_NONE -#define INADDR_NONE ((uint32_t)-1) +#ifndef INCLUDED_netinet_in_h +#include +#define INCLUDED_netinet_in_h #endif +#ifdef HAVE_STDINT_H +#ifndef INCLUDED_stdint_h +#include +#define INCLUDED_stdint_h +#endif +#endif + +struct Client; struct StatDesc; /* Here we define some values lifted from nameser.h */ @@ -38,17 +60,22 @@ struct StatDesc; #define RRFIXEDSZ 10 #define HFIXEDSZ 12 -struct irc_ssaddr +struct irc_in_addr +{ + unsigned short in6_16[8]; +}; + +struct irc_sockaddr { - struct sockaddr_storage ss; - size_t ss_len; + struct irc_in_addr addr; + unsigned short port; }; struct DNSReply { char *h_name; int h_addrtype; - struct irc_ssaddr addr; + struct irc_in_addr addr; }; struct DNSQuery @@ -102,7 +129,10 @@ extern void delete_resolver_queries(const void *vptr); extern void report_dns_servers(struct Client *source_p, struct StatDesc *sd, int stat, char *param); extern void gethost_byname_type(const char *name, const struct DNSQuery *query, int type); extern void gethost_byname(const char *name, const struct DNSQuery *query); -extern void gethost_byaddr(const struct irc_ssaddr *addr, const struct DNSQuery *query); -extern void gethost_byinaddr(const struct in_addr *addr, const struct DNSQuery *query); +extern void gethost_byaddr(const struct irc_in_addr *addr, const struct DNSQuery *query); +extern int irc_in_addr_valid(const struct irc_in_addr *addr); +extern int irc_in_addr_cmp(const struct irc_in_addr *a, const struct irc_in_addr *b); +extern int irc_in_addr_is_ipv4(const struct irc_in_addr *addr); +extern int irc_in_addr_is_loopback(const struct irc_in_addr *addr); #endif diff --git a/include/s_bsd.h b/include/s_bsd.h index 289c5ec..69822bb 100644 --- a/include/s_bsd.h +++ b/include/s_bsd.h @@ -18,6 +18,7 @@ struct Client; struct ConfItem; struct Listener; struct MsgQ; +struct irc_in_addr; /* * TCP window sizes @@ -52,7 +53,7 @@ extern int HighestFd; extern struct Client* LocalClientArray[MAXCONNECTIONS]; extern int OpenFileDescriptorCount; -extern struct sockaddr_in VirtualHost; +extern struct irc_sockaddr VirtualHost; enum PollType { PT_NONE, @@ -73,7 +74,7 @@ struct Pollable { PollReadyFn r_handler; PollReadyFn w_handler; }; - + /* * Proto types */ @@ -87,7 +88,7 @@ extern int read_message(time_t delay); extern void init_server_identity(void); extern void close_connections(int close_stderr); extern int init_connection_limits(void); -extern void set_virtual_host(struct in_addr addr); +extern void set_virtual_host(const struct irc_in_addr *addr); extern void update_write(struct Client* cptr); #endif /* INCLUDED_s_bsd_h */ diff --git a/include/s_conf.h b/include/s_conf.h index 7e37d4c..31a7157 100644 --- a/include/s_conf.h +++ b/include/s_conf.h @@ -13,10 +13,6 @@ #include #define INCLUDED_sys_types_h #endif -#ifndef INCLUDED_netinet_in_h -#include /* struct in_addr */ -#define INCLUDED_netinet_in_h -#endif #include "client.h" struct Client; @@ -56,13 +52,12 @@ struct ConfItem unsigned int status; /* If CONF_ILLEGAL, delete when no clients */ unsigned int clients; /* Number of *LOCAL* clients using this */ struct ConnectionClass *conn_class; /* Class of connection */ - struct in_addr ipnum; /* ip number of host field */ + struct irc_sockaddr address; /* ip and port */ char *host; char *passwd; char *name; time_t hold; /* Hold until this time (calendar time) */ int dns_pending; /* a dns request is pending */ - unsigned short port; unsigned char bits; /* Number of bits for ipkills. */ struct Privs privs; /* Priviledges for opers. */ /* Used to detect if a privilege has been touched. */ @@ -74,8 +69,7 @@ struct ServerConf { char* hostname; char* passwd; char* alias; - struct in_addr address; - int port; + struct irc_in_addr address; int dns_pending; int connected; time_t hold; @@ -94,9 +88,9 @@ struct DenyConf { char* hostmask; char* message; char* usermask; - unsigned int address; + struct irc_in_addr address; unsigned int flags; - char bits; /* Number of bits for ipkills */ + unsigned char bits; /* Number of bits for ipkills */ }; #define DENY_FLAGS_FILE 0x0001 /* Comment is a filename */ @@ -109,7 +103,7 @@ struct DenyConf { struct LocalConf { char* name; char* description; - struct in_addr vhost_address; + struct irc_in_addr vhost_address; unsigned int numeric; char* location1; char* location2; diff --git a/include/s_debug.h b/include/s_debug.h index 30cf015..9b3f5e3 100644 --- a/include/s_debug.h +++ b/include/s_debug.h @@ -5,6 +5,9 @@ */ #ifndef INCLUDED_s_debug_h #define INCLUDED_s_debug_h +#ifndef INCLUDED_config_h +#include "config.h" /* Needed for DEBUGMODE */ +#endif #ifndef INCLUDED_ircd_defs_h #include "ircd_defs.h" /* Needed for HOSTLEN */ #endif diff --git a/include/uping.h b/include/uping.h index afdf286..3bb44b1 100644 --- a/include/uping.h +++ b/include/uping.h @@ -34,6 +34,9 @@ #ifndef INCLUDED_ircd_events_h #include "ircd_events.h" #endif +#ifndef INCLUDED_res_h +#include "res.h" +#endif struct Client; struct ConfItem; @@ -42,7 +45,7 @@ struct UPing { struct UPing* next; /* next ping in list, usually null */ int fd; /* socket file descriptor */ - struct sockaddr_in sin; /* socket name (ip addr, port, family ) */ + struct irc_sockaddr addr; /* socket name (ip addr, port, family ) */ char count; /* number of pings requested */ char sent; /* pings sent */ char received; /* pings received */ diff --git a/ircd/IPcheck.c b/ircd/IPcheck.c index b9e69e1..56552b3 100644 --- a/ircd/IPcheck.c +++ b/ircd/IPcheck.c @@ -47,7 +47,7 @@ struct IPTargetEntry { struct IPRegistryEntry { struct IPRegistryEntry* next; struct IPTargetEntry* target; - unsigned int addr; + struct irc_in_addr addr; int last_connect; unsigned short connected; unsigned char attempts; @@ -75,31 +75,40 @@ static struct IPRegistryEntry* freeList = 0; static struct Timer expireTimer; -static unsigned int ip_registry_hash(unsigned int ip) +static unsigned int ip_registry_hash(const struct irc_in_addr *ip) { - return ((ip >> 16) ^ ip) & (IP_REGISTRY_TABLE_SIZE - 1); + unsigned int res; + + if (ip->in6_16[0] || ip->in6_16[1] || ip->in6_16[2] || ip->in6_16[3] || ip->in6_16[4]) { + /* Only use the first 64 bits of address, since the last 64 bits + * tend to be under user control. */ + res = ip->in6_16[0] ^ ip->in6_16[1] ^ ip->in6_16[2] ^ ip->in6_16[3]; + } else { + /* Looks like an IPv4 address. */ + res = ip->in6_16[6] ^ ip->in6_16[7]; + } + return res & (IP_REGISTRY_TABLE_SIZE - 1); } -static struct IPRegistryEntry* ip_registry_find(unsigned int ip) +static struct IPRegistryEntry* ip_registry_find(const struct irc_in_addr *ip) { struct IPRegistryEntry* entry = hashTable[ip_registry_hash(ip)]; - for ( ; entry; entry = entry->next) { - if (entry->addr == ip) + for ( ; entry; entry = entry->next) + if (!irc_in_addr_cmp(ip, &entry->addr)) break; - } return entry; } static void ip_registry_add(struct IPRegistryEntry* entry) { - unsigned int bucket = ip_registry_hash(entry->addr); + unsigned int bucket = ip_registry_hash(&entry->addr); entry->next = hashTable[bucket]; hashTable[bucket] = entry; } - + static void ip_registry_remove(struct IPRegistryEntry* entry) { - unsigned int bucket = ip_registry_hash(entry->addr); + unsigned int bucket = ip_registry_hash(&entry->addr); if (hashTable[bucket] == entry) hashTable[bucket] = entry->next; else { @@ -112,7 +121,7 @@ static void ip_registry_remove(struct IPRegistryEntry* entry) } } } - + static struct IPRegistryEntry* ip_registry_new_entry() { struct IPRegistryEntry* entry = freeList; @@ -227,14 +236,14 @@ void IPcheck_init(void) * cptr->nexttarget to be `now - (TARGET_DELAY * (FREE_TARGETS - 1))', * where FREE_TARGETS may range from 0 till STARTTARGETS. */ -int ip_registry_check_local(unsigned int addr, time_t* next_target_out) +int ip_registry_check_local(const struct irc_in_addr *addr, time_t* next_target_out) { struct IPRegistryEntry* entry = ip_registry_find(addr); unsigned int free_targets = STARTTARGETS; - + if (0 == entry) { entry = ip_registry_new_entry(); - entry->addr = addr; /* The IP number of registry entry */ + memcpy(&entry->addr, addr, sizeof(entry->addr)); ip_registry_add(entry); return 1; } @@ -290,7 +299,7 @@ int ip_registry_check_local(unsigned int addr, time_t* next_target_out) */ int ip_registry_check_remote(struct Client* cptr, int is_burst) { - struct IPRegistryEntry* entry = ip_registry_find((cli_ip(cptr)).s_addr); + struct IPRegistryEntry* entry = ip_registry_find(&cli_ip(cptr)); /* * Mark that we did add/update an IPregistry entry @@ -298,7 +307,7 @@ int ip_registry_check_remote(struct Client* cptr, int is_burst) SetIPChecked(cptr); if (0 == entry) { entry = ip_registry_new_entry(); - entry->addr = (cli_ip(cptr)).s_addr; + memcpy(&entry->addr, &cli_ip(cptr), sizeof(entry->addr)); if (is_burst) entry->attempts = 0; ip_registry_add(entry); @@ -337,7 +346,7 @@ int ip_registry_check_remote(struct Client* cptr, int is_burst) * a way that the client won't be penalized when trying to reconnect * again. */ -void ip_registry_connect_fail(unsigned int addr) +void ip_registry_connect_fail(const struct irc_in_addr *addr) { struct IPRegistryEntry* entry = ip_registry_find(addr); if (entry) @@ -359,7 +368,7 @@ void ip_registry_connect_succeeded(struct Client *cptr) { const char* tr = ""; unsigned int free_targets = STARTTARGETS; - struct IPRegistryEntry* entry = ip_registry_find((cli_ip(cptr)).s_addr); + struct IPRegistryEntry* entry = ip_registry_find(&cli_ip(cptr)); if (!entry) { Debug((DEBUG_ERROR, "Missing registry entry for: %s", cli_sock_ip(cptr))); @@ -388,7 +397,7 @@ void ip_registry_connect_succeeded(struct Client *cptr) */ void ip_registry_disconnect(struct Client *cptr) { - struct IPRegistryEntry* entry = ip_registry_find((cli_ip(cptr)).s_addr); + struct IPRegistryEntry* entry = ip_registry_find(&cli_ip(cptr)); if (0 == entry) { /* * trying to find an entry for a server causes this to happen, @@ -464,7 +473,7 @@ void ip_registry_disconnect(struct Client *cptr) * * Returns number of clients with the same IP number */ -int ip_registry_count(unsigned int addr) +int ip_registry_count(const struct irc_in_addr *addr) { struct IPRegistryEntry* entry = ip_registry_find(addr); return (entry) ? entry->connected : 0; @@ -496,10 +505,10 @@ int ip_registry_count(unsigned int addr) * cptr->nexttarget to be `now - (TARGET_DELAY * (FREE_TARGETS - 1))', * where FREE_TARGETS may range from 0 till STARTTARGETS. */ -int IPcheck_local_connect(struct in_addr a, time_t* next_target_out) +int IPcheck_local_connect(const struct irc_in_addr *a, time_t* next_target_out) { assert(0 != next_target_out); - return ip_registry_check_local(a.s_addr, next_target_out); + return ip_registry_check_local(a, next_target_out); } /* @@ -530,9 +539,9 @@ int IPcheck_remote_connect(struct Client *cptr, int is_burst) * a way that the client won't be penalized when trying to reconnect * again. */ -void IPcheck_connect_fail(struct in_addr a) +void IPcheck_connect_fail(const struct irc_in_addr *a) { - ip_registry_connect_fail(a.s_addr); + ip_registry_connect_fail(a); } /* @@ -574,5 +583,5 @@ void IPcheck_disconnect(struct Client *cptr) unsigned short IPcheck_nr(struct Client *cptr) { assert(0 != cptr); - return ip_registry_count(cli_ip(cptr).s_addr); + return ip_registry_count(&cli_ip(cptr)); } diff --git a/ircd/Makefile.in b/ircd/Makefile.in index cfe075d..0fa39e2 100644 --- a/ircd/Makefile.in +++ b/ircd/Makefile.in @@ -98,8 +98,6 @@ IRCD_SRC = \ ircd_crypt.c \ ircd_events.c \ ircd_features.c \ - ircd_getaddrinfo.c \ - ircd_getnameinfo.c \ ircd_log.c \ ircd_relay.c \ ircd_reply.c \ @@ -361,46 +359,48 @@ depend: ${DEP_SRC} chattr.tab.c # ../config/config.h: # @cd ../config; ${MAKE} config.h -# DO NOT DELETE THIS LINE -- make depend depends on it. +# DO NOT DELETE THIS LINE (or the blank line after it) -- make depend depends on them. IPcheck.o: IPcheck.c ../config.h ../include/IPcheck.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/msg.h ../include/numnicks.h \ - ../include/ircd_alloc.h ../include/ircd_features.h ../include/s_debug.h \ - ../include/s_user.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/msg.h \ + ../include/numnicks.h ../include/ircd_alloc.h \ + ../include/ircd_features.h ../include/s_debug.h ../include/s_user.h \ + ../include/send.h channel.o: channel.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/destruct_event.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_alloc.h ../include/ircd_chattr.h \ - ../include/ircd_features.h ../include/ircd_log.h \ - ../include/ircd_reply.h ../include/ircd_snprintf.h \ - ../include/ircd_string.h ../include/list.h ../include/match.h \ - ../include/msg.h ../include/numeric.h ../include/numnicks.h \ - ../include/querycmds.h ../include/s_bsd.h ../include/s_conf.h \ - ../include/s_debug.h ../include/s_misc.h ../include/s_user.h \ - ../include/send.h ../include/support.h ../include/sys.h \ - ../include/whowas.h + ../include/res.h ../include/destruct_event.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ + ../include/ircd_chattr.h ../include/ircd_features.h \ + ../include/ircd_log.h ../include/ircd_reply.h \ + ../include/ircd_snprintf.h ../include/ircd_string.h ../include/list.h \ + ../include/match.h ../include/msg.h ../include/numeric.h \ + ../include/numnicks.h ../include/querycmds.h ../include/s_bsd.h \ + ../include/s_conf.h ../include/s_debug.h ../include/s_misc.h \ + ../include/s_user.h ../include/send.h ../include/support.h \ + ../include/sys.h ../include/whowas.h class.o: class.c ../config.h ../include/class.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_alloc.h ../include/ircd_features.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/list.h ../include/numeric.h \ - ../include/s_conf.h ../include/s_debug.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ + ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/list.h \ + ../include/numeric.h ../include/s_conf.h ../include/s_debug.h \ + ../include/send.h client.o: client.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/class.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ - ../include/list.h ../include/numeric.h ../include/s_conf.h \ - ../include/s_debug.h ../include/send.h + ../include/ircd_handler.h ../include/res.h ../include/class.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ + ../include/ircd_reply.h ../include/list.h ../include/numeric.h \ + ../include/s_conf.h ../include/s_debug.h ../include/send.h crule.o: crule.c ../config.h ../include/crule.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_alloc.h ../include/ircd_chattr.h \ - ../include/ircd_string.h ../include/match.h ../include/s_bsd.h \ - ../include/s_debug.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ + ../include/ircd_chattr.h ../include/ircd_string.h ../include/match.h \ + ../include/s_bsd.h ../include/s_debug.h dbuf.o: dbuf.c ../config.h ../include/dbuf.h ../include/ircd_alloc.h \ ../include/ircd_chattr.h ../include/ircd_features.h ../include/send.h \ ../include/sys.h @@ -410,36 +410,35 @@ destruct_event.o: destruct_event.c ../config.h ../include/channel.h \ ../include/send.h ../include/msg.h ../include/ircd_handler.h fileio.o: fileio.c ../config.h ../include/fileio.h \ ../include/ircd_alloc.h -gline.o: gline.c ../config.h ../include/gline.h ../include/client.h \ - ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_alloc.h ../include/ircd_features.h \ - ../include/ircd_log.h ../include/ircd_reply.h \ - ../include/ircd_snprintf.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/match.h ../include/numeric.h \ - ../include/s_bsd.h ../include/s_debug.h ../include/s_misc.h \ - ../include/s_stats.h ../include/send.h ../include/support.h \ - ../include/msg.h ../include/numnicks.h ../include/sys.h \ - ../include/whocmds.h +gline.o: gline.c ../config.h ../include/gline.h ../include/res.h \ + ../include/client.h ../include/ircd_defs.h ../include/dbuf.h \ + ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ + ../include/ircd_features.h ../include/ircd_log.h \ + ../include/ircd_reply.h ../include/ircd_snprintf.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/match.h \ + ../include/numeric.h ../include/s_bsd.h ../include/s_debug.h \ + ../include/s_misc.h ../include/s_stats.h ../include/send.h \ + ../include/support.h ../include/msg.h ../include/numnicks.h \ + ../include/sys.h ../include/whocmds.h hash.o: hash.c ../config.h ../include/hash.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/channel.h \ - ../include/ircd_chattr.h ../include/ircd_string.h ../include/ircd.h \ - ../include/struct.h ../include/msg.h ../include/send.h \ - ../include/support.h ../include/sys.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/channel.h ../include/ircd_chattr.h ../include/ircd_string.h \ + ../include/ircd.h ../include/struct.h ../include/msg.h \ + ../include/send.h ../include/support.h ../include/sys.h ircd.o: ircd.c ../config.h ../include/ircd.h ../include/struct.h \ ../include/ircd_defs.h ../include/IPcheck.h ../include/class.h \ ../include/client.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/crule.h \ - ../include/destruct_event.h ../include/channel.h ../include/hash.h \ - ../include/ircd_alloc.h ../include/ircd_features.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/crule.h ../include/destruct_event.h ../include/channel.h \ + ../include/hash.h ../include/ircd_alloc.h ../include/ircd_features.h \ ../include/ircd_log.h ../include/ircd_reply.h ../include/ircd_signal.h \ ../include/ircd_string.h ../include/ircd_chattr.h \ ../include/ircd_crypt.h ../include/jupe.h ../include/list.h \ ../include/match.h ../include/motd.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/opercmds.h \ - ../include/parse.h ../include/res.h ../include/listener.h \ - ../include/ircd_addrinfo.h ../include/s_auth.h ../include/s_bsd.h \ + ../include/parse.h ../include/s_auth.h ../include/s_bsd.h \ ../include/s_conf.h ../include/s_debug.h ../include/s_misc.h \ ../include/s_stats.h ../include/send.h ../include/sys.h \ ../include/uping.h ../include/userload.h ../include/version.h \ @@ -449,13 +448,12 @@ ircd_alloc.o: ircd_alloc.c ../config.h ../include/ircd_alloc.h \ ../include/ircd_defs.h ircd_auth.o: ircd_auth.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ ../include/ircd_alloc.h ../include/ircd_auth.h \ ../include/ircd_features.h ../include/ircd_log.h \ ../include/ircd_osdep.h ../include/ircd_snprintf.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/ircd.h \ - ../include/struct.h ../include/msg.h ../include/res.h \ - ../include/listener.h ../include/ircd_addrinfo.h ../include/s_bsd.h \ + ../include/struct.h ../include/msg.h ../include/s_bsd.h \ ../include/s_misc.h ../include/s_user.h ../include/send.h ircd_crypt.o: ircd_crypt.c ../config.h ../include/ircd_crypt.h \ ../include/ircd_alloc.h ../include/ircd_features.h \ @@ -469,128 +467,127 @@ ircd_events.o: ircd_events.c ../config.h ../include/ircd_events.h \ ircd_features.o: ircd_features.c ../config.h ../include/ircd_features.h \ ../include/channel.h ../include/ircd_defs.h ../include/class.h \ ../include/client.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ - ../include/ircd_log.h ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/match.h ../include/motd.h \ - ../include/msg.h ../include/numeric.h ../include/numnicks.h \ - ../include/random.h ../include/s_bsd.h ../include/s_debug.h \ - ../include/s_misc.h ../include/send.h ../include/support.h \ - ../include/sys.h ../include/whowas.h -ircd_getaddrinfo.o: ircd_getaddrinfo.c ../include/ircd_addrinfo.h \ - ../config.h -ircd_getnameinfo.o: ircd_getnameinfo.c ../include/ircd_addrinfo.h \ - ../config.h ../include/ircd_string.h ../include/ircd_chattr.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_alloc.h ../include/ircd_log.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/match.h \ + ../include/motd.h ../include/msg.h ../include/numeric.h \ + ../include/numnicks.h ../include/random.h ../include/s_bsd.h \ + ../include/s_debug.h ../include/s_misc.h ../include/send.h \ + ../include/support.h ../include/sys.h ../include/whowas.h ircd_log.o: ircd_log.c ../config.h ../include/ircd_log.h \ ../include/client.h ../include/ircd_defs.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/ircd_alloc.h ../include/ircd_reply.h \ + ../include/res.h ../include/ircd_alloc.h ../include/ircd_reply.h \ ../include/ircd_snprintf.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/ircd.h ../include/struct.h \ ../include/numeric.h ../include/s_debug.h ../include/send.h ircd_relay.o: ircd_relay.c ../config.h ../include/ircd_relay.h \ ../include/channel.h ../include/ircd_defs.h ../include/client.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_chattr.h ../include/ircd_features.h \ - ../include/ircd_reply.h ../include/ircd_string.h ../include/match.h \ - ../include/msg.h ../include/numeric.h ../include/numnicks.h \ - ../include/s_debug.h ../include/s_misc.h ../include/s_user.h \ - ../include/send.h + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_chattr.h \ + ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/match.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/s_debug.h \ + ../include/s_misc.h ../include/s_user.h ../include/send.h ircd_reply.o: ircd_reply.c ../config.h ../include/ircd_reply.h \ ../include/client.h ../include/ircd_defs.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_snprintf.h \ - ../include/msg.h ../include/numeric.h ../include/s_conf.h \ - ../include/s_debug.h ../include/send.h + ../include/res.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_snprintf.h ../include/msg.h ../include/numeric.h \ + ../include/s_conf.h ../include/s_debug.h ../include/send.h ircd_res.o: ircd_res.c ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../config.h ../include/ircd_handler.h ../include/ircd_alloc.h \ - ../include/ircd_log.h ../include/ircd_osdep.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h \ - ../include/ircd_snprintf.h ../include/ircd.h ../include/struct.h \ - ../include/numeric.h ../include/fileio.h ../include/s_bsd.h \ - ../include/s_stats.h ../include/ircd_features.h ../include/send.h \ - ../include/sys.h ../include/res.h ../include/listener.h \ - ../include/ircd_addrinfo.h ../include/ircd_reslib.h + ../config.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd_alloc.h ../include/ircd_log.h ../include/ircd_osdep.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/ircd_snprintf.h ../include/ircd.h \ + ../include/struct.h ../include/numeric.h ../include/fileio.h \ + ../include/s_bsd.h ../include/s_stats.h ../include/ircd_features.h \ + ../include/send.h ../include/sys.h ../include/ircd_reslib.h ircd_reslib.o: ircd_reslib.c ../include/ircd.h ../include/struct.h \ - ../include/ircd_defs.h ../include/res.h ../include/listener.h \ - ../include/ircd_events.h ../config.h ../include/ircd_addrinfo.h \ + ../include/ircd_defs.h ../include/res.h ../config.h \ ../include/ircd_reslib.h ../include/fileio.h ../include/ircd_string.h \ ../include/ircd_chattr.h ircd_signal.o: ircd_signal.c ../config.h ../include/ircd.h \ ../include/struct.h ../include/ircd_defs.h ../include/ircd_events.h \ ../include/ircd_signal.h ../include/s_conf.h ../include/client.h \ - ../include/dbuf.h ../include/msgq.h ../include/ircd_handler.h + ../include/dbuf.h ../include/msgq.h ../include/ircd_handler.h \ + ../include/res.h ircd_snprintf.o: ircd_snprintf.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/channel.h \ - ../include/ircd_snprintf.h ../include/struct.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/channel.h ../include/ircd_snprintf.h ../include/struct.h ircd_string.o: ircd_string.c ../config.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/ircd_defs.h ../include/ircd_log.h \ - chattr.tab.c + ../include/res.h chattr.tab.c jupe.o: jupe.c ../config.h ../include/jupe.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ - ../include/ircd_features.h ../include/ircd_log.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_alloc.h ../include/ircd_features.h \ + ../include/ircd_log.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/match.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/s_bsd.h \ ../include/s_misc.h ../include/send.h ../include/support.h \ ../include/sys.h -lex.yy.o: lex.yy.c ../include/ircd.h ../include/struct.h \ - ../include/ircd_defs.h y.tab.h +lex.yy.o: lex.yy.c ../config.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_defs.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/s_debug.h y.tab.h list.o: list.c ../config.h ../include/list.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_alloc.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/listener.h \ - ../include/match.h ../include/numeric.h ../include/res.h \ - ../include/ircd_addrinfo.h ../include/s_auth.h ../include/s_bsd.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/listener.h ../include/match.h \ + ../include/numeric.h ../include/s_auth.h ../include/s_bsd.h \ ../include/s_conf.h ../include/s_debug.h ../include/s_misc.h \ ../include/s_user.h ../include/send.h ../include/support.h \ ../include/whowas.h listener.o: listener.c ../config.h ../include/listener.h \ - ../include/ircd_defs.h ../include/ircd_events.h ../include/client.h \ - ../include/dbuf.h ../include/msgq.h ../include/ircd_handler.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ - ../include/ircd_features.h ../include/ircd_osdep.h \ - ../include/ircd_reply.h ../include/ircd_snprintf.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/numeric.h \ + ../include/ircd_defs.h ../include/ircd_events.h ../include/res.h \ + ../include/client.h ../include/dbuf.h ../include/msgq.h \ + ../include/ircd_handler.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_alloc.h ../include/ircd_features.h \ + ../include/ircd_osdep.h ../include/ircd_reply.h \ + ../include/ircd_snprintf.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/match.h ../include/numeric.h \ ../include/s_bsd.h ../include/s_conf.h ../include/s_misc.h \ ../include/s_stats.h ../include/send.h ../include/sys.h m_account.o: m_account.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/msg.h ../include/numnicks.h \ - ../include/s_debug.h ../include/s_user.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ + ../include/numnicks.h ../include/s_debug.h ../include/s_user.h \ + ../include/send.h m_admin.o: m_admin.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ - ../include/ircd_reply.h ../include/msg.h ../include/numeric.h \ - ../include/numnicks.h ../include/s_conf.h ../include/s_user.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_features.h ../include/ircd_reply.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/s_conf.h \ + ../include/s_user.h m_asll.o: m_asll.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/numeric.h ../include/numnicks.h \ - ../include/match.h ../include/msg.h ../include/send.h \ - ../include/s_bsd.h ../include/s_user.h + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/numeric.h \ + ../include/numnicks.h ../include/match.h ../include/msg.h \ + ../include/send.h ../include/s_bsd.h ../include/s_user.h m_away.o: m_away.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_alloc.h ../include/ircd_reply.h \ + ../include/ircd_handler.h ../include/res.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_alloc.h ../include/ircd_reply.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/s_user.h \ ../include/send.h m_burst.o: m_burst.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_alloc.h ../include/ircd_features.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_alloc.h ../include/ircd_features.h \ ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/list.h ../include/match.h \ ../include/msg.h ../include/numeric.h ../include/numnicks.h \ @@ -598,23 +595,23 @@ m_burst.o: m_burst.c ../config.h ../include/channel.h \ ../include/support.h ../include/ircd_snprintf.h m_clearmode.o: m_clearmode.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/channel.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_alloc.h ../include/ircd_features.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/channel.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_alloc.h ../include/ircd_features.h \ ../include/ircd_log.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/list.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/s_conf.h \ ../include/send.h ../include/support.h m_close.o: m_close.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_reply.h ../include/numeric.h \ - ../include/s_bsd.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ + ../include/numeric.h ../include/s_bsd.h ../include/send.h m_connect.o: m_connect.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/crule.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_features.h ../include/ircd_log.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/crule.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_features.h ../include/ircd_log.h \ ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/jupe.h ../include/match.h \ ../include/msg.h ../include/numeric.h ../include/numnicks.h \ @@ -622,156 +619,164 @@ m_connect.o: m_connect.c ../config.h ../include/client.h \ ../include/send.h m_cprivmsg.o: m_cprivmsg.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/s_user.h m_create.o: m_create.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ ../include/numnicks.h ../include/s_debug.h ../include/s_misc.h \ ../include/s_user.h ../include/send.h m_defaults.o: m_defaults.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_reply.h ../include/numeric.h \ - ../include/numnicks.h ../include/send.h ../include/supported.h \ - ../include/channel.h ../include/version.h -m_destruct.o: m_destruct.c ../config.h ../include/client.h \ - ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/send.h \ - ../include/channel.h ../include/destruct_event.h + ../include/supported.h ../include/channel.h ../include/version.h +m_destruct.o: m_destruct.c ../config.h ../include/client.h \ + ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ + ../include/numnicks.h ../include/send.h ../include/channel.h \ + ../include/destruct_event.h m_desynch.o: m_desynch.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ - ../include/numeric.h ../include/numnicks.h ../include/s_bsd.h \ - ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ + ../include/numnicks.h ../include/s_bsd.h ../include/send.h m_die.o: m_die.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_handler.h ../include/res.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ ../include/numnicks.h ../include/s_bsd.h ../include/send.h m_endburst.o: m_endburst.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ ../include/numnicks.h ../include/send.h m_error.o: m_error.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/numeric.h ../include/numnicks.h \ - ../include/s_debug.h ../include/s_misc.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_alloc.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/numeric.h \ + ../include/numnicks.h ../include/s_debug.h ../include/s_misc.h \ + ../include/send.h m_get.o: m_get.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/numeric.h \ - ../include/numnicks.h ../include/send.h + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/numeric.h ../include/numnicks.h \ + ../include/send.h m_gline.o: m_gline.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/gline.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/gline.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/match.h \ ../include/msg.h ../include/numeric.h ../include/numnicks.h \ ../include/s_conf.h ../include/s_misc.h ../include/send.h \ ../include/support.h m_help.o: m_help.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ - ../include/numnicks.h ../include/send.h + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/send.h m_info.o: m_info.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_handler.h ../include/res.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ ../include/numnicks.h ../include/s_misc.h ../include/s_user.h \ ../include/s_conf.h ../include/send.h ../include/version.h m_invite.o: m_invite.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/list.h \ ../include/msg.h ../include/numeric.h ../include/numnicks.h \ ../include/s_user.h ../include/send.h m_ison.o: m_ison.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/numeric.h ../include/send.h + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/numeric.h \ + ../include/send.h m_join.o: m_join.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/gline.h ../include/hash.h ../include/ircd.h \ + ../include/res.h ../include/gline.h ../include/hash.h ../include/ircd.h \ ../include/struct.h ../include/ircd_chattr.h ../include/ircd_features.h \ ../include/ircd_reply.h ../include/ircd_string.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/s_debug.h \ ../include/s_user.h ../include/send.h m_jupe.o: m_jupe.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/jupe.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/match.h ../include/msg.h \ - ../include/numeric.h ../include/numnicks.h ../include/s_conf.h \ - ../include/s_misc.h ../include/send.h ../include/support.h + ../include/ircd_handler.h ../include/res.h ../include/jupe.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/match.h \ + ../include/msg.h ../include/numeric.h ../include/numnicks.h \ + ../include/s_conf.h ../include/s_misc.h ../include/send.h \ + ../include/support.h m_kick.o: m_kick.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ ../include/numnicks.h ../include/send.h ../include/ircd_features.h m_kill.o: m_kill.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_features.h ../include/ircd_log.h \ - ../include/ircd_reply.h ../include/ircd_snprintf.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ - ../include/numeric.h ../include/numnicks.h ../include/s_misc.h \ - ../include/send.h ../include/whowas.h + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ + ../include/ircd_log.h ../include/ircd_reply.h \ + ../include/ircd_snprintf.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ + ../include/numnicks.h ../include/s_misc.h ../include/send.h \ + ../include/whowas.h m_links.o: m_links.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/match.h \ - ../include/msg.h ../include/numeric.h ../include/numnicks.h \ - ../include/s_user.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/match.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/s_user.h \ + ../include/send.h m_list.o: m_list.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_alloc.h ../include/ircd_chattr.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_alloc.h ../include/ircd_chattr.h \ ../include/ircd_features.h ../include/ircd_log.h \ ../include/ircd_reply.h ../include/ircd_string.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/s_bsd.h \ ../include/send.h m_lusers.o: m_lusers.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ - ../include/numeric.h ../include/numnicks.h ../include/querycmds.h \ - ../include/s_user.h ../include/s_serv.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ + ../include/numnicks.h ../include/querycmds.h ../include/s_user.h \ + ../include/s_serv.h ../include/send.h m_map.o: m_map.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_handler.h ../include/res.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ ../include/ircd_snprintf.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/list.h ../include/match.h \ ../include/msg.h ../include/numeric.h ../include/s_user.h \ @@ -779,15 +784,15 @@ m_map.o: m_map.c ../config.h ../include/client.h ../include/ircd_defs.h \ m_mode.o: m_mode.c ../config.h ../include/handlers.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ ../include/numnicks.h ../include/s_conf.h ../include/s_debug.h \ ../include/s_user.h ../include/send.h m_motd.o: m_motd.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_handler.h ../include/res.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/match.h \ ../include/motd.h ../include/msg.h ../include/numeric.h \ ../include/numnicks.h ../include/s_conf.h ../include/class.h \ @@ -795,300 +800,315 @@ m_motd.o: m_motd.c ../config.h ../include/client.h ../include/ircd_defs.h \ m_names.o: m_names.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ ../include/numnicks.h ../include/s_user.h ../include/send.h m_nick.o: m_nick.c ../config.h ../include/IPcheck.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_chattr.h \ - ../include/ircd_features.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/msg.h ../include/numeric.h \ - ../include/numnicks.h ../include/s_debug.h ../include/s_misc.h \ - ../include/s_user.h ../include/send.h ../include/sys.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_chattr.h ../include/ircd_features.h \ + ../include/ircd_reply.h ../include/ircd_string.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/s_debug.h \ + ../include/s_misc.h ../include/s_user.h ../include/send.h \ + ../include/sys.h m_notice.o: m_notice.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ ../include/ircd_chattr.h ../include/ircd_relay.h \ ../include/ircd_reply.h ../include/ircd_string.h ../include/match.h \ ../include/msg.h ../include/numeric.h ../include/send.h \ ../include/handlers.h m_oper.o: m_oper.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_features.h ../include/ircd_log.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ + ../include/ircd_log.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/ircd_crypt.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/querycmds.h \ ../include/s_conf.h ../include/s_debug.h ../include/s_user.h \ ../include/s_misc.h ../include/send.h ../include/support.h m_opmode.o: m_opmode.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/channel.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/channel.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/send.h \ ../include/s_conf.h m_part.o: m_part.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/numeric.h ../include/numnicks.h \ ../include/send.h m_pass.o: m_pass.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/ircd_reply.h \ + ../include/ircd_handler.h ../include/res.h ../include/ircd_reply.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/send.h m_ping.o: m_ping.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/ircd.h \ - ../include/struct.h ../include/msg.h ../include/numeric.h \ - ../include/numnicks.h ../include/opercmds.h ../include/s_debug.h \ - ../include/send.h -m_pong.o: m_pong.c ../config.h ../include/client.h ../include/ircd_defs.h \ - ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ - ../include/numnicks.h ../include/opercmds.h ../include/s_user.h \ - ../include/send.h + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/ircd.h ../include/struct.h \ + ../include/msg.h ../include/numeric.h ../include/numnicks.h \ + ../include/opercmds.h ../include/s_debug.h ../include/send.h +m_pong.o: m_pong.c ../config.h ../include/client.h ../include/ircd_defs.h \ + ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/opercmds.h \ + ../include/s_user.h ../include/send.h m_privmsg.o: m_privmsg.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_chattr.h ../include/ircd_features.h \ - ../include/ircd_relay.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/match.h ../include/msg.h \ - ../include/numeric.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_chattr.h \ + ../include/ircd_features.h ../include/ircd_relay.h \ + ../include/ircd_reply.h ../include/ircd_string.h ../include/match.h \ + ../include/msg.h ../include/numeric.h ../include/send.h m_privs.o: m_privs.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/numeric.h \ - ../include/numnicks.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/numeric.h ../include/numnicks.h \ + ../include/send.h m_proto.o: m_proto.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_alloc.h ../include/ircd_chattr.h \ - ../include/ircd_reply.h ../include/ircd_string.h ../include/msg.h \ - ../include/numeric.h ../include/numnicks.h ../include/s_debug.h \ - ../include/s_misc.h ../include/send.h ../include/supported.h \ - ../include/channel.h ../include/version.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ + ../include/ircd_chattr.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/msg.h ../include/numeric.h \ + ../include/numnicks.h ../include/s_debug.h ../include/s_misc.h \ + ../include/send.h ../include/supported.h ../include/channel.h \ + ../include/version.h m_pseudo.o: m_pseudo.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ - ../include/ircd_relay.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h \ - ../include/ircd_snprintf.h ../include/msg.h ../include/numeric.h \ - ../include/numnicks.h ../include/s_conf.h ../include/s_user.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_features.h ../include/ircd_relay.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/ircd_snprintf.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/s_conf.h \ + ../include/s_user.h m_quit.o: m_quit.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/s_misc.h ../include/ircd_reply.h + ../include/res.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/s_misc.h \ + ../include/ircd_reply.h m_rehash.o: m_rehash.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_log.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/motd.h \ - ../include/numeric.h ../include/s_conf.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_log.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/motd.h ../include/numeric.h \ + ../include/s_conf.h ../include/send.h m_reset.o: m_reset.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/numeric.h \ + ../include/numnicks.h ../include/send.h +m_restart.o: m_restart.c ../config.h ../include/client.h \ + ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_log.h \ ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/numeric.h ../include/numnicks.h \ ../include/send.h -m_restart.o: m_restart.c ../config.h ../include/client.h \ - ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_log.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/numeric.h \ - ../include/numnicks.h ../include/send.h m_rping.o: m_rping.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ - ../include/numeric.h ../include/numnicks.h ../include/opercmds.h \ - ../include/s_user.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ + ../include/numnicks.h ../include/opercmds.h ../include/s_user.h \ + ../include/send.h m_rpong.o: m_rpong.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ - ../include/numeric.h ../include/numnicks.h ../include/opercmds.h \ - ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ + ../include/numnicks.h ../include/opercmds.h ../include/send.h m_server.o: m_server.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_log.h \ - ../include/ircd_features.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/jupe.h \ - ../include/list.h ../include/match.h ../include/msg.h \ - ../include/numeric.h ../include/numnicks.h ../include/querycmds.h \ - ../include/s_bsd.h ../include/s_conf.h ../include/s_debug.h \ - ../include/s_misc.h ../include/s_serv.h ../include/send.h \ - ../include/userload.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_log.h ../include/ircd_features.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/jupe.h ../include/list.h \ + ../include/match.h ../include/msg.h ../include/numeric.h \ + ../include/numnicks.h ../include/querycmds.h ../include/s_bsd.h \ + ../include/s_conf.h ../include/s_debug.h ../include/s_misc.h \ + ../include/s_serv.h ../include/send.h ../include/userload.h m_set.o: m_set.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/numeric.h \ - ../include/numnicks.h ../include/send.h + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/numeric.h ../include/numnicks.h \ + ../include/send.h m_settime.o: m_settime.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ - ../include/ircd_reply.h ../include/ircd_snprintf.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/list.h \ - ../include/msg.h ../include/numeric.h ../include/numnicks.h \ - ../include/s_user.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_snprintf.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/list.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/s_user.h \ + ../include/send.h m_silence.o: m_silence.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/list.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/s_user.h \ ../include/send.h m_squit.o: m_squit.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_chattr.h \ - ../include/ircd_reply.h ../include/ircd_string.h ../include/numeric.h \ - ../include/numnicks.h ../include/match.h ../include/s_debug.h \ - ../include/s_misc.h ../include/s_user.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_chattr.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/numeric.h ../include/numnicks.h \ + ../include/match.h ../include/s_debug.h ../include/s_misc.h \ + ../include/s_user.h ../include/send.h m_stats.o: m_stats.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ - ../include/numeric.h ../include/s_stats.h ../include/s_user.h \ - ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ + ../include/s_stats.h ../include/s_user.h ../include/send.h m_time.o: m_time.c ../config.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_handler.h ../include/res.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/s_misc.h \ ../include/s_user.h ../include/send.h m_topic.o: m_topic.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/send.h m_trace.o: m_trace.c ../config.h ../include/class.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/match.h ../include/msg.h \ - ../include/numeric.h ../include/numnicks.h ../include/s_bsd.h \ - ../include/s_conf.h ../include/s_user.h ../include/send.h \ - ../include/version.h -m_uping.o: m_uping.c ../config.h ../include/client.h \ - ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_reply.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_features.h ../include/ircd_reply.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/match.h \ ../include/msg.h ../include/numeric.h ../include/numnicks.h \ - ../include/s_conf.h ../include/s_user.h ../include/send.h \ - ../include/uping.h + ../include/s_bsd.h ../include/s_conf.h ../include/s_user.h \ + ../include/send.h ../include/version.h +m_uping.o: m_uping.c ../config.h ../include/client.h \ + ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/match.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/s_conf.h \ + ../include/s_user.h ../include/send.h ../include/uping.h m_user.o: m_user.c ../config.h ../include/handlers.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_chattr.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/numeric.h ../include/numnicks.h \ - ../include/s_debug.h ../include/s_misc.h ../include/s_user.h \ - ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_chattr.h \ + ../include/ircd_reply.h ../include/ircd_string.h ../include/numeric.h \ + ../include/numnicks.h ../include/s_debug.h ../include/s_misc.h \ + ../include/s_user.h ../include/send.h m_userhost.o: m_userhost.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/numeric.h ../include/s_user.h \ ../include/struct.h m_userip.o: m_userip.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/ircd_features.h \ ../include/numeric.h ../include/s_user.h ../include/struct.h m_version.o: m_version.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ - ../include/ircd_reply.h ../include/ircd_snprintf.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ - ../include/numeric.h ../include/numnicks.h ../include/s_debug.h \ - ../include/s_user.h ../include/send.h ../include/supported.h \ - ../include/channel.h ../include/version.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_snprintf.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ + ../include/numnicks.h ../include/s_debug.h ../include/s_user.h \ + ../include/send.h ../include/supported.h ../include/channel.h \ + ../include/version.h m_wallchops.o: m_wallchops.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ ../include/numnicks.h ../include/s_user.h ../include/send.h m_wallops.o: m_wallops.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ ../include/send.h m_wallusers.o: m_wallusers.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ ../include/send.h m_wallvoices.o: m_wallvoices.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ ../include/numnicks.h ../include/s_user.h ../include/send.h m_who.o: m_who.c ../config.h ../include/channel.h ../include/ircd_defs.h \ ../include/client.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_chattr.h \ - ../include/ircd_features.h ../include/ircd_log.h \ - ../include/ircd_reply.h ../include/ircd_string.h ../include/match.h \ - ../include/numeric.h ../include/numnicks.h ../include/send.h \ - ../include/support.h ../include/whocmds.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_chattr.h ../include/ircd_features.h \ + ../include/ircd_log.h ../include/ircd_reply.h ../include/ircd_string.h \ + ../include/match.h ../include/numeric.h ../include/numnicks.h \ + ../include/send.h ../include/support.h ../include/whocmds.h m_whois.o: m_whois.c ../config.h ../include/channel.h \ ../include/ircd_defs.h ../include/client.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/hash.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/res.h ../include/hash.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_features.h ../include/ircd_reply.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/match.h \ ../include/msg.h ../include/numeric.h ../include/numnicks.h \ ../include/s_user.h ../include/send.h ../include/whocmds.h m_whowas.o: m_whowas.c ../config.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/msg.h ../include/numeric.h \ - ../include/numnicks.h ../include/s_user.h ../include/s_misc.h \ - ../include/send.h ../include/whowas.h -match.o: match.c ../config.h ../include/match.h ../include/ircd_chattr.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/s_user.h \ + ../include/s_misc.h ../include/send.h ../include/whowas.h +match.o: match.c ../config.h ../include/match.h ../include/res.h \ + ../include/ircd_chattr.h ../include/ircd_string.h \ + ../include/ircd_snprintf.h ../include/support.h memdebug.o: memdebug.c ../include/ircd.h ../include/struct.h \ ../include/ircd_defs.h ../include/ircd_alloc.h ../include/client.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../config.h ../include/ircd_handler.h ../include/s_debug.h + ../config.h ../include/ircd_handler.h ../include/res.h \ + ../include/s_debug.h motd.o: motd.c ../config.h ../include/motd.h ../include/class.h \ ../include/client.h ../include/ircd_defs.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/fileio.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_alloc.h ../include/ircd_features.h \ + ../include/res.h ../include/fileio.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_alloc.h ../include/ircd_features.h \ ../include/ircd_reply.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/match.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/s_conf.h \ @@ -1102,108 +1122,107 @@ msgq.o: msgq.c ../config.h ../include/msgq.h ../include/ircd_defs.h \ numnicks.o: numnicks.c ../config.h ../include/numnicks.h \ ../include/client.h ../include/ircd_defs.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/match.h \ - ../include/s_bsd.h ../include/s_debug.h ../include/s_misc.h + ../include/res.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_alloc.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/match.h ../include/s_bsd.h \ + ../include/s_debug.h ../include/s_misc.h opercmds.o: opercmds.c ../config.h ../include/opercmds.h \ ../include/class.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_chattr.h ../include/ircd_reply.h \ + ../include/ircd_handler.h ../include/res.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_chattr.h ../include/ircd_reply.h \ ../include/ircd_string.h ../include/listener.h ../include/match.h \ ../include/msg.h ../include/numeric.h ../include/numnicks.h \ ../include/s_conf.h ../include/send.h os_generic.o: os_generic.c ../config.h ../include/ircd_osdep.h \ - ../include/msgq.h ../include/ircd_defs.h + ../include/msgq.h ../include/ircd_defs.h ../include/res.h \ + ../include/s_bsd.h ../include/sys.h packet.o: packet.c ../config.h ../include/packet.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_chattr.h ../include/parse.h \ - ../include/s_bsd.h ../include/s_misc.h ../include/send.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_chattr.h \ + ../include/parse.h ../include/s_bsd.h ../include/s_misc.h \ + ../include/send.h parse.o: parse.c ../config.h ../include/parse.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/channel.h \ - ../include/handlers.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_alloc.h ../include/ircd_chattr.h \ - ../include/ircd_features.h ../include/ircd_reply.h \ - ../include/ircd_string.h ../include/msg.h ../include/numeric.h \ - ../include/numnicks.h ../include/opercmds.h ../include/querycmds.h \ - ../include/res.h ../include/listener.h ../include/ircd_addrinfo.h \ - ../include/s_bsd.h ../include/s_conf.h ../include/s_debug.h \ - ../include/s_misc.h ../include/s_numeric.h ../include/s_user.h \ - ../include/send.h ../include/sys.h ../include/whocmds.h \ - ../include/whowas.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/channel.h ../include/handlers.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ + ../include/ircd_chattr.h ../include/ircd_features.h \ + ../include/ircd_reply.h ../include/ircd_string.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/opercmds.h \ + ../include/querycmds.h ../include/s_bsd.h ../include/s_conf.h \ + ../include/s_debug.h ../include/s_misc.h ../include/s_numeric.h \ + ../include/s_user.h ../include/send.h ../include/sys.h \ + ../include/whocmds.h ../include/whowas.h querycmds.o: querycmds.c ../config.h ../include/querycmds.h \ ../include/ircd_features.h random.o: random.c ../config.h ../include/random.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ ../include/ircd_log.h ../include/ircd_reply.h ../include/send.h s_auth.o: s_auth.c ../config.h ../include/s_auth.h \ ../include/ircd_events.h ../include/client.h ../include/ircd_defs.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_handler.h \ - ../include/IPcheck.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_alloc.h ../include/ircd_chattr.h \ + ../include/res.h ../include/IPcheck.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_alloc.h ../include/ircd_chattr.h \ ../include/ircd_features.h ../include/ircd_log.h \ ../include/ircd_osdep.h ../include/ircd_snprintf.h \ ../include/ircd_string.h ../include/list.h ../include/numeric.h \ - ../include/querycmds.h ../include/res.h ../include/listener.h \ - ../include/ircd_addrinfo.h ../include/s_bsd.h ../include/s_debug.h \ + ../include/querycmds.h ../include/s_bsd.h ../include/s_debug.h \ ../include/s_misc.h ../include/send.h ../include/sys.h s_bsd.o: s_bsd.c ../config.h ../include/s_bsd.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/IPcheck.h \ - ../include/channel.h ../include/class.h ../include/hash.h \ - ../include/ircd_alloc.h ../include/ircd_log.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/IPcheck.h ../include/channel.h ../include/class.h \ + ../include/hash.h ../include/ircd_alloc.h ../include/ircd_log.h \ ../include/ircd_features.h ../include/ircd_osdep.h \ ../include/ircd_reply.h ../include/ircd_snprintf.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/ircd.h \ ../include/struct.h ../include/list.h ../include/listener.h \ ../include/msg.h ../include/numeric.h ../include/numnicks.h \ ../include/packet.h ../include/parse.h ../include/querycmds.h \ - ../include/res.h ../include/ircd_addrinfo.h ../include/s_auth.h \ - ../include/s_conf.h ../include/s_debug.h ../include/s_misc.h \ - ../include/s_user.h ../include/send.h ../include/support.h \ - ../include/sys.h ../include/uping.h ../include/version.h + ../include/s_auth.h ../include/s_conf.h ../include/s_debug.h \ + ../include/s_misc.h ../include/s_user.h ../include/send.h \ + ../include/support.h ../include/sys.h ../include/uping.h \ + ../include/version.h s_conf.o: s_conf.c ../config.h ../include/s_conf.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/IPcheck.h \ - ../include/class.h ../include/crule.h ../include/ircd_features.h \ - ../include/fileio.h ../include/gline.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ - ../include/ircd_auth.h ../include/ircd_chattr.h ../include/ircd_log.h \ - ../include/ircd_reply.h ../include/ircd_snprintf.h \ - ../include/ircd_string.h ../include/list.h ../include/listener.h \ - ../include/match.h ../include/motd.h ../include/numeric.h \ - ../include/numnicks.h ../include/opercmds.h ../include/parse.h \ - ../include/res.h ../include/ircd_addrinfo.h ../include/s_bsd.h \ - ../include/s_debug.h ../include/s_misc.h ../include/send.h \ - ../include/support.h ../include/sys.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/IPcheck.h ../include/class.h ../include/crule.h \ + ../include/ircd_features.h ../include/fileio.h ../include/gline.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_alloc.h ../include/ircd_auth.h ../include/ircd_chattr.h \ + ../include/ircd_log.h ../include/ircd_reply.h \ + ../include/ircd_snprintf.h ../include/ircd_string.h ../include/list.h \ + ../include/listener.h ../include/match.h ../include/motd.h \ + ../include/numeric.h ../include/numnicks.h ../include/opercmds.h \ + ../include/parse.h ../include/s_bsd.h ../include/s_debug.h \ + ../include/s_misc.h ../include/send.h ../include/support.h \ + ../include/sys.h s_debug.o: s_debug.c ../config.h ../include/s_debug.h \ ../include/ircd_defs.h ../include/channel.h ../include/class.h \ ../include/client.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/gline.h \ - ../include/hash.h ../include/ircd_alloc.h ../include/ircd_features.h \ - ../include/ircd_log.h ../include/ircd_osdep.h ../include/ircd_reply.h \ - ../include/ircd.h ../include/struct.h ../include/jupe.h \ - ../include/list.h ../include/motd.h ../include/numeric.h \ - ../include/numnicks.h ../include/res.h ../include/listener.h \ - ../include/ircd_addrinfo.h ../include/s_bsd.h ../include/s_conf.h \ - ../include/s_stats.h ../include/send.h ../include/sys.h \ - ../include/whowas.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/gline.h ../include/hash.h ../include/ircd_alloc.h \ + ../include/ircd_features.h ../include/ircd_log.h \ + ../include/ircd_osdep.h ../include/ircd_reply.h ../include/ircd.h \ + ../include/struct.h ../include/jupe.h ../include/list.h \ + ../include/motd.h ../include/numeric.h ../include/numnicks.h \ + ../include/s_bsd.h ../include/s_conf.h ../include/s_stats.h \ + ../include/send.h ../include/sys.h ../include/whowas.h s_err.o: s_err.c ../config.h ../include/numeric.h ../include/s_debug.h \ ../include/ircd_defs.h s_misc.o: s_misc.c ../config.h ../include/s_misc.h ../include/IPcheck.h \ ../include/channel.h ../include/ircd_defs.h ../include/client.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_alloc.h ../include/ircd_auth.h \ - ../include/ircd_features.h ../include/ircd_log.h \ + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ + ../include/ircd_auth.h ../include/ircd_features.h ../include/ircd_log.h \ ../include/ircd_reply.h ../include/ircd_snprintf.h \ ../include/ircd_string.h ../include/ircd_chattr.h ../include/list.h \ ../include/match.h ../include/msg.h ../include/numeric.h \ ../include/numnicks.h ../include/parse.h ../include/querycmds.h \ - ../include/res.h ../include/listener.h ../include/ircd_addrinfo.h \ ../include/s_bsd.h ../include/s_conf.h ../include/s_debug.h \ ../include/s_stats.h ../include/s_user.h ../include/send.h \ ../include/support.h ../include/sys.h ../include/uping.h \ @@ -1211,40 +1230,41 @@ s_misc.o: s_misc.c ../config.h ../include/s_misc.h ../include/IPcheck.h \ s_numeric.o: s_numeric.c ../config.h ../include/s_numeric.h \ ../include/channel.h ../include/ircd_defs.h ../include/client.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_features.h \ + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_features.h \ ../include/ircd_snprintf.h ../include/numnicks.h ../include/send.h s_serv.o: s_serv.c ../config.h ../include/s_serv.h ../include/IPcheck.h \ ../include/channel.h ../include/ircd_defs.h ../include/client.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/gline.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ - ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/ircd_chattr.h ../include/ircd_snprintf.h \ - ../include/ircd_crypt.h ../include/jupe.h ../include/list.h \ - ../include/match.h ../include/msg.h ../include/numeric.h \ - ../include/numnicks.h ../include/parse.h ../include/querycmds.h \ - ../include/ircd_features.h ../include/s_bsd.h ../include/s_conf.h \ - ../include/s_debug.h ../include/s_misc.h ../include/s_user.h \ - ../include/send.h ../include/sys.h ../include/userload.h + ../include/ircd_handler.h ../include/res.h ../include/gline.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_alloc.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/ircd_chattr.h \ + ../include/ircd_snprintf.h ../include/ircd_crypt.h ../include/jupe.h \ + ../include/list.h ../include/match.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/parse.h \ + ../include/querycmds.h ../include/ircd_features.h ../include/s_bsd.h \ + ../include/s_conf.h ../include/s_debug.h ../include/s_misc.h \ + ../include/s_user.h ../include/send.h ../include/sys.h \ + ../include/userload.h s_stats.o: s_stats.c ../config.h ../include/class.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/gline.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_chattr.h \ - ../include/ircd_features.h ../include/ircd_crypt.h \ - ../include/ircd_log.h ../include/ircd_reply.h ../include/ircd_string.h \ - ../include/listener.h ../include/list.h ../include/match.h \ - ../include/motd.h ../include/msg.h ../include/numeric.h \ - ../include/numnicks.h ../include/res.h ../include/ircd_addrinfo.h \ - ../include/s_bsd.h ../include/s_conf.h ../include/s_debug.h \ - ../include/s_misc.h ../include/s_serv.h ../include/s_stats.h \ - ../include/s_user.h ../include/send.h ../include/userload.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/gline.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_chattr.h ../include/ircd_features.h \ + ../include/ircd_crypt.h ../include/ircd_log.h ../include/ircd_reply.h \ + ../include/ircd_string.h ../include/listener.h ../include/list.h \ + ../include/match.h ../include/motd.h ../include/msg.h \ + ../include/numeric.h ../include/numnicks.h ../include/s_bsd.h \ + ../include/s_conf.h ../include/s_debug.h ../include/s_misc.h \ + ../include/s_serv.h ../include/s_stats.h ../include/s_user.h \ + ../include/send.h ../include/userload.h s_user.o: s_user.c ../config.h ../include/s_user.h ../include/IPcheck.h \ ../include/channel.h ../include/ircd_defs.h ../include/class.h \ ../include/client.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/hash.h \ - ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ - ../include/ircd_auth.h ../include/ircd_chattr.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/hash.h ../include/ircd.h ../include/struct.h \ + ../include/ircd_alloc.h ../include/ircd_auth.h ../include/ircd_chattr.h \ ../include/ircd_features.h ../include/ircd_log.h \ ../include/ircd_reply.h ../include/ircd_snprintf.h \ ../include/ircd_string.h ../include/list.h ../include/match.h \ @@ -1258,21 +1278,22 @@ s_user.o: s_user.c ../config.h ../include/s_user.h ../include/IPcheck.h \ send.o: send.c ../config.h ../include/send.h ../include/channel.h \ ../include/ircd_defs.h ../include/class.h ../include/client.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/ircd.h ../include/struct.h \ - ../include/ircd_features.h ../include/ircd_snprintf.h \ - ../include/ircd_string.h ../include/ircd_chattr.h ../include/list.h \ - ../include/match.h ../include/msg.h ../include/numnicks.h \ - ../include/parse.h ../include/s_bsd.h ../include/s_debug.h \ - ../include/s_misc.h ../include/s_user.h ../include/sys.h + ../include/ircd_handler.h ../include/res.h ../include/ircd.h \ + ../include/struct.h ../include/ircd_features.h \ + ../include/ircd_snprintf.h ../include/ircd_string.h \ + ../include/ircd_chattr.h ../include/list.h ../include/match.h \ + ../include/msg.h ../include/numnicks.h ../include/parse.h \ + ../include/s_bsd.h ../include/s_debug.h ../include/s_misc.h \ + ../include/s_user.h ../include/sys.h support.o: support.c ../config.h ../include/support.h ../include/fileio.h \ ../include/ircd.h ../include/struct.h ../include/ircd_defs.h \ ../include/ircd_chattr.h ../include/ircd_snprintf.h ../include/s_bsd.h \ ../include/s_debug.h ../include/send.h ../include/sys.h uping.o: uping.c ../config.h ../include/uping.h ../include/ircd_defs.h \ - ../include/ircd_events.h ../include/client.h ../include/dbuf.h \ - ../include/msgq.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_alloc.h ../include/ircd_log.h \ - ../include/ircd_osdep.h ../include/ircd_string.h \ + ../include/ircd_events.h ../include/res.h ../include/client.h \ + ../include/dbuf.h ../include/msgq.h ../include/ircd_handler.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ + ../include/ircd_log.h ../include/ircd_osdep.h ../include/ircd_string.h \ ../include/ircd_chattr.h ../include/match.h ../include/msg.h \ ../include/numeric.h ../include/numnicks.h ../include/s_bsd.h \ ../include/s_conf.h ../include/s_debug.h ../include/s_misc.h \ @@ -1280,41 +1301,43 @@ uping.o: uping.c ../config.h ../include/uping.h ../include/ircd_defs.h \ userload.o: userload.c ../config.h ../include/userload.h \ ../include/client.h ../include/ircd_defs.h ../include/dbuf.h \ ../include/msgq.h ../include/ircd_events.h ../include/ircd_handler.h \ - ../include/ircd.h ../include/struct.h ../include/msg.h \ + ../include/res.h ../include/ircd.h ../include/struct.h ../include/msg.h \ ../include/numnicks.h ../include/querycmds.h ../include/ircd_features.h \ ../include/s_misc.h ../include/s_stats.h ../include/send.h \ ../include/sys.h whocmds.o: whocmds.c ../config.h ../include/whocmds.h \ ../include/channel.h ../include/ircd_defs.h ../include/client.h \ ../include/dbuf.h ../include/msgq.h ../include/ircd_events.h \ - ../include/ircd_handler.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_chattr.h ../include/ircd_features.h \ - ../include/ircd_reply.h ../include/ircd_snprintf.h \ - ../include/ircd_string.h ../include/list.h ../include/match.h \ - ../include/numeric.h ../include/numnicks.h ../include/querycmds.h \ - ../include/random.h ../include/s_bsd.h ../include/s_conf.h \ - ../include/s_misc.h ../include/s_user.h ../include/send.h \ - ../include/support.h ../include/sys.h ../include/userload.h \ - ../include/version.h ../include/whowas.h ../include/msg.h + ../include/ircd_handler.h ../include/res.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_chattr.h \ + ../include/ircd_features.h ../include/ircd_reply.h \ + ../include/ircd_snprintf.h ../include/ircd_string.h ../include/list.h \ + ../include/match.h ../include/numeric.h ../include/numnicks.h \ + ../include/querycmds.h ../include/random.h ../include/s_bsd.h \ + ../include/s_conf.h ../include/s_misc.h ../include/s_user.h \ + ../include/send.h ../include/support.h ../include/sys.h \ + ../include/userload.h ../include/version.h ../include/whowas.h \ + ../include/msg.h whowas.o: whowas.c ../config.h ../include/whowas.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_alloc.h ../include/ircd_chattr.h \ - ../include/ircd_features.h ../include/ircd_string.h ../include/list.h \ - ../include/numeric.h ../include/s_debug.h ../include/s_misc.h \ - ../include/s_user.h ../include/send.h ../include/support.h \ - ../include/sys.h ../include/msg.h + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ + ../include/ircd_chattr.h ../include/ircd_features.h \ + ../include/ircd_string.h ../include/list.h ../include/numeric.h \ + ../include/s_debug.h ../include/s_misc.h ../include/s_user.h \ + ../include/send.h ../include/support.h ../include/sys.h \ + ../include/msg.h y.tab.o: y.tab.c ../config.h ../include/s_conf.h ../include/client.h \ ../include/ircd_defs.h ../include/dbuf.h ../include/msgq.h \ - ../include/ircd_events.h ../include/ircd_handler.h ../include/class.h \ - ../include/crule.h ../include/ircd_features.h ../include/fileio.h \ - ../include/gline.h ../include/hash.h ../include/ircd.h \ - ../include/struct.h ../include/ircd_alloc.h ../include/ircd_auth.h \ - ../include/ircd_chattr.h ../include/ircd_log.h ../include/ircd_reply.h \ - ../include/ircd_snprintf.h ../include/ircd_string.h ../include/list.h \ - ../include/listener.h ../include/match.h ../include/motd.h \ - ../include/numeric.h ../include/numnicks.h ../include/opercmds.h \ - ../include/parse.h ../include/res.h ../include/ircd_addrinfo.h \ + ../include/ircd_events.h ../include/ircd_handler.h ../include/res.h \ + ../include/class.h ../include/crule.h ../include/ircd_features.h \ + ../include/fileio.h ../include/gline.h ../include/hash.h \ + ../include/ircd.h ../include/struct.h ../include/ircd_alloc.h \ + ../include/ircd_auth.h ../include/ircd_chattr.h ../include/ircd_log.h \ + ../include/ircd_reply.h ../include/ircd_snprintf.h \ + ../include/ircd_string.h ../include/list.h ../include/listener.h \ + ../include/match.h ../include/motd.h ../include/numeric.h \ + ../include/numnicks.h ../include/opercmds.h ../include/parse.h \ ../include/s_bsd.h ../include/s_debug.h ../include/s_misc.h \ ../include/send.h ../include/support.h ../include/sys.h engine_devpoll.o: engine_devpoll.c ../config.h ../include/ircd_events.h \ diff --git a/ircd/channel.c b/ircd/channel.c index 6b03827..885e787 100644 --- a/ircd/channel.c +++ b/ircd/channel.c @@ -174,12 +174,11 @@ static char *make_nick_user_host(char *namebuf, const char *nick, * Create a string of form "foo!bar@123.456.789.123" given foo, bar and the * IP-number as the parameters. If NULL, they become "*". */ -#define NUI_BUFSIZE (NICKLEN + USERLEN + 16 + 3) +#define NUI_BUFSIZE (NICKLEN + USERLEN + SOCKIPLEN + 4) static char *make_nick_user_ip(char *ipbuf, char *nick, char *name, - struct in_addr ip) + const struct irc_in_addr *ip) { - ircd_snprintf(0, ipbuf, NUI_BUFSIZE, "%s!%s@%s", nick, name, - ircd_ntoa((const char*) &ip)); + ircd_snprintf(0, ipbuf, NUI_BUFSIZE, "%s!%s@%s", nick, name, ircd_ntoa(ip)); return ipbuf; } @@ -480,7 +479,7 @@ static int is_banned(struct Client *cptr, struct Channel *chptr, if ((tmp->flags & CHFL_BAN_IPMASK)) { if (!ip_s) ip_s = make_nick_user_ip(nu_ip, cli_name(cptr), - (cli_user(cptr))->username, cli_ip(cptr)); + (cli_user(cptr))->username, &cli_ip(cptr)); if (match(tmp->value.ban.banstr, ip_s) == 0) break; } diff --git a/ircd/gline.c b/ircd/gline.c index 7201b96..3fd81c9 100644 --- a/ircd/gline.c +++ b/ircd/gline.c @@ -141,43 +141,8 @@ make_gline(char *user, char *host, char *reason, time_t expire, time_t lastmod, else gline->gl_host = NULL; - if (*user != '$' && check_if_ipmask(host)) { /* mark if it's an IP mask */ - int c_class; - char ipname[16]; - int ad[4] = { 0 }; - int bits2 = 0; - char *ch; - int seenwild; - int badmask=0; - - /* Sanity check for dodgy IP masks - * Any mask featuring a digit after a wildcard will - * not behave as expected. */ - for (seenwild=0,ch=host;*ch;ch++) { - if (*ch=='*' || *ch=='?') - seenwild=1; - if (IsDigit(*ch) && seenwild) { - badmask=1; - break; - } - } - - if (badmask) { - /* It's bad - let's make it match 0.0.0.0/32 */ - gline->bits=32; - gline->ipnum.s_addr=0; - } else { - c_class = sscanf(host,"%d.%d.%d.%d/%d", - &ad[0],&ad[1],&ad[2],&ad[3], &bits2); - if (c_class!=5) - gline->bits=c_class*8; - else - gline->bits=bits2; - ircd_snprintf(0, ipname, sizeof(ipname), "%d.%d.%d.%d", ad[0], ad[1], - ad[2], ad[3]); - gline->ipnum.s_addr = inet_addr(ipname); - } - Debug((DEBUG_DEBUG,"IP gline: %08x/%i",gline->ipnum.s_addr,gline->bits)); + if (*user != '$' && ipmask_parse(host, &gline->gl_addr, &gline->gl_bits)) { + Debug((DEBUG_DEBUG,"IP gline: %s/%u", ircd_ntoa(&gline->gl_addr), gline->gl_bits)); gline->gl_flags |= GLINE_IPMASK; } @@ -215,7 +180,7 @@ do_gline(struct Client *cptr, struct Client *sptr, struct Gline *gline) if ((acptr = LocalClientArray[fd])) { if (!cli_user(acptr)) continue; - + if (GlineIsRealName(gline)) { /* Realname Gline */ Debug((DEBUG_DEBUG,"Realname Gline: %s %s",(cli_info(acptr)), gline->gl_user+2)); @@ -223,13 +188,16 @@ do_gline(struct Client *cptr, struct Client *sptr, struct Gline *gline) continue; Debug((DEBUG_DEBUG,"Matched!")); } else { /* Host/IP gline */ - if (cli_user(acptr)->username && + if (cli_user(acptr)->username && match(gline->gl_user, (cli_user(acptr))->username) != 0) - continue; - + continue; + if (GlineIsIpMask(gline)) { - Debug((DEBUG_DEBUG,"IP gline: %08x %08x/%i",(cli_ip(cptr)).s_addr,gline->ipnum.s_addr,gline->bits)); - if (((cli_ip(acptr)).s_addr & NETMASK(gline->bits)) != gline->ipnum.s_addr) +#ifdef DEBUGMODE + char tbuf1[SOCKIPLEN], tbuf2[SOCKIPLEN]; + Debug((DEBUG_DEBUG,"IP gline: %s %s/%u", ircd_ntoa_r(tbuf1, &cli_ip(cptr)), ircd_ntoa_r(tbuf2, &gline->gl_addr), gline->gl_bits)); +#endif + if (!ipmask_check(&cli_ip(cptr), &gline->gl_addr, gline->gl_bits)) continue; } else { @@ -282,17 +250,24 @@ gline_checkmask(char *mask) ++mask; ipmask = strtoul(mask, &mask, 10); - if (*mask || dots != 3 || ipmask > 32 || /* sanity-check to date */ - (flags & (MASK_WILDS | MASK_IP)) != MASK_IP) - return CHECK_REJECTED; /* how strange... */ - - if (ipmask < 32) /* it's a masked address; mark wilds */ - flags |= MASK_WILDS; + /* sanity-check to date */ + if (*mask || (flags & (MASK_WILDS | MASK_IP)) != MASK_IP) + return CHECK_REJECTED; + if (!dots) { + if (ipmask > 128) + return CHECK_REJECTED; + if (ipmask < 128) + flags |= MASK_WILDS; + } else { + if (dots != 3 || ipmask > 3) + return CHECK_REJECTED; + if (ipmask < 32) + flags |= MASK_WILDS; + } flags |= MASK_HALT; /* Halt the ipmask calculation */ - break; /* get out of the loop */ - } else if (!IsDigit(*mask)) { + } else if (!IsIP6Char(*mask)) { flags &= ~MASK_IP; /* not an IP anymore! */ ipmask = 0; } @@ -343,7 +318,7 @@ gline_propagate(struct Client *cptr, struct Client *sptr, struct Gline *gline) return 0; } -int +int gline_add(struct Client *cptr, struct Client *sptr, char *userhost, char *reason, time_t expire, time_t lastmod, unsigned int flags) { @@ -355,28 +330,14 @@ gline_add(struct Client *cptr, struct Client *sptr, char *userhost, assert(0 != userhost); assert(0 != reason); - /* NO_OLD_GLINE allows *@#channel to work correctly */ - if (*userhost == '#' || *userhost == '&' -# ifndef NO_OLD_GLINE - || ((userhost[2] == '#' || userhost[2] == '&') && (userhost[1] == '@')) -# endif /* OLD_GLINE */ - ) { + if (*userhost == '#' || *userhost == '&') { if ((flags & GLINE_LOCAL) && !HasPriv(sptr, PRIV_LOCAL_BADCHAN)) return send_reply(sptr, ERR_NOPRIVILEGES); flags |= GLINE_BADCHAN; -# ifndef NO_OLD_GLINE - if ((userhost[2] == '#' || userhost[2] == '&') && (userhost[1] == '@')) - user = userhost + 2; - else -# endif /* OLD_GLINE */ - user = userhost; + user = userhost; host = 0; - } else if (*userhost == '$' -# ifndef NO_OLD_GLINE - || userhost[2] == '$' -# endif /* OLD_GLINE */ - ) { + } else if (*userhost == '$') { switch (*userhost == '$' ? userhost[1] : userhost[3]) { case 'R': flags |= GLINE_REALNAME; break; default: @@ -593,11 +554,7 @@ gline_find(char *userhost, unsigned int flags) } if ((flags & (GLINE_BADCHAN | GLINE_ANY)) == GLINE_BADCHAN || - *userhost == '#' || *userhost == '&' -#ifndef NO_OLD_GLINE - || userhost[2] == '#' || userhost[2] == '&' -#endif /* NO_OLD_GLINE */ - ) + *userhost == '#' || *userhost == '&') return 0; DupString(t_uh, userhost); @@ -663,14 +620,17 @@ gline_lookup(struct Client *cptr, unsigned int flags) else { if (match(gline->gl_user, (cli_user(cptr))->username) != 0) continue; - + if (GlineIsIpMask(gline)) { - Debug((DEBUG_DEBUG,"IP gline: %08x %08x/%i",(cli_ip(cptr)).s_addr,gline->ipnum.s_addr,gline->bits)); - if (((cli_ip(cptr)).s_addr & NETMASK(gline->bits)) != gline->ipnum.s_addr) +#ifdef DEBUGMODE + char tbuf1[SOCKIPLEN], tbuf2[SOCKIPLEN]; + Debug((DEBUG_DEBUG,"IP gline: %s %s/%u", ircd_ntoa_r(tbuf1, &cli_ip(cptr)), ircd_ntoa_r(tbuf2, &gline->gl_addr), gline->gl_bits)); +#endif + if (!ipmask_check(&cli_ip(cptr), &gline->gl_addr, gline->gl_bits)) continue; } else { - if (match(gline->gl_host, (cli_user(cptr))->realhost) != 0) + if (match(gline->gl_host, (cli_user(cptr))->realhost) != 0) continue; } } @@ -822,7 +782,7 @@ gline_memory_count(size_t *gl_size) { struct Gline *gline; unsigned int gl = 0; - + for (gline = GlobalGlineList; gline; gline = gline->gl_next) { gl++; @@ -833,4 +793,3 @@ gline_memory_count(size_t *gl_size) } return gl; } - diff --git a/ircd/ircd.c b/ircd/ircd.c index 33dbfaf..b8c7cb4 100644 --- a/ircd/ircd.c +++ b/ircd/ircd.c @@ -256,7 +256,7 @@ static void try_connections(struct Event* ev) { Debug((DEBUG_NOTICE, "Connection check at : %s", myctime(CurrentTime))); for (aconf = GlobalConfList; aconf; aconf = aconf->next) { /* Also when already connecting! (update holdtimes) --SRB */ - if (!(aconf->status & CONF_SERVER) || aconf->port == 0 || aconf->hold == 0) + if (!(aconf->status & CONF_SERVER) || aconf->address.port == 0 || aconf->hold == 0) continue; /* Also skip juped servers */ diff --git a/ircd/ircd_auth.c b/ircd/ircd_auth.c index 23a9070..31fc366 100644 --- a/ircd/ircd_auth.c +++ b/ircd/ircd_auth.c @@ -89,8 +89,7 @@ struct IAuth { char i_buffer[BUFSIZE+1]; /* partial unprocessed line from server */ char i_passwd[PASSWDLEN+1]; /* password for connection */ char i_host[HOSTLEN+1]; /* iauth server hostname */ - uint32_t i_addr; /* iauth server ip address */ - unsigned short i_port; /* iauth server port */ + struct irc_sockaddr i_addr; /* iauth server ip address and port */ struct IAuth *i_next; /* next connection in list */ }; @@ -133,7 +132,7 @@ struct IAuth { #define i_passwd(iauth) ((iauth)->i_passwd) #define i_host(iauth) ((iauth)->i_host) #define i_addr(iauth) ((iauth)->i_addr) -#define i_port(iauth) ((iauth)->i_port) +#define i_port(iauth) ((iauth)->i_addr.port) #define i_next(iauth) ((iauth)->i_next) struct IAuthCmd { @@ -182,8 +181,7 @@ struct IAuth *iauth_connect(char *host, unsigned short port, char *passwd, time_ msgq_init(&i_sendQ(iauth)); ircd_strncpy(i_host(iauth), host, HOSTLEN); i_port(iauth) = port; - i_addr(iauth) = INADDR_NONE; - i_next(iauth) = iauth_active; + memset(&i_addr(iauth), 0, sizeof(i_addr(iauth))); iauth_active = iauth; i_reconnect(iauth) = reconnect; iauth_reconnect(iauth); @@ -328,13 +326,10 @@ static void iauth_dns_callback(void *vptr, struct DNSReply *he) struct IAuth *iauth = vptr; if (!he) { sendto_opmask_butone(0, SNO_OLDSNO, "IAuth connection to %s failed: host lookup failed", i_host(iauth)); - } else if (he->h_addrtype != AF_INET) { - sendto_opmask_butone(0, SNO_OLDSNO, "IAuth connection to %s failed: bad host type %d", i_host(iauth), he->h_addrtype); } else { - struct sockaddr_in *sin = (struct sockaddr_in*)&he->addr; - i_addr(iauth) = sin->sin_addr.s_addr; - if (INADDR_NONE == i_addr(iauth)) { - sendto_opmask_butone(0, SNO_OLDSNO, "IAuth connection to %s failed: host came back as INADDR_NONE", i_host(iauth)); + memcpy(&i_addr(iauth).addr, &he->addr, sizeof(i_addr(iauth).addr)); + if (!irc_in_addr_valid(&i_addr(iauth).addr)) { + sendto_opmask_butone(0, SNO_OLDSNO, "IAuth connection to %s failed: host came back as unresolved", i_host(iauth)); return; } iauth_reconnect(iauth); @@ -357,46 +352,25 @@ static void iauth_schedule_reconnect(struct IAuth *iauth) static void iauth_reconnect(struct IAuth *iauth) { - extern struct sockaddr_in VirtualHost; - struct sockaddr_in sin; IOResult result; int fd; - if (INADDR_NONE == i_addr(iauth)) { - i_addr(iauth) = inet_addr(i_host(iauth)); - if (INADDR_NONE == i_addr(iauth)) { - i_query(iauth).vptr = iauth; - i_query(iauth).callback = iauth_dns_callback; - gethost_byname(i_host(iauth), &i_query(iauth)); - return; - } - } - fd = socket(AF_INET, SOCK_STREAM, 0); - if (0 > fd) { - sendto_opmask_butone(0, SNO_OLDSNO, "IAuth reconnect unable to allocate socket: %s", strerror(errno)); + if (!irc_in_addr_valid(&i_addr(iauth).addr) + && !ircd_aton(&i_addr(iauth).addr, i_host(iauth))) { + i_query(iauth).vptr = iauth; + i_query(iauth).callback = iauth_dns_callback; + gethost_byname(i_host(iauth), &i_query(iauth)); return; } - if (feature_bool(FEAT_VIRTUAL_HOST) - && bind(fd, (struct sockaddr*)&VirtualHost, sizeof(VirtualHost)) != 0) { - close(fd); - sendto_opmask_butone(0, SNO_OLDSNO, "IAuth reconnect unable to bind vhost: %s", strerror(errno)); + fd = os_socket((feature_bool(FEAT_VIRTUAL_HOST) ? &VirtualHost : NULL), SOCK_STREAM, "IAuth"); + if (fd < 0) return; - } if (!os_set_sockbufs(fd, SERVER_TCP_WINDOW, SERVER_TCP_WINDOW)) { close(fd); sendto_opmask_butone(0, SNO_OLDSNO, "IAuth reconnect unable to set socket buffers: %s", strerror(errno)); return; } - if (!os_set_nonblocking(fd)) { - close(fd); - sendto_opmask_butone(0, SNO_OLDSNO, "IAuth reconnect unable to make socket non-blocking: %s", strerror(errno)); - return; - } - memset(&sin, 0, sizeof(sin)); - sin.sin_family = AF_INET; - sin.sin_addr.s_addr = i_addr(iauth); - sin.sin_port = htons(i_port(iauth)); - result = os_connect_nonb(fd, &sin); + result = os_connect_nonb(fd, &i_addr(iauth)); if (result == IO_FAILURE) { close(fd); sendto_opmask_butone(0, SNO_OLDSNO, "IAuth reconnect unable to initiate connection: %s", strerror(errno)); diff --git a/ircd/ircd_getaddrinfo.c b/ircd/ircd_getaddrinfo.c deleted file mode 100644 index 3aff6c1..0000000 --- a/ircd/ircd_getaddrinfo.c +++ /dev/null @@ -1,631 +0,0 @@ -/* - * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the project nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - */ - -#include "ircd_addrinfo.h" -#include /* for offsetof() */ -#include /* for free() */ -#include /* for memset() */ -#include /* for close() */ -#include /* for inet_aton(), inet_pton() */ -#include /* for errno */ - -#ifndef AI_MASK -#define AI_MASK (AI_NUMERICHOST | AI_PASSIVE) -#endif - -/* $Id$ */ - -static const char in_addrany[] = { 0, 0, 0, 0 }; -static const char in_loopback[] = { 127, 0, 0, 1 }; -static const char in6_addrany[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 -}; -static const char in6_loopback[] = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 -}; - -static const struct afd { - int a_af; - int a_addrlen; - int a_socklen; - int a_off; - const char *a_addrany; - const char *a_loopback; - int a_scoped; -} afdl [] = { -#define N_INET6 0 -#ifdef IPV6 - {PF_INET6, sizeof(struct in6_addr), - sizeof(struct sockaddr_in6), - offsetof(struct sockaddr_in6, sin6_addr), - in6_addrany, in6_loopback, 1}, -#endif -#define N_INET 1 - {PF_INET, sizeof(struct in_addr), - sizeof(struct sockaddr_in), - offsetof(struct sockaddr_in, sin_addr), - in_addrany, in_loopback, 0}, - {0, 0, 0, 0, NULL, NULL, 0}, -}; - -struct explore { - int e_af; - int e_socktype; - int e_protocol; - const char *e_protostr; - int e_wild; -#define WILD_AF(ex) ((ex)->e_wild & 0x01) -#define WILD_SOCKTYPE(ex) ((ex)->e_wild & 0x02) -#define WILD_PROTOCOL(ex) ((ex)->e_wild & 0x04) -}; - -#define ANY 0 - -static const struct explore explore[] = { -#ifdef IPV6 - { PF_INET6, SOCK_DGRAM, IPPROTO_UDP, "udp", 0x07 }, - { PF_INET6, SOCK_STREAM, IPPROTO_TCP, "tcp", 0x07 }, - { PF_INET6, SOCK_RAW, ANY, NULL, 0x05 }, -#endif - { PF_INET, SOCK_DGRAM, IPPROTO_UDP, "udp", 0x07 }, - { PF_INET, SOCK_STREAM, IPPROTO_TCP, "tcp", 0x07 }, - { PF_INET, SOCK_RAW, ANY, NULL, 0x05 }, - { PF_UNSPEC, SOCK_DGRAM, IPPROTO_UDP, "udp", 0x07 }, - { PF_UNSPEC, SOCK_STREAM, IPPROTO_TCP, "tcp", 0x07 }, - { PF_UNSPEC, SOCK_RAW, ANY, NULL, 0x05 }, - { -1, 0, 0, NULL, 0 }, -}; - -#define PTON_MAX 16 - -static int str_isnumber(const char *); -static int explore_null(const struct addrinfo *, - const char *, struct addrinfo **); -static int explore_numeric(const struct addrinfo *, const char *, - const char *, struct addrinfo **); -static struct addrinfo *get_ai(const struct addrinfo *, - const struct afd *, const char *); -static int get_portmatch(const struct addrinfo *, const char *); -static int get_port(struct addrinfo *, const char *, int); -static const struct afd *find_afd(int); -#if 0 -/* We will need this should we ever want gai_strerror(). - * Note though that GNU libc doesn't define EAI_BADHINTS. */ -static char *ai_errlist[] = { - "Success", - "Address family for hostname not supported", /* EAI_ADDRFAMILY */ - "Temporary failure in name resolution", /* EAI_AGAIN */ - "Invalid value for ai_flags", /* EAI_BADFLAGS */ - "Non-recoverable failure in name resolution", /* EAI_FAIL */ - "ai_family not supported", /* EAI_FAMILY */ - "Memory allocation failure", /* EAI_MEMORY */ - "No address associated with hostname", /* EAI_NODATA */ - "hostname nor servname provided, or not known", /* EAI_NONAME */ - "servname not supported for ai_socktype", /* EAI_SERVICE */ - "ai_socktype not supported", /* EAI_SOCKTYPE */ - "System error returned in errno", /* EAI_SYSTEM */ - "Invalid value for hints", /* EAI_BADHINTS */ - "Resolved protocol is unknown", /* EAI_PROTOCOL */ - "Unknown error", /* EAI_MAX */ -}; -#endif -/* XXX macros that make external reference is BAD. */ - -#define GET_AI(ai, afd, addr) \ -do { \ - /* external reference: pai, error, and label free */ \ - (ai) = get_ai(pai, (afd), (addr)); \ - if ((ai) == NULL) { \ - error = EAI_MEMORY; \ - goto free; \ - } \ -} while (/*CONSTCOND*/0) - -#define GET_PORT(ai, serv) \ -do { \ - /* external reference: error and label free */ \ - error = get_port((ai), (serv), 0); \ - if (error != 0) \ - goto free; \ -} while (/*CONSTCOND*/0) - -#define ERR(err) \ -do { \ - /* external reference: error, and label bad */ \ - error = (err); \ - goto bad; \ - /*NOTREACHED*/ \ -} while (/*CONSTCOND*/0) - -#define MATCH_FAMILY(x, y, w) \ - ((x) == (y) || (/*CONSTCOND*/(w) && ((x) == PF_UNSPEC || (y) == PF_UNSPEC))) -#define MATCH(x, y, w) \ - ((x) == (y) || (/*CONSTCOND*/(w) && ((x) == ANY || (y) == ANY))) - -#if 0 -/* We will need this should we ever want gai_strerror() */ -char * -irc_gai_strerror(int ecode) -{ - if (ecode < 0 || ecode > EAI_MAX) - ecode = EAI_MAX; - return ai_errlist[ecode]; -} -#endif - -void -irc_freeaddrinfo(struct addrinfo *ai) -{ - struct addrinfo *next; - - do { - next = ai->ai_next; - if (ai->ai_canonname) - free(ai->ai_canonname); - /* no need to free(ai->ai_addr) */ - free(ai); - ai = next; - } while (ai); -} - -static int -str_isnumber(const char *p) -{ - char *ep; - - if (*p == '\0') - return 0; - ep = NULL; - errno = 0; - (void)strtoul(p, &ep, 10); - if (errno == 0 && ep && *ep == '\0') - return 1; - else - return 0; -} - -int -irc_getaddrinfo(const char *hostname, const char *servname, - const struct addrinfo *hints, struct addrinfo **res) -{ - struct addrinfo sentinel; - struct addrinfo *cur; - int error = 0; - struct addrinfo ai; - struct addrinfo ai0; - struct addrinfo *pai; - const struct explore *ex; - - memset(&sentinel, 0, sizeof(sentinel)); - cur = &sentinel; - pai = &ai; - pai->ai_flags = 0; - pai->ai_family = PF_UNSPEC; - pai->ai_socktype = ANY; - pai->ai_protocol = ANY; - pai->ai_addrlen = 0; - pai->ai_canonname = NULL; - pai->ai_addr = NULL; - pai->ai_next = NULL; - - if (hostname == NULL && servname == NULL) - return EAI_NONAME; - if (hints) { - /* error check for hints */ - if (hints->ai_addrlen || hints->ai_canonname || - hints->ai_addr || hints->ai_next) - { -#ifdef EAI_BADHINTS - ERR(EAI_BADHINTS); /* xxx */ -#else - errno = EINVAL; - ERR(EAI_SYSTEM); -#endif - } - if (hints->ai_flags & ~AI_MASK) - ERR(EAI_BADFLAGS); - switch (hints->ai_family) { - case PF_UNSPEC: - case PF_INET: -#ifdef IPV6 - case PF_INET6: -#endif - break; - default: - ERR(EAI_FAMILY); - } - memcpy(pai, hints, sizeof(*pai)); - - /* - * if both socktype/protocol are specified, check if they - * are meaningful combination. - */ - if (pai->ai_socktype != ANY && pai->ai_protocol != ANY) { - for (ex = explore; ex->e_af >= 0; ex++) { - if (pai->ai_family != ex->e_af) - continue; - if (ex->e_socktype == ANY) - continue; - if (ex->e_protocol == ANY) - continue; - if (pai->ai_socktype == ex->e_socktype && - pai->ai_protocol != ex->e_protocol) { -#ifdef EAI_BADHINTS - ERR(EAI_BADHINTS); /* xxx */ -#else - errno = EINVAL; - ERR(EAI_SYSTEM); -#endif - } - } - } - } - - /* - * check for special cases. (1) numeric servname is disallowed if - * socktype/protocol are left unspecified. (2) servname is disallowed - * for raw and other inet{,6} sockets. - */ - if (MATCH_FAMILY(pai->ai_family, PF_INET, 1) -#ifdef IPV6 - || MATCH_FAMILY(pai->ai_family, PF_INET6, 1) -#endif - ) { - ai0 = *pai; /* backup *pai */ - - if (pai->ai_family == PF_UNSPEC) { -#ifdef IPV6 - pai->ai_family = PF_INET6; -#else - pai->ai_family = PF_INET; -#endif - } - error = get_portmatch(pai, servname); - if (error) - ERR(error); - - *pai = ai0; - } - - ai0 = *pai; - - /* NULL hostname, or numeric hostname */ - for (ex = explore; ex->e_af >= 0; ex++) { - *pai = ai0; - - /* PF_UNSPEC entries are prepared for DNS queries only */ - if (ex->e_af == PF_UNSPEC) - continue; - - if (!MATCH_FAMILY(pai->ai_family, ex->e_af, WILD_AF(ex))) - continue; - if (!MATCH(pai->ai_socktype, ex->e_socktype, WILD_SOCKTYPE(ex))) - continue; - if (!MATCH(pai->ai_protocol, ex->e_protocol, WILD_PROTOCOL(ex))) - continue; - - if (pai->ai_family == PF_UNSPEC) - pai->ai_family = ex->e_af; - if (pai->ai_socktype == ANY && ex->e_socktype != ANY) - pai->ai_socktype = ex->e_socktype; - if (pai->ai_protocol == ANY && ex->e_protocol != ANY) - pai->ai_protocol = ex->e_protocol; - - if (hostname == NULL) - error = explore_null(pai, servname, &cur->ai_next); - else - error = explore_numeric(pai, hostname, servname, &cur->ai_next); - - if (error) - goto free; - - while (cur && cur->ai_next) - cur = cur->ai_next; - } - - /* - * XXX - * If numeric representation of AF1 can be interpreted as FQDN - * representation of AF2, we need to think again about the code below. - */ - if (sentinel.ai_next) - goto good; - - if (pai->ai_flags & AI_NUMERICHOST) - ERR(EAI_NONAME); - if (hostname == NULL) - ERR(EAI_NODATA); - - /* XXX */ - if (sentinel.ai_next) - error = 0; - - if (error) - goto free; - if (error == 0) { - if (sentinel.ai_next) { - good: - *res = sentinel.ai_next; - return 0; - } else - error = EAI_FAIL; - } - free: - bad: - if (sentinel.ai_next) - irc_freeaddrinfo(sentinel.ai_next); - *res = NULL; - return error; -} - -/* - * hostname == NULL. - * passive socket -> anyaddr (0.0.0.0 or ::) - * non-passive socket -> localhost (127.0.0.1 or ::1) - */ -static int -explore_null(const struct addrinfo *pai, const char *servname, struct addrinfo **res) -{ - int s; - const struct afd *afd; - struct addrinfo *cur; - struct addrinfo sentinel; - int error; - - *res = NULL; - sentinel.ai_next = NULL; - cur = &sentinel; - - /* - * filter out AFs that are not supported by the kernel - * XXX errno? - */ - s = socket(pai->ai_family, SOCK_DGRAM, 0); - if (s < 0) { - if (errno != EMFILE) - return 0; - } else - close(s); - - /* - * if the servname does not match socktype/protocol, ignore it. - */ - if (get_portmatch(pai, servname) != 0) - return 0; - - afd = find_afd(pai->ai_family); - if (afd == NULL) - return 0; - - if (pai->ai_flags & AI_PASSIVE) { - GET_AI(cur->ai_next, afd, afd->a_addrany); - GET_PORT(cur->ai_next, servname); - } else { - GET_AI(cur->ai_next, afd, afd->a_loopback); - GET_PORT(cur->ai_next, servname); - } - cur = cur->ai_next; - - *res = sentinel.ai_next; - return 0; - -free: - if (sentinel.ai_next) - irc_freeaddrinfo(sentinel.ai_next); - return error; -} - -/* - * numeric hostname - */ -static int -explore_numeric(const struct addrinfo *pai, const char *hostname, - const char *servname, struct addrinfo **res) -{ - const struct afd *afd; - struct addrinfo *cur; - struct addrinfo sentinel; - int error; - char pton[PTON_MAX]; - - *res = NULL; - sentinel.ai_next = NULL; - cur = &sentinel; - - /* - * if the servname does not match socktype/protocol, ignore it. - */ - if (get_portmatch(pai, servname) != 0) - return 0; - - afd = find_afd(pai->ai_family); - if (afd == NULL) - return 0; - - switch (afd->a_af) { -#if 1 /*X/Open spec*/ - case AF_INET: - if (inet_aton(hostname, (struct in_addr *)pton) == 1) { - if (pai->ai_family == afd->a_af || - pai->ai_family == PF_UNSPEC /*?*/) { - GET_AI(cur->ai_next, afd, pton); - GET_PORT(cur->ai_next, servname); - while (cur && cur->ai_next) - cur = cur->ai_next; - } else - ERR(EAI_FAMILY); /*xxx*/ - } - break; -#endif - default: - if (inet_pton(afd->a_af, hostname, pton) == 1) { - if (pai->ai_family == afd->a_af || - pai->ai_family == PF_UNSPEC /*?*/) { - GET_AI(cur->ai_next, afd, pton); - GET_PORT(cur->ai_next, servname); - while (cur && cur->ai_next) - cur = cur->ai_next; - } else - ERR(EAI_FAMILY); /* XXX */ - } - break; - } - - *res = sentinel.ai_next; - return 0; - -free: -bad: - if (sentinel.ai_next) - irc_freeaddrinfo(sentinel.ai_next); - return error; -} - -static struct addrinfo * -get_ai(const struct addrinfo *pai, const struct afd *afd, const char *addr) -{ - char *p; - struct addrinfo *ai; - - ai = (struct addrinfo *)malloc(sizeof(struct addrinfo) - + (afd->a_socklen)); - if (ai == NULL) - return NULL; - - memcpy(ai, pai, sizeof(struct addrinfo)); - ai->ai_addr = (struct sockaddr *)(void *)(ai + 1); - memset(ai->ai_addr, 0, (size_t)afd->a_socklen); - ai->ai_addrlen = afd->a_socklen; - ai->ai_addr->sa_family = ai->ai_family = afd->a_af; - p = (char *)(void *)(ai->ai_addr); - memcpy(p + afd->a_off, addr, (size_t)afd->a_addrlen); - return ai; -} - -static int -get_portmatch(const struct addrinfo *ai, const char *servname) -{ - /* get_port does not touch first argument. when matchonly == 1. */ - /* LINTED const cast */ - return(get_port((struct addrinfo *)ai, servname, 1)); -} - -static int -get_port(struct addrinfo *ai, const char *servname, int matchonly) -{ - const char *proto; - struct servent *sp; - int port; - int allownumeric; - - if (servname == NULL) - return 0; - switch (ai->ai_family) { - case AF_INET: -#ifdef AF_INET6 - case AF_INET6: -#endif - break; - default: - return 0; - } - - switch (ai->ai_socktype) { - case SOCK_RAW: - return EAI_SERVICE; - case SOCK_DGRAM: - case SOCK_STREAM: - allownumeric = 1; - break; - case ANY: - allownumeric = 0; - break; - default: - return EAI_SOCKTYPE; - } - - if (str_isnumber(servname)) { - if (!allownumeric) - return EAI_SERVICE; - port = atoi(servname); - if (port < 0 || port > 65535) - return EAI_SERVICE; - port = htons(port); - } else { - switch (ai->ai_socktype) { - case SOCK_DGRAM: - proto = "udp"; - break; - case SOCK_STREAM: - proto = "tcp"; - break; - default: - proto = NULL; - break; - } - - if ((sp = getservbyname(servname, proto)) == NULL) - return EAI_SERVICE; - port = sp->s_port; - } - - if (!matchonly) { - switch (ai->ai_family) { - case AF_INET: - ((struct sockaddr_in *)(void *) - ai->ai_addr)->sin_port = port; - break; -#ifdef IPV6 - case AF_INET6: - ((struct sockaddr_in6 *)(void *) - ai->ai_addr)->sin6_port = port; - break; -#endif - } - } - - return 0; -} - -static const struct afd * -find_afd(int af) -{ - const struct afd *afd; - - if (af == PF_UNSPEC) - return(NULL); - - for (afd = afdl; afd->a_af; afd++) - { - if (afd->a_af == af) - return(afd); - } - - return(NULL); -} diff --git a/ircd/ircd_getnameinfo.c b/ircd/ircd_getnameinfo.c deleted file mode 100644 index 2a514a1..0000000 --- a/ircd/ircd_getnameinfo.c +++ /dev/null @@ -1,243 +0,0 @@ -/* - * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the project nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - */ - -/* - * Issues to be discussed: - * - Thread safe-ness must be checked - * - RFC2553 says that we should raise error on short buffer. X/Open says - * we need to truncate the result. We obey RFC2553 (and X/Open should be - * modified). ipngwg rough consensus seems to follow RFC2553. - * - What is "local" in NI_FQDN? - * - NI_NAMEREQD and NI_NUMERICHOST conflict with each other. - * - (KAME extension) always attach textual scopeid (fe80::1%lo0), if - * sin6_scope_id is filled - standardization status? - * XXX breaks backward compat for code that expects no scopeid. - * beware on merge. - */ - -#include "ircd_addrinfo.h" -#include "ircd_string.h" -#include /* for offsetof() */ -#include /* for snprintf() */ -#include /* for strlen() */ -#include /* for inet_aton(), inet_pton() */ - -/* $Id$ */ - -static const struct afd { - int a_af; - int a_addrlen; - socklen_t a_socklen; - int a_off; -} afdl [] = { -#ifdef IPV6 - {PF_INET6, sizeof(struct in6_addr), sizeof(struct sockaddr_in6), - offsetof(struct sockaddr_in6, sin6_addr)}, -#endif - {PF_INET, sizeof(struct in_addr), sizeof(struct sockaddr_in), - offsetof(struct sockaddr_in, sin_addr)}, - {0, 0, 0, 0}, -}; - -struct sockinet -{ - unsigned char si_len; - unsigned char si_family; - unsigned short si_port; -}; - -#ifdef IPV6 -static int ip6_parsenumeric(const struct sockaddr *, const char *, char *, - size_t, int); -#endif - -int -irc_getnameinfo(const struct sockaddr *sa, socklen_t salen, char *host, - size_t hostlen, char *serv, size_t servlen, int flags) -{ - const struct afd *afd; - struct servent *sp; - unsigned short port; - int family, i; - const char *addr; - uint32_t v4a; - char numserv[512]; - char numaddr[512]; - - if (sa == NULL) - return EAI_FAIL; - -/* if (sa->sa_len != salen) - return EAI_FAIL; -*/ - family = sa->sa_family; - for (i = 0; afdl[i].a_af; i++) - if (afdl[i].a_af == family) { - afd = &afdl[i]; - goto found; - } - return EAI_FAMILY; - - found: - if (salen != afd->a_socklen) - return EAI_FAIL; - - /* network byte order */ - port = ((const struct sockinet *)sa)->si_port; - addr = (const char *)sa + afd->a_off; - - if (serv == NULL || servlen == 0) { - /* - * do nothing in this case. - * in case you are wondering if "&&" is more correct than - * "||" here: rfc2553bis-03 says that serv == NULL OR - * servlen == 0 means that the caller does not want the result. - */ - } else { - if (flags & NI_NUMERICSERV) - sp = NULL; - else { - sp = getservbyport(port, - (flags & NI_DGRAM) ? "udp" : "tcp"); - } - if (sp) { - if (strlen(sp->s_name) + 1 > servlen) - return EAI_MEMORY; - ircd_strncpy(serv, sp->s_name, servlen); - } else { - snprintf(numserv, sizeof(numserv), "%u", ntohs(port)); - if (strlen(numserv) + 1 > servlen) - return EAI_MEMORY; - ircd_strncpy(serv, numserv, servlen); - } - } - - switch (sa->sa_family) { - case AF_INET: - v4a = - ntohl(((const struct sockaddr_in *)sa)->sin_addr.s_addr); - if (IN_MULTICAST(v4a) || IN_EXPERIMENTAL(v4a)) - flags |= NI_NUMERICHOST; - v4a >>= IN_CLASSA_NSHIFT; - if (v4a == 0) - flags |= NI_NUMERICHOST; - break; -#ifdef IPV6 - case AF_INET6: - { - const struct sockaddr_in6 *sin6; - sin6 = (const struct sockaddr_in6 *)sa; - switch (sin6->sin6_addr.s6_addr[0]) { - case 0x00: - if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) - ; - else if (IN6_IS_ADDR_LOOPBACK(&sin6->sin6_addr)) - ; - else - flags |= NI_NUMERICHOST; - break; - default: - if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) { - flags |= NI_NUMERICHOST; - } - else if (IN6_IS_ADDR_MULTICAST(&sin6->sin6_addr)) - flags |= NI_NUMERICHOST; - break; - } - } - break; -#endif - } - if (host == NULL || hostlen == 0) { - /* - * do nothing in this case. - * in case you are wondering if "&&" is more correct than - * "||" here: rfc2553bis-03 says that host == NULL or - * hostlen == 0 means that the caller does not want the result. - */ - } else if (flags & NI_NUMERICHOST) { - size_t numaddrlen; - - /* NUMERICHOST and NAMEREQD conflicts with each other */ - if (flags & NI_NAMEREQD) - return EAI_NONAME; - - switch(afd->a_af) { -#ifdef IPV6 - case AF_INET6: - { - int error; - - if ((error = ip6_parsenumeric(sa, addr, host, - hostlen, flags)) != 0) - return(error); - break; - } -#endif - default: - if (inet_ntop(afd->a_af, addr, numaddr, sizeof(numaddr)) - == NULL) - return EAI_SYSTEM; - numaddrlen = strlen(numaddr); - if (numaddrlen + 1 > hostlen) /* don't forget terminator */ - return EAI_MEMORY; - ircd_strncpy(host, numaddr, hostlen); - break; - } - } - return(0); -} - -#ifdef IPV6 -static int -ip6_parsenumeric(const struct sockaddr *sa, const char *addr, - char *host, size_t hostlen, int flags) -{ - size_t numaddrlen; - char numaddr[512]; - - if (inet_ntop(AF_INET6, addr, numaddr, sizeof(numaddr)) == NULL) - return(EAI_SYSTEM); - - numaddrlen = strlen(numaddr); - - if (numaddrlen + 1 > hostlen) /* don't forget terminator */ - return(EAI_MEMORY); - - if (*numaddr == ':') - { - *host = '0'; - ircd_strncpy(host+1, numaddr, hostlen-1); - } - else - ircd_strncpy(host, numaddr, hostlen); - - return(0); -} -#endif diff --git a/ircd/ircd_lexer.l b/ircd/ircd_lexer.l index c8943b4..458e571 100644 --- a/ircd/ircd_lexer.l +++ b/ircd/ircd_lexer.l @@ -23,6 +23,7 @@ %{ #include #include +#include #include "config.h" #include "ircd.h" #include "ircd_string.h" @@ -42,6 +43,7 @@ static struct lexer_token { TOKEN(CONTACT), TOKEN(CLASS), TOKEN(PINGFREQ), + TOKEN(CONNECT), TOKEN(CONNECTFREQ), TOKEN(MAXLINKS), TOKEN(SENDQ), diff --git a/ircd/ircd_parser.y b/ircd/ircd_parser.y index b3ce75b..e1a0ace 100644 --- a/ircd/ircd_parser.y +++ b/ircd/ircd_parser.y @@ -295,9 +295,7 @@ generaldesc: DESCRIPTION '=' QSTRING ';' generalvhost: VHOST '=' QSTRING ';' { - if (INADDR_NONE == - (localConf.vhost_address.s_addr = inet_addr(yylval.text))) - localConf.vhost_address.s_addr = INADDR_ANY; + ircd_aton(&localConf.vhost_address, yylval.text); }; adminblock: ADMIN '{' adminitems '}' @@ -389,20 +387,18 @@ connectblock: CONNECT port = 0; } '{' connectitems '}' { - if (name != NULL && pass != NULL && host != NULL && c_class != NULL && - /*ccount < MAXCONFLINKS &&*/ !strchr(host, '*') && - !strchr(host, '?')) + if (name != NULL && pass != NULL && host != NULL && c_class != NULL + && !strchr(host, '*') && !strchr(host, '?')) { aconf = make_conf(); aconf->status = CONF_SERVER; aconf->name = name; aconf->passwd = pass; aconf->conn_class = c_class; - aconf->port = port; + aconf->address.port = port; aconf->status = CONF_SERVER; aconf->host = host; aconf->next = GlobalConfList; - aconf->ipnum.s_addr = INADDR_NONE; lookup_confhost(aconf); GlobalConfList = aconf; } @@ -768,25 +764,7 @@ killuhost: HOST '=' QSTRING ';' } DupString(dconf->hostmask, h); DupString(dconf->usermask, u); - if (strchr(yylval.text, '.')) - { - int c_class; - char ipname[16]; - int ad[4] = { 0 }; - int bits2 = 0; - dconf->flags |= DENY_FLAGS_IP; - c_class = sscanf(dconf->hostmask, "%d.%d.%d.%d/%d", - &ad[0], &ad[1], &ad[2], &ad[3], &bits2); - if (c_class != 5) { - dconf->bits = c_class * 8; - } - else { - dconf->bits = bits2; - } - ircd_snprintf(0, ipname, sizeof(ipname), "%d.%d.%d.%d", ad[0], ad[1], - ad[2], ad[3]); - dconf->address = inet_addr(ipname); - } + ipmask_parse(dconf->hostmask, &dconf->address, &dconf->bits); }; killreal: REAL '=' QSTRING ';' diff --git a/ircd/ircd_res.c b/ircd/ircd_res.c index 2843fe2..57a50e4 100644 --- a/ircd/ircd_res.c +++ b/ircd/ircd_res.c @@ -30,12 +30,12 @@ #include "numeric.h" #include "fileio.h" /* for fbopen / fbclose / fbputs */ #include "s_bsd.h" +#include "s_debug.h" #include "s_stats.h" #include "send.h" #include "sys.h" #include "res.h" #include "ircd_reslib.h" -#include "ircd_addrinfo.h" #include #include @@ -70,9 +70,7 @@ typedef enum REQ_IDLE, /* We're doing not much at all */ REQ_PTR, /* Looking up a PTR */ REQ_A, /* Looking up an A, possibly because AAAA failed */ -#ifdef IPV6 REQ_AAAA, /* Looking up an AAAA */ -#endif REQ_CNAME, /* We got a CNAME in response, we better get a real answer next */ REQ_INT /* ip6.arpa failed, falling back to ip6.int */ } request_state; @@ -83,7 +81,7 @@ struct dlink struct dlink *next; }; -struct reslist +struct reslist { struct dlink node; int id; @@ -96,7 +94,7 @@ struct reslist char resend; /* send flag. 0 == dont resend */ time_t sentat; time_t timeout; - struct irc_ssaddr addr; + struct irc_in_addr addr; char *name; struct DNSQuery query; /* query callback for this request */ }; @@ -108,7 +106,7 @@ static struct reslist *make_request(const struct DNSQuery *query); static void do_query_name(const struct DNSQuery *query, const char* name, struct reslist *request, int); static void do_query_number(const struct DNSQuery *query, - const struct irc_ssaddr *, + const struct irc_in_addr *, struct reslist *request); static void query_name(const char *name, int query_class, int query_type, struct reslist *request); @@ -120,7 +118,7 @@ static struct DNSReply *make_dnsreply(struct reslist *request); static void res_readreply(struct Event *ev); static void timeout_resolver(struct Event *notused); -extern struct irc_ssaddr irc_nsaddr_list[IRCD_MAXNS]; +extern struct irc_sockaddr irc_nsaddr_list[IRCD_MAXNS]; extern int irc_nscount; extern char irc_domain[HOSTLEN]; @@ -136,52 +134,14 @@ extern char irc_domain[HOSTLEN]; * revised for ircd, cryogen(stu) may03 */ static int -res_ourserver(const struct irc_ssaddr *inp) +res_ourserver(const struct irc_sockaddr *inp) { -#ifdef IPV6 - struct sockaddr_in6 *v6; - struct sockaddr_in6 *v6in = (struct sockaddr_in6 *)inp; -#endif - struct sockaddr_in *v4; - struct sockaddr_in *v4in = (struct sockaddr_in *)inp; int ns; for (ns = 0; ns < irc_nscount; ns++) - { - const struct irc_ssaddr *srv = &irc_nsaddr_list[ns]; -#ifdef IPV6 - v6 = (struct sockaddr_in6 *)srv; -#endif - v4 = (struct sockaddr_in *)srv; - - /* could probably just memcmp(srv, inp, srv.ss_len) here - * but we'll air on the side of caution - stu - * - */ - switch (srv->ss.ss_family) - { -#ifdef IPV6 - case AF_INET6: - if (srv->ss.ss_family == inp->ss.ss_family) - if (v6->sin6_port == v6in->sin6_port) - if ((memcmp(&v6->sin6_addr.s6_addr, &v6in->sin6_addr.s6_addr, - sizeof(struct in6_addr)) == 0) || - (memcmp(&v6->sin6_addr.s6_addr, &in6addr_any, - sizeof(struct in6_addr)) == 0)) - return(1); - break; -#endif - case AF_INET: - if (srv->ss.ss_family == inp->ss.ss_family) - if (v4->sin_port == v4in->sin_port) - if ((v4->sin_addr.s_addr == INADDR_ANY) || - (v4->sin_addr.s_addr == v4in->sin_addr.s_addr)) - return(1); - break; - default: - break; - } - } + if (!irc_in_addr_cmp(&inp->addr, &irc_nsaddr_list[ns].addr) + && inp->port == irc_nsaddr_list[ns].port) + return 1; return(0); } @@ -196,16 +156,15 @@ start_resolver(void) irc_res_init(); if (!request_list.next) - request_list.next = request_list.prev = &request_list; + request_list.next = request_list.prev = &request_list; if (!s_active(&res_socket)) { int fd; - fd = socket(irc_nsaddr_list[0].ss.ss_family, SOCK_DGRAM, 0); - if (fd < 0) {} /* TODO: bail on socket() failure */ - if (!os_set_nonblocking(fd)) {} /* TODO: bail on failure */ + fd = os_socket(NULL, SOCK_DGRAM, "Resolver UDP socket"); + if (fd < 0) return; if (!socket_add(&res_socket, res_readreply, NULL, SS_DATAGRAM, - SOCK_EVENT_READABLE, fd)) {} /* TODO: bail on socket_add() failure */ + SOCK_EVENT_READABLE, fd)) return; timer_init(&res_timeout); timer_add(&res_timeout, timeout_resolver, NULL, TT_PERIODIC, 1); } @@ -338,6 +297,7 @@ timeout_query_list(time_t now) { if (--request->retries <= 0) { + Debug((DEBUG_DNS, "Request %p out of retries; destroying", request)); (*request->query.callback)(request->query.vptr, 0); rem_request(request); continue; @@ -382,8 +342,10 @@ delete_resolver_queries(const void *vptr) { next_ptr = ptr->next; request = (struct reslist*)ptr; - if (vptr == request->query.vptr) + if (vptr == request->query.vptr) { + Debug((DEBUG_DNS, "Removing request %p with vptr %p", request, vptr)); rem_request(request); + } } } @@ -408,12 +370,8 @@ send_res_msg(const char *msg, int len, int rcount) max_queries = 1; for (i = 0; i < max_queries; i++) - { - if (sendto(s_fd(&res_socket), msg, len, 0, - (struct sockaddr*)&(irc_nsaddr_list[i]), - irc_nsaddr_list[i].ss_len) == len) + if (os_sendto_nonb(s_fd(&res_socket), msg, len, NULL, 0, &irc_nsaddr_list[i]) == IO_SUCCESS) ++sent; - } return(sent); } @@ -431,10 +389,13 @@ find_id(int id) { request = (struct reslist*)ptr; - if (request->id == id) + if (request->id == id) { + Debug((DEBUG_DNS, "find_id(%d) -> %p", id, request)); return(request); + } } + Debug((DEBUG_DNS, "find_id(%d) -> NULL", id, request)); return(NULL); } @@ -462,27 +423,11 @@ gethost_byname(const char *name, const struct DNSQuery *query) * gethost_byaddr - get host name from address */ void -gethost_byaddr(const struct irc_ssaddr *addr, const struct DNSQuery *query) +gethost_byaddr(const struct irc_in_addr *addr, const struct DNSQuery *query) { do_query_number(query, addr, NULL); } -/* - * gethost_byinaddr - kludgy hack for IPv4-only compatibility - */ -void -gethost_byinaddr(const struct in_addr *addr, const struct DNSQuery *query) -{ - struct irc_ssaddr new_addr; - struct sockaddr_in *sin; - memset(&new_addr, 0, sizeof(new_addr)); - sin = (struct sockaddr_in*)&new_addr.ss; - sin->sin_family = AF_INET; - memcpy(&sin->sin_addr, addr, sizeof(sin->sin_addr)); - new_addr.ss_len = sizeof(*sin); - gethost_byaddr(&new_addr, query); -} - /* * do_query_name - nameserver lookup name */ @@ -510,6 +455,7 @@ do_query_name(const struct DNSQuery *query, const char *name, } request->type = type; + Debug((DEBUG_DNS, "Requesting DNS %s %s as %p", (request->state == REQ_AAAA ? "AAAA" : "A"), host_name, request)); query_name(host_name, C_IN, type, request); } @@ -517,35 +463,29 @@ do_query_name(const struct DNSQuery *query, const char *name, * do_query_number - Use this to do reverse IP# lookups. */ static void -do_query_number(const struct DNSQuery *query, const struct irc_ssaddr *addr, +do_query_number(const struct DNSQuery *query, const struct irc_in_addr *addr, struct reslist *request) { char ipbuf[128]; const unsigned char *cp; -#ifdef IPV6 - const char *intarpa; -#endif - if (addr->ss.ss_family == AF_INET) - { - struct sockaddr_in *v4 = (struct sockaddr_in *)addr; - cp = (const unsigned char*)&v4->sin_addr.s_addr; - ircd_snprintf(NULL, ipbuf, sizeof(ipbuf), - "%u.%u.%u.%u.in-addr.arpa.", + if (irc_in_addr_is_ipv4(addr)) + { + cp = (const unsigned char*)&addr->in6_16[6]; + ircd_snprintf(NULL, ipbuf, sizeof(ipbuf), "%u.%u.%u.%u.in-addr.arpa.", (unsigned int)(cp[3]), (unsigned int)(cp[2]), (unsigned int)(cp[1]), (unsigned int)(cp[0])); } -#ifdef IPV6 - else if (addr->ss.ss_family == AF_INET6) + else { - struct sockaddr_in6 *v6 = (struct sockaddr_in6 *)addr; - cp = (const unsigned char *)&v6->sin6_addr.s6_addr; + const char *intarpa; if (request != NULL && request->state == REQ_INT) intarpa = "int"; else intarpa = "arpa"; + cp = (const unsigned char *)&addr->in6_16[0]; ircd_snprintf(NULL, ipbuf, sizeof(ipbuf), "%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x." "%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.ip6.%s.", @@ -566,15 +506,14 @@ do_query_number(const struct DNSQuery *query, const struct irc_ssaddr *addr, (unsigned int)(cp[1]&0xf), (unsigned int)(cp[1]>>4), (unsigned int)(cp[0]&0xf), (unsigned int)(cp[0]>>4), intarpa); } -#endif if (request == NULL) { request = make_request(query); request->type = T_PTR; - memcpy(&request->addr, addr, sizeof(struct irc_ssaddr)); + memcpy(&request->addr, addr, sizeof(request->addr)); request->name = (char *)MyMalloc(HOSTLEN + 1); } - + Debug((DEBUG_DNS, "Requesting DNS PTR %s as %p", ipbuf, request)); query_name(ipbuf, C_IN, T_PTR, request); } @@ -590,7 +529,7 @@ query_name(const char *name, int query_class, int type, memset(buf, 0, sizeof(buf)); - if ((request_len = irc_res_mkquery(name, query_class, type, + if ((request_len = irc_res_mkquery(name, query_class, type, (unsigned char *)buf, sizeof(buf))) > 0) { HEADER *header = (HEADER *)buf; @@ -639,12 +578,10 @@ resend_query(struct reslist *request) case T_A: do_query_name(NULL, request->name, request, request->type); break; -#ifdef IPV6 case T_AAAA: /* didnt work, try A */ if (request->state == REQ_AAAA) do_query_name(NULL, request->name, request, T_A); -#endif default: break; } @@ -662,10 +599,7 @@ proc_answer(struct reslist *request, HEADER* header, char* buf, char* eob) int type; /* answer type */ int n; /* temp count */ int rd_length; - struct sockaddr_in *v4; /* conversion */ -#ifdef IPV6 - struct sockaddr_in6 *v6; -#endif + current = (unsigned char *)buf + sizeof(HEADER); for (; header->qdcount > 0; --header->qdcount) @@ -724,8 +658,8 @@ proc_answer(struct reslist *request, HEADER* header, char* buf, char* eob) rd_length = irc_ns_get16(current); current += RDLENGTH_SIZE; - /* - * Wait to set request->type until we verify this structure + /* + * Wait to set request->type until we verify this structure */ switch (type) { @@ -738,25 +672,18 @@ proc_answer(struct reslist *request, HEADER* header, char* buf, char* eob) */ if (rd_length != sizeof(struct in_addr)) return(0); - v4 = (struct sockaddr_in *)&request->addr; - request->addr.ss_len = sizeof(struct sockaddr_in); - v4->sin_family = AF_INET; - memcpy(&v4->sin_addr, current, sizeof(struct in_addr)); + memset(&request->addr, 0, sizeof(request->addr)); + memcpy(&request->addr.in6_16[6], current, sizeof(struct in_addr)); return(1); break; -#ifdef IPV6 case T_AAAA: if (request->type != T_AAAA) return(0); - if (rd_length != sizeof(struct in6_addr)) + if (rd_length != sizeof(struct irc_in_addr)) return(0); - request->addr.ss_len = sizeof(struct sockaddr_in6); - v6 = (struct sockaddr_in6 *)&request->addr; - v6->sin6_family = AF_INET6; - memcpy(&v6->sin6_addr, current, sizeof(struct in6_addr)); + memcpy(&request->addr, current, sizeof(struct irc_in_addr)); return(1); break; -#endif case T_PTR: if (request->type != T_PTR) return(0); @@ -771,9 +698,9 @@ proc_answer(struct reslist *request, HEADER* header, char* buf, char* eob) return(1); break; - case T_CNAME: /* first check we already havent started looking + case T_CNAME: /* first check we already havent started looking into a cname */ - if (request->type != T_PTR) + if (request->type != T_PTR) return(0); if (request->state == REQ_CNAME) @@ -789,7 +716,7 @@ proc_answer(struct reslist *request, HEADER* header, char* buf, char* eob) request->state = REQ_CNAME; current += rd_length; break; - + default: /* XXX I'd rather just throw away the entire bogus thing * but its possible its just a broken nameserver with still @@ -809,22 +736,20 @@ proc_answer(struct reslist *request, HEADER* header, char* buf, char* eob) static void res_readreply(struct Event *ev) { + struct irc_sockaddr lsin; struct Socket *sock; char buf[sizeof(HEADER) + MAXPACKET]; HEADER *header; struct reslist *request = NULL; struct DNSReply *reply = NULL; - int rc; + unsigned int rc; int answer_count; - socklen_t len = sizeof(struct irc_ssaddr); - struct irc_ssaddr lsin; assert(ev_socket(ev) == &res_socket); sock = ev_socket(ev); - rc = recvfrom(s_fd(sock), buf, sizeof(buf), 0, (struct sockaddr *)&lsin, &len); - /* Better to cast the sizeof instead of rc */ - if (rc <= (int)(sizeof(HEADER))) + if (IO_SUCCESS != os_recvfrom_nonb(s_fd(sock), buf, sizeof(buf), &rc, &lsin) + || (rc <= sizeof(HEADER))) return; /* @@ -855,40 +780,39 @@ res_readreply(struct Event *ev) resend_query(request); else { - /* + /* * If we havent already tried this, and we're looking up AAAA, try A * now */ -#ifdef IPV6 if (request->state == REQ_AAAA && request->type == T_AAAA) { request->timeout += 4; resend_query(request); } else if (request->type == T_PTR && request->state != REQ_INT && - request->addr.ss.ss_family == AF_INET6) + !irc_in_addr_is_ipv4(&request->addr)) { request->state = REQ_INT; request->timeout += 4; resend_query(request); } else -#endif { /* * If a bad error was returned, we stop here and dont send * send any more (no retries granted). */ + Debug((DEBUG_DNS, "Request %p has bad response (state %d type %d)", request, request->state, request->type)); (*request->query.callback)(request->query.vptr, 0); rem_request(request); - } + } } return; } /* - * If this fails there was an error decoding the received packet, + * If this fails there was an error decoding the received packet, * try it again and hope it works the next time. */ answer_count = proc_answer(request, header, buf, buf + rc); @@ -903,6 +827,7 @@ res_readreply(struct Event *ev) * got a PTR response with no name, something bogus is happening * don't bother trying again, the client address doesn't resolve */ + Debug((DEBUG_DNS, "Request %p PTR had empty name", request)); (*request->query.callback)(request->query.vptr, reply); rem_request(request); return; @@ -910,15 +835,15 @@ res_readreply(struct Event *ev) /* * Lookup the 'authoritative' name that we were given for the - * ip#. - * + * ip#. */ #ifdef IPV6 - if (request->addr.ss.ss_family == AF_INET6) + if (!irc_in_addr_is_ipv4(&request->addr)) gethost_byname_type(request->name, &request->query, T_AAAA); else #endif gethost_byname_type(request->name, &request->query, T_A); + Debug((DEBUG_DNS, "Request %p switching to forward resolution", request)); rem_request(request); } else @@ -928,6 +853,7 @@ res_readreply(struct Event *ev) */ reply = make_dnsreply(request); (*request->query.callback)(request->query.vptr, (reply) ? reply : 0); + Debug((DEBUG_DNS, "Request %p got forward resolution", request)); rem_request(request); } } @@ -939,6 +865,7 @@ res_readreply(struct Event *ev) assert(0); /* XXX don't leak it */ + Debug((DEBUG_DNS, "Request %p was unexpected(!)", request)); rem_request(request); } } @@ -964,10 +891,8 @@ report_dns_servers(struct Client *source_p, struct StatDesc *sd, int stat, char for (i = 0; i < irc_nscount; i++) { - irc_getnameinfo((struct sockaddr *)&(irc_nsaddr_list[i]), - irc_nsaddr_list[i].ss_len, ipaddr, sizeof(ipaddr), NULL, 0, - NI_NUMERICHOST); - send_reply(source_p, RPL_STATSALINE, ipaddr); + ircd_ntoa_r(ipaddr, &irc_nsaddr_list[i].addr); + send_reply(source_p, RPL_STATSALINE, ipaddr); } } @@ -983,7 +908,7 @@ cres_mem(struct Client* sptr) request = (struct reslist*)dlink; request_mem += sizeof(*request); if (request->name) - request_mem += strlen(request->name) + 1; + request_mem += strlen(request->name) + 1; ++request_count; } @@ -991,3 +916,41 @@ cres_mem(struct Client* sptr) ":Resolver: requests %d(%d)", request_count, request_mem); return request_mem; } + +int irc_in_addr_valid(const struct irc_in_addr *addr) +{ + unsigned int ii; + unsigned short val; + + val = addr->in6_16[0]; + if (val != 0 || val != 0xffff) + return 1; + for (ii = 1; ii < 8; ii++) + if (addr->in6_16[ii] != val) + return 1; + return 0; +} + +int irc_in_addr_cmp(const struct irc_in_addr *a, const struct irc_in_addr *b) +{ + if (irc_in_addr_is_ipv4(a)) + return a->in6_16[6] != b->in6_16[6] + || a->in6_16[7] != b->in6_16[7] + || !irc_in_addr_is_ipv4(b); + else + return memcmp(a, b, sizeof(*a)); +} + +int irc_in_addr_is_loopback(const struct irc_in_addr *addr) +{ + if (addr->in6_16[0] != 0 + || addr->in6_16[1] != 0 + || addr->in6_16[2] != 0 + || addr->in6_16[3] != 0 + || addr->in6_16[4] != 0) + return 0; + if ((addr->in6_16[5] == 0xffff) || (addr->in6_16[5] == 0 && addr->in6_16[6] != 0)) + return (ntohs(addr->in6_16[6]) & 0xff00) == 0x7f00; + else + return addr->in6_16[5] == 0 && addr->in6_16[6] == 0 && htons(addr->in6_16[7]) == 1; +} diff --git a/ircd/ircd_reslib.c b/ircd/ircd_reslib.c index 699a2d8..ba953bb 100644 --- a/ircd/ircd_reslib.c +++ b/ircd/ircd_reslib.c @@ -86,7 +86,6 @@ #include "ircd_defs.h" #include "fileio.h" #include "ircd_string.h" -#include "ircd_addrinfo.h" #include #include @@ -100,7 +99,7 @@ /* $Id$ */ -struct irc_ssaddr irc_nsaddr_list[IRCD_MAXNS]; +struct irc_sockaddr irc_nsaddr_list[IRCD_MAXNS]; int irc_nscount = 0; char irc_domain[HOSTLEN + 1]; @@ -221,26 +220,18 @@ parse_resvconf(void) static void add_nameserver(char *arg) { - struct addrinfo hints, *res; + struct irc_sockaddr res; + /* Done max number of nameservers? */ if ((irc_nscount + 1) >= IRCD_MAXNS) return; - memset(&hints, 0, sizeof(hints)); - hints.ai_family = PF_UNSPEC; - hints.ai_socktype = SOCK_DGRAM; - hints.ai_flags = AI_PASSIVE | AI_NUMERICHOST; - - if (irc_getaddrinfo(arg, "domain", &hints, &res)) - return; - - if (res == NULL) - return; - - memcpy(&irc_nsaddr_list[irc_nscount].ss, res->ai_addr, res->ai_addrlen); - irc_nsaddr_list[irc_nscount].ss_len = res->ai_addrlen; + /* Failure converting from numeric string? */ + if (!ircd_aton(&res.addr, arg)) + return; + res.port = 53; + memcpy(&irc_nsaddr_list[irc_nscount], &res, sizeof(irc_nsaddr_list[irc_nscount])); irc_nscount++; - irc_freeaddrinfo(res); } /* diff --git a/ircd/ircd_string.c b/ircd/ircd_string.c index dc3886e..dc9a461 100644 --- a/ircd/ircd_string.c +++ b/ircd/ircd_string.c @@ -24,9 +24,14 @@ #include "ircd_defs.h" #include "ircd_chattr.h" #include "ircd_log.h" +#include "res.h" + #include #include #include +#include +#include + /* * include the character attribute tables here */ @@ -385,7 +390,7 @@ char* host_from_uh(char* host, const char* userhost, size_t n) return host; } -/* +/* * this new faster inet_ntoa was ripped from: * From: Thomas Helvey */ @@ -430,40 +435,229 @@ static const char* IpQuadTab[] = * argv 11/90). * inet_ntoa -- its broken on some Ultrix/Dynix too. -avalon */ -const char* ircd_ntoa(const char* in) +const char* ircd_ntoa(const struct irc_in_addr* in) { - static char buf[20]; + static char buf[SOCKIPLEN]; return ircd_ntoa_r(buf, in); } +/* This doesn't really belong here, but otherwise umkpasswd breaks. */ +int irc_in_addr_is_ipv4(const struct irc_in_addr *addr) +{ + return addr->in6_16[0] == 0 + && addr->in6_16[1] == 0 + && addr->in6_16[2] == 0 + && addr->in6_16[3] == 0 + && addr->in6_16[4] == 0 + && (addr->in6_16[5] == 0 || addr->in6_16[5] == 0xffff) + && addr->in6_16[6] != 0; +} + /* * reentrant version of above */ -const char* ircd_ntoa_r(char* buf, const char* in) +const char* ircd_ntoa_r(char* buf, const struct irc_in_addr* in) { - char* p = buf; - const unsigned char* a = (const unsigned char*)in; - const char* n; - - assert(0 != buf); - assert(0 != in); - - n = IpQuadTab[*a++]; - while ((*p = *n++)) - ++p; - *p++ = '.'; - n = IpQuadTab[*a++]; - while ((*p = *n++)) - ++p; - *p++ = '.'; - n = IpQuadTab[*a++]; - while ((*p = *n++)) - ++p; - *p++ = '.'; - n = IpQuadTab[*a]; - while ((*p = *n++)) - ++p; - return buf; + assert(buf != NULL); + assert(in != NULL); + + if (irc_in_addr_is_ipv4(in)) { + unsigned int pos, len; + unsigned char *pch; + + pch = (unsigned char*)&in->in6_16[6]; + len = strlen(IpQuadTab[*pch]); + memcpy(buf, IpQuadTab[*pch++], len); + pos = len; + buf[pos++] = '.'; + len = strlen(IpQuadTab[*pch]); + memcpy(buf+pos, IpQuadTab[*pch++], len); + pos += len; + buf[pos++] = '.'; + len = strlen(IpQuadTab[*pch]); + memcpy(buf+pos, IpQuadTab[*pch++], len); + pos += len; + buf[pos++] = '.'; + len = strlen(IpQuadTab[*pch]); + memcpy(buf+pos, IpQuadTab[*pch++], len); + buf[pos + len] = '\0'; + return buf; + } else { + static const char hexdigits[] = "0123456789abcdef"; + unsigned int pos, part, max_start, max_zeros, curr_zeros, ii; + + /* Find longest run of zeros. */ + for (max_start = ii = 1, max_zeros = curr_zeros = 0; ii < 8; ++ii) { + if (!in->in6_16[ii]) + curr_zeros++; + else if (curr_zeros > max_zeros) { + max_start = ii - curr_zeros; + max_zeros = curr_zeros; + curr_zeros = 0; + } + } + if (curr_zeros > max_zeros) { + max_start = ii - curr_zeros; + max_zeros = curr_zeros; + } + + /* Print out address. */ +#define APPEND(CH) do { buf[pos++] = (CH); } while (0) + for (pos = ii = 0; (ii < 8); ++ii) { + if ((max_zeros > 0) && (ii == max_start)) { + APPEND(':'); + ii += max_zeros - 1; + continue; + } + part = ntohs(in->in6_16[ii]); + if (part >= 0x1000) + APPEND(hexdigits[part >> 12]); + if (part >= 0x100) + APPEND(hexdigits[(part >> 8) & 15]); + if (part >= 0x10) + APPEND(hexdigits[(part >> 4) & 15]); + APPEND(hexdigits[part & 15]); + if (ii < 7) + APPEND(':'); + } + if (max_zeros + max_start == 8) + APPEND(':'); +#undef APPEND + + /* Nul terminate and return number of characters used. */ + buf[pos++] = '\0'; + return buf; + } } +static unsigned int +ircd_aton_ip4(const char *input, unsigned int *output) +{ + unsigned int dots = 0, pos = 0, part = 0, ip = 0; + /* Intentionally no support for bizarre IPv4 formats (plain + * integers, octal or hex components) -- only vanilla dotted + * decimal quads. + */ + if (input[0] == '.') + return 0; + while (1) { + if (IsDigit(input[pos])) { + part = part * 10 + input[pos++] - '0'; + if (part > 255) + return 0; + if ((dots == 3) && !IsDigit(input[pos])) { + *output = htonl(ip | part); + return pos; + } + } else if (input[pos] == '.') { + if (input[++pos] == '.') + return 0; + ip |= part << (24 - 8 * dots++); + part = 0; + } else + return 0; + } +} + +/* ircd_aton - Parse a numeric IPv4 or IPv6 address into an irc_in_addr. + * Returns number of characters used by address, or 0 if the address was + * unparseable or malformed. + */ +int +ircd_aton(struct irc_in_addr *ip, const char *input) +{ + char *colon; + char *dot; + + assert(ip); + assert(input); + memset(ip, 0, sizeof(*ip)); + colon = strchr(input, ':'); + dot = strchr(input, '.'); + + if (colon && (!dot || (dot > colon))) { + unsigned int part = 0, pos = 0, ii = 0, colon = 8; + const char *part_start = NULL; + + /* Parse IPv6, possibly like ::127.0.0.1. + * This is pretty straightforward; the only trick is borrowed + * from Paul Vixie (BIND): when it sees a "::" continue as if + * it were a single ":", but note where it happened, and fill + * with zeros afterwards. + */ + if (input[pos] == ':') { + if ((input[pos+1] != ':') || (input[pos+2] == ':')) + return 0; + colon = 0; + pos += 2; + } + while (ii < 8) { + unsigned char chval; + + switch (input[pos]) { + case '0': case '1': case '2': case '3': case '4': + case '5': case '6': case '7': case '8': case '9': + chval = input[pos] - '0'; + use_chval: + part = (part << 4) | chval; + if (part > 0xffff) + return 0; + pos++; + break; + case 'A': case 'B': case 'C': case 'D': case 'E': case 'F': + chval = input[pos] - 'A' + 10; + goto use_chval; + case 'a': case 'b': case 'c': case 'd': case 'e': case 'f': + chval = input[pos] - 'a' + 10; + goto use_chval; + case ':': + part_start = input + ++pos; + if (input[pos] == '.') + return 0; + ip->in6_16[ii++] = htons(part); + part = 0; + if (input[pos] == ':') { + if (colon < 8) + return 0; + colon = ii; + pos++; + } + break; + case '.': { + uint32_t ip4; + unsigned int len; + len = ircd_aton_ip4(input + pos, &ip4); + if (!len || (ii > 6)) + return 0; + ip->in6_16[ii++] = htons(ntohl(ip4) >> 16); + ip->in6_16[ii++] = htons(ntohl(ip4) & 65535); + pos += len; + break; + } + default: { + unsigned int jj; + if (colon >= 8) + return 0; + /* Shift stuff after "::" up and fill middle with zeros. */ + ip->in6_16[ii++] = htons(part); + for (jj = 0; jj < ii - colon; jj++) + ip->in6_16[7 - jj] = ip->in6_16[ii - jj - 1]; + for (jj = 0; jj < 8 - ii; jj++) + ip->in6_16[colon + jj] = 0; + return pos; + } + } + } + return pos; + } else if (dot) { + unsigned int addr; + int len = ircd_aton_ip4(input, &addr); + if (len) { + ip->in6_16[6] = htons(ntohl(addr) >> 16); + ip->in6_16[7] = htons(ntohl(addr) & 65535); + return len; + } + } + return 0; /* parse failed */ +} diff --git a/ircd/listener.c b/ircd/listener.c index 6b67d0c..0556ce9 100644 --- a/ircd/listener.c +++ b/ircd/listener.c @@ -30,6 +30,7 @@ #include "ircd_reply.h" #include "ircd_snprintf.h" #include "ircd_string.h" +#include "match.h" #include "numeric.h" #include "s_bsd.h" #include "s_conf.h" @@ -56,17 +57,17 @@ struct Listener* ListenerPollList = 0; static void accept_connection(struct Event* ev); -static struct Listener* make_listener(int port, struct in_addr addr) +static struct Listener* make_listener(int port, const struct irc_in_addr *addr) { - struct Listener* listener = + struct Listener* listener = (struct Listener*) MyMalloc(sizeof(struct Listener)); assert(0 != listener); memset(listener, 0, sizeof(struct Listener)); listener->fd = -1; - listener->port = port; - listener->addr.s_addr = addr.s_addr; + listener->addr.port = port; + memcpy(&listener->addr.addr, addr, sizeof(listener->addr.addr)); #ifdef NULL_POINTER_NOT_ZERO listener->next = NULL; @@ -91,7 +92,7 @@ const char* get_listener_name(const struct Listener* listener) { static char buf[HOSTLEN + PORTNAMELEN + 4]; assert(0 != listener); - ircd_snprintf(0, buf, sizeof(buf), "%s:%u", cli_name(&me), listener->port); + ircd_snprintf(0, buf, sizeof(buf), "%s:%u", cli_name(&me), listener->addr.port); return buf; } @@ -132,7 +133,7 @@ void show_ports(struct Client* sptr, struct StatDesc* sd, int stat, port = atoi(param); for (listener = ListenerPollList; listener; listener = listener->next) { - if (port && port != listener->port) + if (port && port != listener->addr.port) continue; flags[0] = (listener->server) ? 'S' : 'C'; if (listener->hidden) { @@ -144,7 +145,7 @@ void show_ports(struct Client* sptr, struct StatDesc* sd, int stat, else flags[1] = '\0'; - send_reply(sptr, RPL_STATSPLINE, listener->port, listener->ref_count, + send_reply(sptr, RPL_STATSPLINE, listener->addr.port, listener->ref_count, flags, (listener->active) ? "active" : "disabled"); if (--count == 0) break; @@ -168,41 +169,14 @@ void show_ports(struct Client* sptr, struct StatDesc* sd, int stat, static int inetport(struct Listener* listener) { - struct sockaddr_in sin; int fd; /* * At first, open a new socket */ - if (-1 == (fd = socket(AF_INET, SOCK_STREAM, 0))) { - report_error(SOCKET_ERROR_MSG, get_listener_name(listener), errno); + fd = os_socket(&listener->addr, SOCK_STREAM, get_listener_name(listener)); + if (fd < 0) return 0; - } - else if (fd > MAXCLIENTS - 1) { - report_error(CONNLIMIT_ERROR_MSG, get_listener_name(listener), 0); - close(fd); - return 0; - } - - if (!os_set_reuseaddr(fd)) { - report_error(REUSEADDR_ERROR_MSG, get_listener_name(listener), errno); - close(fd); - return 0; - } - /* - * Bind a port to listen for new connections if port is non-null, - * else assume it is already open and try get something from it. - */ - memset(&sin, 0, sizeof(sin)); - sin.sin_family = AF_INET; - sin.sin_addr = listener->addr; - sin.sin_port = htons(listener->port); - - if (bind(fd, (struct sockaddr*) &sin, sizeof(sin))) { - report_error(BIND_ERROR_MSG, get_listener_name(listener), errno); - close(fd); - return 0; - } /* * Set the buffer sizes for the listener. Accepted connections * inherit the accepting sockets settings for SO_RCVBUF S_SNDBUF @@ -222,14 +196,6 @@ static int inetport(struct Listener* listener) close(fd); return 0; } - /* - * XXX - this should always work, performance will suck if it doesn't - */ - if (!os_set_nonblocking(fd)) { - report_error(NONB_ERROR_MSG, get_listener_name(listener), errno); - close(fd); - return 0; - } /* * Set the TOS bits - this is nonfatal if it doesn't stick. */ @@ -255,70 +221,27 @@ static int inetport(struct Listener* listener) * XXX - this function does N comparisons so if the list is huge * we may want to do something else for this. (rehash and init use this) */ -static struct Listener* find_listener(int port, struct in_addr addr) +static struct Listener* find_listener(int port, const struct irc_in_addr *addr) { struct Listener* listener; for (listener = ListenerPollList; listener; listener = listener->next) { - if (port == listener->port && addr.s_addr == listener->addr.s_addr) + if (port == listener->addr.port && !memcmp(addr, &listener->addr.addr, sizeof(*addr))) return listener; } return 0; } /* - * set_listener_mask - set the connection mask for this listener - */ -static void set_listener_mask(struct Listener* listener, const char* mask) -{ - int ad[4]; - char ipname[20]; - - assert(0 != listener); - - if (EmptyString(mask) || 0 == strcmp(mask, "*")) { - listener->mask.s_addr = 0; - return; - } - ad[0] = ad[1] = ad[2] = ad[3] = 0; - /* - * do it this way because building ip# from separate values for each - * byte requires endian knowledge or some nasty messing. Also means - * easy conversion of "*" 0.0.0.0 or 134.* to 134.0.0.0 :-) - */ - sscanf(mask, "%d.%d.%d.%d", &ad[0], &ad[1], &ad[2], &ad[3]); - ircd_snprintf(0, ipname, sizeof(ipname), "%d.%d.%d.%d", ad[0], ad[1], ad[2], - ad[3]); - listener->mask.s_addr = inet_addr(ipname); -} - -/* - * connection_allowed - spin through mask and addr passed to see if connect - * allowed on a listener, uses mask generated by set_listener_mask - */ -static int connection_allowed(const char* addr, const char* mask) -{ - int i = 4; - for ( ; i > 0; --i) { - if (*mask && *addr != *mask) - break; - ++addr; - ++mask; - } - return (0 == i); -} - - -/* - * add_listener- create a new listener + * add_listener- create a new listener * port - the port number to listen on * vhost_ip - if non-null must contain a valid IP address string in * the format "255.255.255.255" */ void add_listener(int port, const char* vhost_ip, const char* mask, - int is_server, int is_hidden) + int is_server, int is_hidden) { struct Listener* listener; - struct in_addr vaddr; + struct irc_in_addr vaddr; /* * if no port in conf line, don't bother @@ -326,35 +249,40 @@ void add_listener(int port, const char* vhost_ip, const char* mask, if (0 == port) return; - vaddr.s_addr = INADDR_ANY; + memset(&vaddr, 0, sizeof(vaddr)); - if (!EmptyString(vhost_ip) && strcmp(vhost_ip,"*") != 0) { - vaddr.s_addr = inet_addr(vhost_ip); - if (INADDR_NONE == vaddr.s_addr) + if (!EmptyString(vhost_ip) + && strcmp(vhost_ip, "*") + && !ircd_aton(&vaddr, vhost_ip)) return; - } - if ((listener = find_listener(port, vaddr))) { + if ((listener = find_listener(port, &vaddr))) { /* - * set active flag and change connect mask here, it's the only thing + * set active flag and change connect mask here, it's the only thing * that can change on a rehash */ listener->active = 1; - set_listener_mask(listener, mask); + if (mask) + ipmask_parse(mask, &listener->mask, &listener->mask_bits); + else + listener->mask_bits = 0; listener->hidden = is_hidden; listener->server = is_server; return; } - listener = make_listener(port, vaddr); + listener = make_listener(port, &vaddr); if (inetport(listener)) { listener->active = 1; - set_listener_mask(listener, mask); + if (mask) + ipmask_parse(mask, &listener->mask, &listener->mask_bits); + else + listener->mask_bits = 0; listener->hidden = is_hidden; listener->server = is_server; listener->next = ListenerPollList; - ListenerPollList = listener; + ListenerPollList = listener; } else free_listener(listener); @@ -426,10 +354,9 @@ void release_listener(struct Listener* listener) */ static void accept_connection(struct Event* ev) { - struct Listener* listener; - struct sockaddr_in addr = { 0 }; - unsigned int addrlen = sizeof(struct sockaddr_in); - int fd; + struct Listener* listener; + struct irc_sockaddr addr; + int fd; assert(0 != ev_socket(ev)); assert(0 != s_data(ev_socket(ev))); @@ -462,8 +389,7 @@ static void accept_connection(struct Event* ev) */ while (1) { - if ((fd = accept(listener->fd, (struct sockaddr*) &addr, &addrlen)) - == -1) + if ((fd = os_accept(listener->fd, &addr)) == -1) { if (errno == EAGAIN || #ifdef EWOULDBLOCK @@ -507,8 +433,7 @@ static void accept_connection(struct Event* ev) /* * check to see if connection is allowed for this address mask */ - if (!connection_allowed((const char*) &addr, - (const char*) &listener->mask)) + if (!ipmask_check(&addr.addr, &listener->mask, listener->mask_bits)) { ++ServerStats->is_ref; send(fd, "ERROR :Use another port\r\n", 25, 0); diff --git a/ircd/m_connect.c b/ircd/m_connect.c index b7dfd3c..55feddd 100644 --- a/ircd/m_connect.c +++ b/ircd/m_connect.c @@ -185,13 +185,12 @@ int ms_connect(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) /* * save the old port */ - tmpport = aconf->port; - if (port) { - aconf->port = port; - } - else { - port = aconf->port; - } + tmpport = aconf->address.port; + if (port) + aconf->address.port = port; + else + port = aconf->address.port; + /* * Notify all operators about remote connect requests */ @@ -210,7 +209,7 @@ int ms_connect(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :*** Connection to %s failed", sptr, aconf->name); } - aconf->port = tmpport; + aconf->address.port = tmpport; return 0; } @@ -314,7 +313,7 @@ int mo_connect(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) * use the default from configuration structure. If missing * from there, then use the precompiled default. */ - port = aconf->port; + port = aconf->address.port; if (parc > 2) { assert(0 != parv[2]); if (0 == (port = atoi(parv[2]))) { @@ -329,8 +328,8 @@ int mo_connect(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) return 0; } - tmpport = aconf->port; - aconf->port = port; + tmpport = aconf->address.port; + aconf->address.port = port; if (connect_server(aconf, sptr)) { sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :*** Connecting to %s.", sptr, @@ -340,6 +339,6 @@ int mo_connect(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :*** Connection to %s failed", sptr, aconf->name); } - aconf->port = tmpport; + aconf->address.port = tmpport; return 0; } diff --git a/ircd/m_nick.c b/ircd/m_nick.c index e7b08f7..d993a66 100644 --- a/ircd/m_nick.c +++ b/ircd/m_nick.c @@ -247,7 +247,7 @@ int m_nick(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) */ if (IsUnknown(acptr) && MyConnect(acptr)) { ++ServerStats->is_ref; - IPcheck_connect_fail(cli_ip(acptr)); + IPcheck_connect_fail(&cli_ip(acptr)); exit_client(cptr, acptr, &me, "Overridden by other sign on"); return set_nick_name(cptr, sptr, nick, parc, parv); } @@ -377,7 +377,7 @@ int ms_nick(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) if (IsUnknown(acptr) && MyConnect(acptr)) { ServerStats->is_ref++; - IPcheck_connect_fail(cli_ip(acptr)); + IPcheck_connect_fail(&cli_ip(acptr)); exit_client(cptr, acptr, &me, "Overridden by other sign on"); return set_nick_name(cptr, sptr, nick, parc, parv); } @@ -401,13 +401,15 @@ int ms_nick(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) */ if (IsServer(sptr)) { + struct irc_in_addr ip; /* * A new NICK being introduced by a neighbouring * server (e.g. message type ":server NICK new ..." received) * * compare IP address and username */ - differ = (cli_ip(acptr).s_addr != htonl(base64toint(parv[parc - 3]))) || + base64toip(parv[parc - 3], &ip); + differ = (0 != memcmp(&cli_ip(acptr), &ip, sizeof(cli_ip(acptr)))) || (0 != ircd_strcmp(cli_user(acptr)->username, parv[4])); sendto_opmask_butone(0, SNO_OLDSNO, "Nick collision on %C (%C %Tu <- " "%C %Tu (%s user@host))", acptr, cli_from(acptr), @@ -421,8 +423,8 @@ int ms_nick(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) * * compare IP address and username */ - differ = (cli_ip(acptr).s_addr != cli_ip(sptr).s_addr) || - (0 != ircd_strcmp(cli_user(acptr)->username, cli_user(sptr)->username)); + differ = (0 != memcmp(&cli_ip(acptr), &cli_ip(sptr), sizeof(cli_ip(acptr)))) || + (0 != ircd_strcmp(cli_user(acptr)->username, cli_user(sptr)->username)); sendto_opmask_butone(0, SNO_OLDSNO, "Nick change collision from %C to " "%C (%C %Tu <- %C %Tu)", sptr, acptr, cli_from(acptr), cli_lastnick(acptr), cptr, lastnick); diff --git a/ircd/m_oper.c b/ircd/m_oper.c index a180c05..cc2e47c 100644 --- a/ircd/m_oper.c +++ b/ircd/m_oper.c @@ -144,9 +144,9 @@ int m_oper(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) return need_more_params(sptr, "OPER"); aconf = find_conf_exact(name, cli_username(sptr), cli_sockhost(sptr), CONF_OPERATOR); - if (!aconf) + if (!aconf) aconf = find_conf_exact(name, cli_username(sptr), - ircd_ntoa((const char*) &(cli_ip(cptr))), CONF_OPERATOR); + ircd_ntoa(&cli_ip(cptr)), CONF_OPERATOR); if (!aconf || IsIllegal(aconf)) { diff --git a/ircd/m_userip.c b/ircd/m_userip.c index 3568112..80078ff 100644 --- a/ircd/m_userip.c +++ b/ircd/m_userip.c @@ -100,7 +100,7 @@ static void userip_formatter(struct Client* cptr, struct Client *sptr, struct Ms cli_user(cptr)->away ? '-' : '+', cli_user(cptr)->username, HasHiddenHost(cptr) && !IsAnOper(sptr) && (sptr != cptr) ? feature_str(FEAT_HIDDEN_IP) : - ircd_ntoa((const char*) &(cli_ip(cptr)))); + ircd_ntoa(&cli_ip(cptr))); } /* diff --git a/ircd/m_who.c b/ircd/m_who.c index 797b5a8..c4fd81f 100644 --- a/ircd/m_who.c +++ b/ircd/m_who.c @@ -351,12 +351,14 @@ int m_who(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) real mask and try to match all relevant fields */ if (!(commas || (counter < 1))) { + struct irc_in_addr imask; int minlen, cset; - static struct in_mask imask; + unsigned char ibits; + if (mask) { matchcomp(mymask, &minlen, &cset, mask); - if (matchcompIP(&imask, mask)) + if (!ipmask_parse(mask, &imask, &ibits)) matchsel &= ~WHO_FIELD_NIP; if ((minlen > NICKLEN) || !(cset & NTL_IRCNK)) matchsel &= ~WHO_FIELD_NIC; @@ -401,9 +403,7 @@ int m_who(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) || matchexec(cli_info(acptr), mymask, minlen)) && ((!(matchsel & WHO_FIELD_NIP)) || (HasHiddenHost(acptr) && !IsAnOper(sptr)) - || ((((cli_ip(acptr).s_addr & imask.mask.s_addr) != - imask.bits.s_addr)) || (imask.fall - && matchexec(ircd_ntoa((const char*) &(cli_ip(acptr))), mymask, minlen))))) + || !ipmask_check(&cli_ip(acptr), &imask, ibits))) continue; if (!SHOW_MORE(sptr, counter)) break; @@ -439,9 +439,7 @@ int m_who(struct Client* cptr, struct Client* sptr, int parc, char* parv[]) || matchexec(cli_info(acptr), mymask, minlen)) && ((!(matchsel & WHO_FIELD_NIP)) || (HasHiddenHost(acptr) && !IsAnOper(sptr)) - || ((((cli_ip(acptr).s_addr & imask.mask.s_addr) != imask.bits.s_addr)) - || (imask.fall - && matchexec(ircd_ntoa((const char*) &(cli_ip(acptr))), mymask, minlen))))) + || !ipmask_check(&cli_ip(acptr), &imask, ibits))) continue; if (!SHOW_MORE(sptr, counter)) break; diff --git a/ircd/m_whois.c b/ircd/m_whois.c index 0230e8a..5660ba6 100644 --- a/ircd/m_whois.c +++ b/ircd/m_whois.c @@ -209,15 +209,15 @@ static void do_whois(struct Client* sptr, struct Client *acptr, int parc) if (HasHiddenHost(acptr) && (IsAnOper(sptr) || acptr == sptr)) send_reply(sptr, RPL_WHOISACTUALLY, name, user->username, - user->realhost, ircd_ntoa((const char*) &(cli_ip(acptr)))); - + user->realhost, ircd_ntoa(&cli_ip(acptr))); + /* Hint: if your looking to add more flags to a user, eg +h, here's * probably a good place to add them :) */ - + if (MyConnect(acptr) && (!feature_bool(FEAT_HIS_WHOIS_IDLETIME) || (sptr == acptr || IsAnOper(sptr) || parc >= 3))) - send_reply(sptr, RPL_WHOISIDLE, name, CurrentTime - user->last, + send_reply(sptr, RPL_WHOISIDLE, name, CurrentTime - user->last, cli_firsttime(acptr)); } } diff --git a/ircd/match.c b/ircd/match.c index 821c222..5cb91da 100644 --- a/ircd/match.c +++ b/ircd/match.c @@ -22,6 +22,10 @@ #include "match.h" #include "ircd_chattr.h" +#include "ircd_string.h" +#include "ircd_snprintf.h" +#include "support.h" + /* * mmatch() * @@ -788,195 +792,72 @@ int mmexec(const char *wcm, int wminlen, const char *rcm, int rminlen) return 1; /* Auch... something left out ? Fail */ } -/* - * matchcompIP() - * Compiles an IP mask into an in_mask structure - * The given can either be: - * - An usual irc type mask, containing * and or ? - * - An ip number plus a /bitnumber part, that will only consider - * the first "bitnumber" bits of the IP (bitnumber must be in 0-31 range) - * - An ip numer plus a /ip.bit.mask.values that will consider - * only the bits marked as 1 in the ip.bit.mask.values - * In the last two cases both the ip number and the bitmask can specify - * less than 4 bytes, the missing bytes then default to zero, note that - * this is *different* from the way inet_aton() does and that this does - * NOT happen for normal IPmasks (not containing '/') - * If the returned value is zero the produced in_mask might match some IP, - * if it's nonzero it will never match anything (and the imask struct is - * set so that always fails). - * - * The returned structure contains 3 fields whose meaning is the following: - * im.mask = The bits considered significative in the IP - * im.bits = What these bits should look like to have a match - * im.fall = If zero means that the above information used as - * ((IP & im.mask) == im.bits) is enough to tell if the compiled - * mask matches the given IP, nonzero means that it is needed, - * in case they did match, to call also the usual text match - * functions, because the mask wasn't "completely compiled" - * - * They should be used like: - * matchcompIP(&im, mask); - * if ( ((IP & im.mask)!=im.bits)) || (im.fall&&match(mask,inet_ntoa(IP))) ) - * { handle_non_match } else { handle_match }; - * instead of: - * if ( match(mask, inet_ntoa(IP)) ) - * { handle_non_match } else { handle_match }; - * - * Note: This function could be smarter when dealing with complex masks, - * this implementation is quite lazy and understands only very simple - * cases, whatever contains a ? anywhere or contains a '*' that isn't - * part of a trailing '.*' will fallback to text-match, this could be - * avoided for masks like 12?3.5.6 12.*.3.4 1.*.*.2 72?72?72?72 and - * so on that "could" be completely compiled to IP masks. - * If you try to improve this be aware of the fact that ? and * - * could match both dots and digits and we _must_ always reject - * what doesn't match in textform (like leading zeros and so on), - * so it's a LOT more tricky than it might seem. By now most common - * cases are optimized. - */ +#include +#include +#include +#include +#include +#include -int matchcompIP(struct in_mask *imask, const char *mask) +static int ipmask_parse_ipv4(const char *in, struct in_addr *out) { - const char *m = mask; - unsigned int bits = 0; - unsigned int filt = 0; - int unco = 0; - int digits = 0; - int shift = 24; - int tmp = 0; - - do - { - switch (*m) - { - case '\\': - if ((m[1] == '\\') || (m[1] == '*') || (m[1] == '?') - || (m[1] == '\0')) - break; - continue; - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - if (digits && !tmp) /* Leading zeros */ - break; - digits++; - tmp *= 10; - tmp += (*m - '0'); /* Can't overflow, INT_MAX > 2559 */ - if (tmp > 255) - break; - continue; - case '\0': - filt = 0xFFFFFFFF; - /* Intentional fallthrough */ - case '.': - if ((!shift) != (!*m)) - break; - /* Intentional fallthrough */ - case '/': - bits |= (tmp << shift); - shift -= 8; - digits = 0; - tmp = 0; - if (*m != '/') - continue; - shift = 24; - do - { - m++; - if (IsDigit(*m)) - { - if (digits && !tmp) /* Leading zeros */ - break; - digits++; - tmp *= 10; - tmp += (*m - '0'); /* Can't overflow, INT_MAX > 2559 */ - if (tmp > 255) - break; - } - else - { - switch (*m) - { - case '.': - case '\0': - if ((!shift) && (*m)) - break; - filt |= (tmp << shift); - shift -= 8; - tmp = 0; - digits = 0; - continue; - default: - break; - } - break; - } - } - while (*m); - if (*m) - break; - if (filt && (!(shift < 16)) && (!(filt & 0xE0FFFFFF))) - filt = 0xFFFFFFFF << (32 - ((filt >> 24))); - bits &= filt; - continue; - case '?': - unco = 1; - /* Intentional fallthrough */ - case '*': - if (digits) - unco = 1; - filt = (0xFFFFFFFF << (shift)) << 8; - while (*++m) - { - if (IsDigit(*m)) - unco = 1; - else - { - switch (*m) - { - case '.': - if (m[1] != '*') - unco = 1; - if (!shift) - break; - shift -= 8; - continue; - case '?': - unco = 1; - case '*': - continue; - default: - break; - } - break; - } - } - if (*m) - break; - continue; - default: - break; - } - - /* If we get here there is some error and this can't ever match */ - filt = 0; - bits = ~0; - unco = 0; - break; /* This time break the loop :) */ + int class; + char ipname[16]; + int ad[4] = { 0 }; + int bits = 0; + + class = sscanf(in, "%d.%d.%d.%d/%d", &ad[0], &ad[1], &ad[2], &ad[3], &bits); + if (class != 5) + bits = class * 8; + ircd_snprintf(0, ipname, sizeof(ipname), "%d.%d.%d.%d", ad[0], ad[1], ad[2], ad[3]); + out->s_addr = inet_addr(ipname); + return bits; +} +int ipmask_parse(const char *in, struct irc_in_addr *mask, unsigned char *bits_ptr) +{ + struct in_addr ipv4; + char *p; + int bits = 0; + + if (check_if_ipmask(in)) { + bits = ipmask_parse_ipv4(in, &ipv4); + mask->in6_16[0] = mask->in6_16[1] = mask->in6_16[2] = 0; + mask->in6_16[3] = mask->in6_16[4] = mask->in6_16[5] = 0; + memcpy(&mask->in6_16[6], &ipv4.s_addr, sizeof(ipv4.s_addr)); + bits += 96; + } else { + if (!(p = strchr(in, '/'))) + bits = 128; + else + *p = 0; + if (!ircd_aton(mask, in)) { + if (p) + *p = '/'; + return 0; + } + if (p) { + bits = atoi(p + 1); + *p = '/'; + } } - while (*m++); - imask->bits.s_addr = htonl(bits); - imask->mask.s_addr = htonl(filt); - imask->fall = unco; - return ((bits & ~filt) ? -1 : 0); + if (bits_ptr) + *bits_ptr = bits; + return 1; +} +int ipmask_check(const struct irc_in_addr *addr, const struct irc_in_addr *mask, unsigned char bits) +{ + int k; + + for (k = 0; k < 8; k++) { + if (bits < 16) + return (addr->in6_16[k] & ((unsigned char) (0xffff << (16-bits)))) == mask->in6_16[k]; + if (addr->in6_16[k] != mask->in6_16[k]) + return 0; + if (!(bits -= 16)) + return 1; + } + return -1; } diff --git a/ircd/numnicks.c b/ircd/numnicks.c index 8574fe7..781ff6f 100644 --- a/ircd/numnicks.c +++ b/ircd/numnicks.c @@ -369,4 +369,74 @@ struct Client* find_match_server(char *mask) return 0; } +const char* iptobase64(char* buf, const struct irc_in_addr* addr, unsigned int count) +{ + if (irc_in_addr_is_ipv4(addr)) { + assert(count >= 6); + inttobase64(buf, (htons(addr->in6_16[6]) << 16) | htons(addr->in6_16[7]), 6); + } else { + unsigned int max_start, max_zeros, curr_zeros, zero, ii; + char *output = buf; + + assert(count >= 25); + /* Can start by printing out the leading non-zero parts. */ + for (ii = 0; (addr->in6_16[ii]) && (ii < 8); ++ii) { + inttobase64(output, ntohs(addr->in6_16[ii]), 3); + output += 3; + } + /* Find the longest run of zeros. */ + for (max_start = zero = ii, max_zeros = curr_zeros = 0; ii < 8; ++ii) { + if (!addr->in6_16[ii]) + curr_zeros++; + else if (curr_zeros > max_zeros) { + max_start = ii - curr_zeros; + max_zeros = curr_zeros; + curr_zeros = 0; + } + } + if (curr_zeros > max_zeros) { + max_start = ii - curr_zeros; + max_zeros = curr_zeros; + curr_zeros = 0; + } + /* Print the rest of the address */ + for (ii = zero; ii < 8; ) { + if ((ii == max_start) && max_zeros) { + *output++ = '_'; + ii += max_zeros; + } else { + inttobase64(output, ntohs(addr->in6_16[ii]), 3); + output += 3; + ii++; + } + } + *output = '\0'; + } + return buf; +} +void base64toip(const char* input, struct irc_in_addr* addr) +{ + memset(addr, 0, sizeof(*addr)); + if (strlen(input) == 6) { + unsigned int in = base64toint(input); + addr->in6_16[6] = htons(in >> 16); + addr->in6_16[7] = htons(in & 65535); + } else { + unsigned int pos = 0; + do { + if (*input == '_') { + unsigned int left; + for (left = (strlen(input) - 1) / 3; left; left--) + addr->in6_16[pos++] = 0; + input++; + } else { + unsigned short accum = convert2n[(unsigned char)*input++]; + accum = (accum << NUMNICKLOG) | convert2n[(unsigned char)*input++]; + accum = (accum << NUMNICKLOG) | convert2n[(unsigned char)*input++]; + addr->in6_16[pos++] = ntohs(accum); + input += 3; + } + } while (pos < 8); + } +} diff --git a/ircd/os_bsd.c b/ircd/os_bsd.c deleted file mode 100644 index 09850d9..0000000 --- a/ircd/os_bsd.c +++ /dev/null @@ -1,390 +0,0 @@ -/* - * IRC - Internet Relay Chat, ircd/os_generic.c - * Copyright (C) 1999 Thomas Helvey - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 1, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - * - * $Id$ - * - */ -#include "config.h" - -#define _XOPEN_SOURCE /* make limits.h #define IOV_MAX */ - -#include "ircd_osdep.h" -#include "msgq.h" - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#ifndef IOV_MAX -#define IOV_MAX 16 /* minimum required */ -#endif - -#ifdef HPUX -#include -#define getrusage(a,b) syscall(SYS_GETRUSAGE, a, b) -#endif - -/* - * This is part of the STATS replies. There is no offical numeric for this - * since this isnt an official command, in much the same way as HASH isnt. - * It is also possible that some systems wont support this call or have - * different field names for "struct rusage". - * -avalon - */ -int os_get_rusage(struct Client *cptr, int uptime, EnumFn enumerator) -{ -#ifdef HAVE_GETRUSAGE - char buf[256]; - struct rusage rus; - time_t secs; - -#ifdef hz -# define hzz hz -#else -# ifdef HZ -# define hzz HZ -# else - int hzz = 1; -# ifdef HPUX - hzz = sysconf(_SC_CLK_TCK); -# endif -#endif -#endif - - assert(0 != enumerator); - if (getrusage(RUSAGE_SELF, &rus) == -1) - return 0; - - secs = rus.ru_utime.tv_sec + rus.ru_stime.tv_sec; - if (secs == 0) - secs = 1; - - sprintf(buf, "CPU Secs %ld:%ld User %ld:%ld System %ld:%ld", - secs / 60, secs % 60, - rus.ru_utime.tv_sec / 60, rus.ru_utime.tv_sec % 60, - rus.ru_stime.tv_sec / 60, rus.ru_stime.tv_sec % 60); - (*enumerator)(cptr, buf); - - sprintf(buf, "RSS %ld ShMem %ld Data %ld Stack %ld", - rus.ru_maxrss, - rus.ru_ixrss / (uptime * hzz), rus.ru_idrss / (uptime * hzz), - rus.ru_isrss / (uptime * hzz)); - (*enumerator)(cptr, buf); - - sprintf(buf, "Swaps %ld Reclaims %ld Faults %ld", - rus.ru_nswap, rus.ru_minflt, rus.ru_majflt); - (*enumerator)(cptr, buf); - - sprintf(buf, "Block in %ld out %ld", rus.ru_inblock, rus.ru_oublock); - (*enumerator)(cptr, buf); - - sprintf(buf, "Msg Rcv %ld Send %ld", rus.ru_msgrcv, rus.ru_msgsnd); - (*enumerator)(cptr, buf); - - sprintf(buf, "Signals %ld Context Vol. %ld Invol %ld", - rus.ru_nsignals, rus.ru_nvcsw, rus.ru_nivcsw); - (*enumerator)(cptr, buf); - -#else /* HAVE_GETRUSAGE */ -#if HAVE_TIMES - char buf[256]; - struct tms tmsbuf; - time_t secs, mins; - int hzz = 1, ticpermin; - int umin, smin, usec, ssec; - - assert(0 != enumerator); -#ifdef HPUX - hzz = sysconf(_SC_CLK_TCK); -#endif - ticpermin = hzz * 60; - - umin = tmsbuf.tms_utime / ticpermin; - usec = (tmsbuf.tms_utime % ticpermin) / (float)hzz; - smin = tmsbuf.tms_stime / ticpermin; - ssec = (tmsbuf.tms_stime % ticpermin) / (float)hzz; - secs = usec + ssec; - mins = (secs / 60) + umin + smin; - secs %= hzz; - - if (times(&tmsbuf) == -1) - return 0; - secs = tmsbuf.tms_utime + tmsbuf.tms_stime; - - sprintf(buf, "CPU Secs %d:%d User %d:%d System %d:%d", - mins, secs, umin, usec, smin, ssec); - (*enumerator)(cptr, buf); -#endif /* HAVE_TIMES */ -#endif /* HAVE_GETRUSAGE */ - return 1; -} - -int os_get_sockerr(int fd) -{ - int err = 0; -#if defined(SO_ERROR) - unsigned int len = sizeof(err); - getsockopt(fd, SOL_SOCKET, SO_ERROR, &err, &len); -#endif - return err; -} - -/* - * set_non_blocking - * - * Set the client connection into non-blocking mode. If your - * system doesn't support this, you can make this a dummy - * function (and get all the old problems that plagued the - * blocking version of IRC--not a problem if you are a - * lightly loaded node...) - */ -int os_set_nonblocking(int fd) -{ - int res; -#ifndef NBLOCK_SYSV - int nonb = 0; -#endif - - /* - * NOTE: consult ALL your relevant manual pages *BEFORE* changing - * these ioctl's. There are quite a few variations on them, - * as can be seen by the PCS one. They are *NOT* all the same. - * Heed this well. - Avalon. - */ -#ifdef NBLOCK_POSIX - nonb |= O_NONBLOCK; -#endif -#ifdef NBLOCK_BSD - nonb |= O_NDELAY; -#endif -#ifdef NBLOCK_SYSV - /* This portion of code might also apply to NeXT. -LynX */ - res = 1; - - if (ioctl(fd, FIONBIO, &res) == -1) - return 0; -#else - if ((res = fcntl(fd, F_GETFL, 0)) == -1) - return 0; - else if (fcntl(fd, F_SETFL, res | nonb) == -1) - return 0; -#endif - return 1; -} - - -/* - * set_sock_opts - */ -int os_set_reuseaddr(int fd) -{ - unsigned int opt = 1; - return (0 == setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, - (const char*) &opt, sizeof(opt))); -} - -int os_set_sockbufs(int fd, unsigned int ssize, unsigned int rsize) -{ - unsigned int sopt = ssize; - unsigned int ropt = rsize; - return (0 == setsockopt(fd, SOL_SOCKET, SO_RCVBUF, - (const char*) &ropt, sizeof(ropt)) && - 0 == setsockopt(fd, SOL_SOCKET, SO_SNDBUF, - (const char*) &sopt, sizeof(sopt))); -} - -int os_set_tos(int fd,int tos) -{ - unsigned int opt = tos; - return (0 == setsockopt(fd, IPPROTO_IP, IP_TOS, &opt, sizeof(opt))); -} - -int os_disable_options(int fd) -{ -#if defined(IP_OPTIONS) && defined(IPPROTO_IP) - return (0 == setsockopt(fd, IPPROTO_IP, IP_OPTIONS, NULL, 0)); -#else - return 1; -#endif -} - -/* - * Try and find the correct name to use with getrlimit() for setting the max. - * number of files allowed to be open by this process. - */ -#ifdef RLIMIT_FDMAX -#define RLIMIT_FD_MAX RLIMIT_FDMAX -#else -#ifdef RLIMIT_NOFILE -#define RLIMIT_FD_MAX RLIMIT_NOFILE -#else -#ifdef RLIMIT_OPEN_MAX -#define RLIMIT_FD_MAX RLIMIT_OPEN_MAX -#else -#undef RLIMIT_FD_MAX -#endif -#endif -#endif - -int os_set_fdlimit(unsigned int max_descriptors) -{ -#if defined(HAVE_SETRLIMIT) && defined(RLIMIT_FD_MAX) - struct rlimit limit; - - if (!getrlimit(RLIMIT_FD_MAX, &limit)) { - if (limit.rlim_max < MAXCONNECTIONS) - return limit.rlim_max; - limit.rlim_cur = limit.rlim_max; /* make soft limit the max */ - return setrlimit(RLIMIT_FD_MAX, &limit); - } -#endif /* defined(HAVE_SETRLIMIT) && defined(RLIMIT_FD_MAX) */ - return 0; -} - -IOResult os_recv_nonb(int fd, char* buf, unsigned int length, - unsigned int* count_out) -{ - int res; - assert(0 != buf); - assert(0 != count_out); - *count_out = 0; - errno = 0; - - if (0 < (res = recv(fd, buf, length, 0))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (res < 0) { - if (EWOULDBLOCK == errno || EAGAIN == errno) - return IO_BLOCKED; - else - return IO_FAILURE; - } - /* - * 0 == client closed the connection - * < 1 == error - */ - return IO_FAILURE; -} - -IOResult os_recvfrom_nonb(int fd, char* buf, unsigned int length, - unsigned int* length_out, struct sockaddr_in* sin_out) -{ - int res; - unsigned int len = sizeof(struct sockaddr_in); - assert(0 != buf); - assert(0 != length_out); - assert(0 != sin_out); - errno = 0; - *length_out = 0; - - res = recvfrom(fd, buf, length, 0, (struct sockaddr*) sin_out, &len); - if (-1 == res) { - if (EWOULDBLOCK == errno || ENOMEM == errno) - return IO_BLOCKED; - return IO_FAILURE; - } - *length_out = res; - return IO_SUCCESS; -} - -IOResult os_send_nonb(int fd, const char* buf, unsigned int length, - unsigned int* count_out) -{ - int res; - assert(0 != buf); - assert(0 != count_out); - *count_out = 0; - errno = 0; - - if (-1 < (res = send(fd, buf, length, 0))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (EWOULDBLOCK == errno || EAGAIN == errno || - ENOMEM == errno || ENOBUFS == errno) - return IO_BLOCKED; - return IO_FAILURE; -} - -IOResult os_sendv_nonb(int fd, struct MsgQ* buf, unsigned int* count_in, - unsigned int* count_out) -{ - int res; - int count; - struct iovec iov[IOV_MAX]; - - assert(0 != buf); - assert(0 != count_in); - assert(0 != count_out); - - *count_in = 0; - *count_out = 0; - errno = 0; - - count = msgq_mapiov(buf, iov, IOV_MAX, count_in); - - if (-1 < (res = writev(fd, iov, count))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (EWOULDBLOCK == errno || EAGAIN == errno || - ENOMEM == errno || ENOBUFS == errno) - return IO_BLOCKED; - - return IO_FAILURE; -} - -IOResult os_connect_nonb(int fd, const struct sockaddr_in* sin) -{ - if (connect(fd, (struct sockaddr*) sin, sizeof(struct sockaddr_in))) - return (errno == EINPROGRESS) ? IO_BLOCKED : IO_FAILURE; - return IO_SUCCESS; -} - -int os_get_sockname(int fd, struct sockaddr_in* sin_out) -{ - unsigned int len = sizeof(struct sockaddr_in); - assert(0 != sin_out); - return (0 == getsockname(fd, (struct sockaddr*) sin_out, &len)); -} - -int os_get_peername(int fd, struct sockaddr_in* sin_out) -{ - unsigned int len = sizeof(struct sockaddr_in); - assert(0 != sin_out); - return (0 == getpeername(fd, (struct sockaddr*) sin_out, &len)); -} - -int os_set_listen(int fd, int backlog) -{ - return (0 == listen(fd, backlog)); -} - - diff --git a/ircd/os_generic.c b/ircd/os_generic.c index ccd9e80..99750a3 100644 --- a/ircd/os_generic.c +++ b/ircd/os_generic.c @@ -22,9 +22,13 @@ #include "config.h" #define _XOPEN_SOURCE 500 /* make limits.h #define IOV_MAX */ +#define __EXTENSIONS__ 1 /* make Solaris netinet/in.h know IPv6 */ #include "ircd_osdep.h" #include "msgq.h" +#include "res.h" +#include "s_bsd.h" +#include "sys.h" /* Include file dependency notes: * FreeBSD requires struct timeval from sys/time.h before struct @@ -63,6 +67,48 @@ #define getrusage(a,b) syscall(SYS_GETRUSAGE, a, b) #endif +#ifdef IPV6 +#define sockaddr_native sockaddr_in6 + +void sockaddr_to_irc(const struct sockaddr_in6 *v6, struct irc_sockaddr *irc) +{ + assert(v6->sin6_family == AF_INET6); + memcpy(&irc->addr.in6_16[0], &v6->sin6_addr, sizeof(v6->sin6_addr)); + irc->port = ntohs(v6->sin6_port); +} + +void sockaddr_from_irc(struct sockaddr_in6 *v6, const struct irc_sockaddr *irc, int persist) +{ + memset(v6, 0, sizeof(*v6)); + v6->sin6_family = AF_INET6; + memcpy(&v6->sin6_addr, &irc->addr.in6_16[0], sizeof(v6->sin6_addr)); + if (persist && irc_in_addr_is_ipv4(&irc->addr)) + v6->sin6_addr.s6_addr[10] = v6->sin6_addr.s6_addr[11] = '\xff'; + v6->sin6_port = htons(irc->port); +} + +#else +#define sockaddr_native sockaddr_in + +void sockaddr_to_irc(const struct sockaddr_in *v4, struct irc_sockaddr *irc) +{ + assert(v4->sin_family == AF_INET); + memset(&irc->addr, 0, 6*sizeof(irc->addr.in6_16[0])); + memcpy(&irc->addr.in6_16[6], &v4->sin_addr, sizeof(v4->sin_addr)); + irc->port = ntohs(v4->sin_port); +} + +void sockaddr_from_irc(struct sockaddr_in *v4, const struct irc_sockaddr *irc, int persist) +{ + v4->sin_family = AF_INET6; + assert(!irc->addr.in6_16[0] && !irc->addr.in6_16[1] && !irc->addr.in6_16[2] && !irc->addr.in6_16[3] && !irc->addr.in6_16[4] && (!irc->addr.in6_16[5] || irc->addr.in6_16[5] == 0xffff)); + memcpy(&v4->sin_addr, &irc->addr.in6_16[7], sizeof(v4->sin_addr)); + v4->sin_port = htons(irc->port); + (void)persist; +} + +#endif + /* * This is part of the STATS replies. There is no offical numeric for this * since this isnt an official command, in much the same way as HASH isnt. @@ -327,17 +373,19 @@ IOResult os_recv_nonb(int fd, char* buf, unsigned int length, } IOResult os_recvfrom_nonb(int fd, char* buf, unsigned int length, - unsigned int* length_out, struct sockaddr_in* sin_out) + unsigned int* length_out, + struct irc_sockaddr* addr_out) { + struct sockaddr_native addr; + unsigned int len = sizeof(addr); int res; - unsigned int len = sizeof(struct sockaddr_in); assert(0 != buf); assert(0 != length_out); - assert(0 != sin_out); + assert(0 != addr_out); errno = 0; *length_out = 0; - res = recvfrom(fd, buf, length, 0, (struct sockaddr*) sin_out, &len); + res = recvfrom(fd, buf, length, 0, (struct sockaddr*) &addr, &len); if (-1 == res) { if (EWOULDBLOCK == errno || ENOMEM == errno #ifdef ENOMEM @@ -350,10 +398,47 @@ IOResult os_recvfrom_nonb(int fd, char* buf, unsigned int length, return IO_BLOCKED; return IO_FAILURE; } + sockaddr_to_irc(&addr, addr_out); *length_out = res; return IO_SUCCESS; } +/* + * os_sendto_nonb - non blocking send to a UDP socket + * returns: + * 1 if data was written, *count_out contains number of bytes + * 0 if sendto call blocked + * -1 if an unrecoverable error occurred + */ +IOResult os_sendto_nonb(int fd, const char* buf, unsigned int length, + unsigned int* count_out, unsigned int flags, + const struct irc_sockaddr* peer) +{ + struct sockaddr_native addr; + int res; + assert(0 != buf); + if (count_out) + *count_out = 0; + errno = 0; + + sockaddr_from_irc(&addr, peer, 1); + if (-1 < (res = sendto(fd, buf, length, flags, (struct sockaddr*)&addr, sizeof(addr)))) { + if (count_out) + *count_out = (unsigned) res; + return IO_SUCCESS; + } + else if (EWOULDBLOCK == errno || EAGAIN == errno +#ifdef ENOMEM + || ENOMEM == errno +#endif +#ifdef ENOBUFS + || ENOBUFS == errno +#endif + ) + return IO_BLOCKED; + return IO_FAILURE; +} + /* * os_send_nonb - non blocking read of a connection * returns: @@ -422,25 +507,92 @@ IOResult os_sendv_nonb(int fd, struct MsgQ* buf, unsigned int* count_in, return IO_FAILURE; } -IOResult os_connect_nonb(int fd, const struct sockaddr_in* sin) +int os_socket(const struct irc_sockaddr* local, int type, const char* port_name) +{ + int family, fd; +#ifdef IPV6 + family = AF_INET6; +#else + family = AF_INET; +#endif + fd = socket(family, type, 0); + if (fd < 0) { + report_error(SOCKET_ERROR_MSG, port_name, errno); + return -1; + } + if (fd > MAXCLIENTS - 1) { + report_error(CONNLIMIT_ERROR_MSG, port_name, 0); + close(fd); + return -1; + } + if (!os_set_reuseaddr(fd)) { + report_error(REUSEADDR_ERROR_MSG, port_name, errno); + close(fd); + return -1; + } + if (!os_set_nonblocking(fd)) { + report_error(NONB_ERROR_MSG, port_name, errno); + close(fd); + return -1; + } + if (local) { + struct sockaddr_native addr; + sockaddr_from_irc(&addr, local, 1); + if (bind(fd, (struct sockaddr*)&addr, sizeof(addr))) { + report_error(BIND_ERROR_MSG, port_name, errno); + close(fd); + return -1; + } + } + return fd; +} + +int os_accept(int fd, struct irc_sockaddr* peer) { - if (connect(fd, (struct sockaddr*) sin, sizeof(struct sockaddr_in))) + struct sockaddr_native addr; + socklen_t addrlen; + int new_fd; + + addrlen = sizeof(addr); + new_fd = accept(fd, (struct sockaddr*)&addr, &addrlen); + if (new_fd < 0) + memset(peer, 0, sizeof(*peer)); + else + sockaddr_to_irc(&addr, peer); + return new_fd; +} + +IOResult os_connect_nonb(int fd, const struct irc_sockaddr* sin) +{ + struct sockaddr_native addr; + sockaddr_from_irc(&addr, sin, 1); + if (connect(fd, (struct sockaddr*) &addr, sizeof(addr))) return (errno == EINPROGRESS) ? IO_BLOCKED : IO_FAILURE; return IO_SUCCESS; } -int os_get_sockname(int fd, struct sockaddr_in* sin_out) +int os_get_sockname(int fd, struct irc_sockaddr* sin_out) { - unsigned int len = sizeof(struct sockaddr_in); + struct sockaddr_native addr; + unsigned int len = sizeof(addr); + assert(0 != sin_out); - return (0 == getsockname(fd, (struct sockaddr*) sin_out, &len)); + if (getsockname(fd, (struct sockaddr*) &addr, &len)) + return 0; + sockaddr_to_irc(&addr, sin_out); + return 1; } -int os_get_peername(int fd, struct sockaddr_in* sin_out) +int os_get_peername(int fd, struct irc_sockaddr* sin_out) { - unsigned int len = sizeof(struct sockaddr_in); + struct sockaddr_native addr; + unsigned int len = sizeof(addr); + assert(0 != sin_out); - return (0 == getpeername(fd, (struct sockaddr*) sin_out, &len)); + if (getpeername(fd, (struct sockaddr*) &addr, &len)) + return 0; + sockaddr_to_irc(&addr, sin_out); + return 1; } int os_set_listen(int fd, int backlog) diff --git a/ircd/os_linux.c b/ircd/os_linux.c deleted file mode 100644 index 2c24bb1..0000000 --- a/ircd/os_linux.c +++ /dev/null @@ -1,337 +0,0 @@ -/* - * IRC - Internet Relay Chat, ircd/os_linux.c - * Copyright (C) 1999 Thomas Helvey - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 1, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - * - * $Id$ - * - */ -#include "config.h" - -#define _XOPEN_SOURCE /* make limits.h #define IOV_MAX */ - -#include "ircd_osdep.h" -#include "msgq.h" - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -/* - * This is part of the STATS replies. There is no offical numeric for this - * since this isnt an official command, in much the same way as HASH isnt. - * It is also possible that some systems wont support this call or have - * different field names for "struct rusage". - * -avalon - */ -int os_get_rusage(struct Client *cptr, int uptime, EnumFn enumerator) -{ - char buf[256]; - struct rusage rus; - struct tms tmsbuf; - time_t secs; - time_t mins; - int umin; - int smin; - int usec; - int ssec; - int ticpermin = HZ * 60; - unsigned int tick_count = uptime * HZ; - - if (0 == tick_count) - ++tick_count; - - assert(0 != enumerator); - if (getrusage(RUSAGE_SELF, &rus) == -1) - return 0; - - secs = rus.ru_utime.tv_sec + rus.ru_stime.tv_sec; - if (secs == 0) - secs = 1; - - sprintf(buf, "CPU Secs %ld:%ld User %ld:%ld System %ld:%ld", - secs / 60, secs % 60, - rus.ru_utime.tv_sec / 60, rus.ru_utime.tv_sec % 60, - rus.ru_stime.tv_sec / 60, rus.ru_stime.tv_sec % 60); - (*enumerator)(cptr, buf); - - sprintf(buf, "RSS %ld ShMem %ld Data %ld Stack %ld", - rus.ru_maxrss, - rus.ru_ixrss / tick_count, rus.ru_idrss / tick_count, - rus.ru_isrss / tick_count); - (*enumerator)(cptr, buf); - - sprintf(buf, "Swaps %ld Reclaims %ld Faults %ld", - rus.ru_nswap, rus.ru_minflt, rus.ru_majflt); - (*enumerator)(cptr, buf); - - sprintf(buf, "Block in %ld out %ld", rus.ru_inblock, rus.ru_oublock); - (*enumerator)(cptr, buf); - - sprintf(buf, "Msg Rcv %ld Send %ld", rus.ru_msgrcv, rus.ru_msgsnd); - (*enumerator)(cptr, buf); - - sprintf(buf, "Signals %ld Context Vol. %ld Invol %ld", - rus.ru_nsignals, rus.ru_nvcsw, rus.ru_nivcsw); - (*enumerator)(cptr, buf); - - if (times(&tmsbuf) == -1) - return 0; - - umin = tmsbuf.tms_utime / ticpermin; - usec = (tmsbuf.tms_utime % ticpermin) / (float)HZ; - smin = tmsbuf.tms_stime / ticpermin; - ssec = (tmsbuf.tms_stime % ticpermin) / (float)HZ; - secs = usec + ssec; - mins = (secs / 60) + umin + smin; - secs %= HZ; - - sprintf(buf, "CPU Secs %ld:%ld User %d:%d System %d:%d", - mins, secs, umin, usec, smin, ssec); - (*enumerator)(cptr, buf); - return 1; -} - -int os_get_sockerr(int fd) -{ - int err = 0; - unsigned int len = sizeof(err); - getsockopt(fd, SOL_SOCKET, SO_ERROR, &err, &len); - return err; -} - -/* - * set_non_blocking - * - * Set the client connection into non-blocking mode. If your - * system doesn't support this, you can make this a dummy - * function (and get all the old problems that plagued the - * blocking version of IRC--not a problem if you are a - * lightly loaded node...) - */ -int os_set_nonblocking(int fd) -{ - int res = 1; - return (0 == ioctl(fd, FIONBIO, &res)); -} - - -/* - * set_sock_opts - */ -int os_set_reuseaddr(int fd) -{ - unsigned int opt = 1; - return (0 == setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt))); -} - -int os_set_sockbufs(int fd, unsigned int ssize, unsigned int rsize) -{ - unsigned int sopt = ssize; - unsigned int ropt = rsize; - return (0 == setsockopt(fd, SOL_SOCKET, SO_RCVBUF, - (const char*) &ropt, sizeof(ropt)) && - 0 == setsockopt(fd, SOL_SOCKET, SO_SNDBUF, - (const char*) &sopt, sizeof(sopt))); -} - -int os_set_tos(int fd,int tos) -{ - unsigned int opt = tos; - return (0 == setsockopt(fd, SOL_IP, IP_TOS, &opt, sizeof(opt))); -} - -int os_disable_options(int fd) -{ - return (0 == setsockopt(fd, IPPROTO_IP, IP_OPTIONS, NULL, 0)); -} - -int os_set_fdlimit(unsigned int max_descriptors) -{ - struct rlimit limit; - - if (!getrlimit(RLIMIT_NOFILE, &limit)) { - if (limit.rlim_max < max_descriptors) - return limit.rlim_max; - limit.rlim_cur = limit.rlim_max; /* make soft limit the max */ - return setrlimit(RLIMIT_NOFILE, &limit); - } - return 0; -} - -/* - * os_recv_nonb - non blocking read of a connection - * returns: - * 1 if data was read or socket is blocked (recoverable error) - * count_out > 0 if data was read - * - * 0 if socket closed from other end - * -1 if an unrecoverable error occurred - */ -IOResult os_recv_nonb(int fd, char* buf, unsigned int length, - unsigned int* count_out) -{ - int res; - assert(0 != buf); - assert(0 != count_out); - *count_out = 0; - errno = 0; - - if (0 < (res = recv(fd, buf, length, 0))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (res < 0) { - if (EWOULDBLOCK == errno || EAGAIN == errno) - return IO_BLOCKED; - else - return IO_FAILURE; - } - /* - * 0 == client closed the connection - * < 1 == error - */ - return IO_FAILURE; -} - -IOResult os_recvfrom_nonb(int fd, char* buf, unsigned int length, - unsigned int* length_out, struct sockaddr_in* sin_out) -{ - int res; - unsigned int len = sizeof(struct sockaddr_in); - assert(0 != buf); - assert(0 != length_out); - assert(0 != sin_out); - errno = 0; - - res = recvfrom(fd, buf, length, 0, (struct sockaddr*) sin_out, &len); - if (-1 == res) { - if (EWOULDBLOCK == errno || ENOMEM == errno) - return IO_BLOCKED; - return IO_FAILURE; - } - *length_out = res; - return IO_SUCCESS; -} - -/* - * os_send_nonb - non blocking read of a connection - * returns: - * 1 if data was written - * count_out contains amount written - * - * 0 if write call blocked, recoverable error - * -1 if an unrecoverable error occurred - */ -IOResult os_send_nonb(int fd, const char* buf, unsigned int length, - unsigned int* count_out) -{ - int res; - assert(0 != buf); - assert(0 != count_out); - *count_out = 0; - errno = 0; - - if (-1 < (res = send(fd, buf, length, 0))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (EAGAIN == errno || ENOMEM == errno || ENOBUFS == errno) - return IO_BLOCKED; - - return IO_FAILURE; -} - -/* - * os_sendv_nonb - non blocking writev to a connection - * returns: - * 1 if data was written - * count_out contains amount written - * - * 0 if write call blocked, recoverable error - * -1 if an unrecoverable error occurred - */ -IOResult os_sendv_nonb(int fd, struct MsgQ* buf, unsigned int* count_in, - unsigned int* count_out) -{ - int res; - int count; - struct iovec iov[IOV_MAX]; - - assert(0 != buf); - assert(0 != count_in); - assert(0 != count_out); - - *count_in = 0; - *count_out = 0; - errno = 0; - - count = msgq_mapiov(buf, iov, IOV_MAX, count_in); - - if (-1 < (res = writev(fd, iov, count))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (EAGAIN == errno || ENOMEM == errno || ENOBUFS == errno) - return IO_BLOCKED; - - return IO_FAILURE; -} - - -IOResult os_connect_nonb(int fd, const struct sockaddr_in* sin) -{ - if (connect(fd, (const struct sockaddr*) sin, sizeof(struct sockaddr_in))) - return (errno == EINPROGRESS) ? IO_BLOCKED : IO_FAILURE; - return IO_SUCCESS; -} - -int os_get_sockname(int fd, struct sockaddr_in* sin_out) -{ - unsigned int len = sizeof(struct sockaddr_in); - assert(0 != sin_out); - return (0 == getsockname(fd, (struct sockaddr*) sin_out, &len)); -} - -int os_get_peername(int fd, struct sockaddr_in* sin_out) -{ - unsigned int len = sizeof(struct sockaddr_in); - assert(0 != sin_out); - return (0 == getpeername(fd, (struct sockaddr*) sin_out, &len)); -} - -int os_set_listen(int fd, int backlog) -{ - /* - * for linux 2.2 backlog is the number of connections ready to be accepted - * not the max syn requests, there is a kernel tweak there to set the max - * syn request queue length - */ - return (0 == listen(fd, backlog)); -} - diff --git a/ircd/os_openbsd.c b/ircd/os_openbsd.c deleted file mode 100644 index 27c5ded..0000000 --- a/ircd/os_openbsd.c +++ /dev/null @@ -1,397 +0,0 @@ -/* - * IRC - Internet Relay Chat, ircd/os_openbsd.c - * Copyright (C) 2001 Joseph Bongaarts - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 1, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - * - * $Id$ - * - */ -#include "config.h" - -#define _XOPEN_SOURCE /* Need this for IOV_MAX */ - -/* These typedef's are needed for socket.h to be happy. Bleep PROMISES to make - * to make this less hackish in the future... HONEST. -GW - */ -typedef unsigned char u_char; -typedef unsigned short u_short; -typedef unsigned int u_int; -typedef unsigned long u_long; - -#include "ircd_osdep.h" -#include "msgq.h" - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#ifndef IOV_MAX -#define IOV_MAX 16 /* minimum required */ -#endif - -#ifdef HPUX -#include -#define getrusage(a,b) syscall(SYS_GETRUSAGE, a, b) -#endif - -/* - * This is part of the STATS replies. There is no offical numeric for this - * since this isnt an official command, in much the same way as HASH isnt. - * It is also possible that some systems wont support this call or have - * different field names for "struct rusage". - * -avalon - */ -int os_get_rusage(struct Client *cptr, int uptime, EnumFn enumerator) -{ - char buf[256]; -#ifdef HAVE_GETRUSAGE - struct rusage rus; - time_t secs; - -#ifdef hz -# define hzz hz -#else -# ifdef HZ -# define hzz HZ -# else - int hzz = 1; -# ifdef HPUX - hzz = sysconf(_SC_CLK_TCK); -# endif -#endif -#endif - - assert(0 != enumerator); - if (getrusage(RUSAGE_SELF, &rus) == -1) - return 0; - - secs = rus.ru_utime.tv_sec + rus.ru_stime.tv_sec; - if (secs == 0) - secs = 1; - - sprintf(buf, "CPU Secs %ld:%ld User %ld:%ld System %ld:%ld", - secs / 60, secs % 60, - rus.ru_utime.tv_sec / 60, rus.ru_utime.tv_sec % 60, - rus.ru_stime.tv_sec / 60, rus.ru_stime.tv_sec % 60); - (*enumerator)(cptr, buf); - - sprintf(buf, "RSS %ld ShMem %ld Data %ld Stack %ld", - rus.ru_maxrss, - rus.ru_ixrss / (uptime * hzz), rus.ru_idrss / (uptime * hzz), - rus.ru_isrss / (uptime * hzz)); - (*enumerator)(cptr, buf); - - sprintf(buf, "Swaps %ld Reclaims %ld Faults %ld", - rus.ru_nswap, rus.ru_minflt, rus.ru_majflt); - (*enumerator)(cptr, buf); - - sprintf(buf, "Block in %ld out %ld", rus.ru_inblock, rus.ru_oublock); - (*enumerator)(cptr, buf); - - sprintf(buf, "Msg Rcv %ld Send %ld", rus.ru_msgrcv, rus.ru_msgsnd); - (*enumerator)(cptr, buf); - - sprintf(buf, "Signals %ld Context Vol. %ld Invol %ld", - rus.ru_nsignals, rus.ru_nvcsw, rus.ru_nivcsw); - (*enumerator)(cptr, buf); - -#else /* HAVE_GETRUSAGE */ -#if HAVE_TIMES - struct tms tmsbuf; - time_t secs, mins; - int hzz = 1, ticpermin; - int umin, smin, usec, ssec; - - assert(0 != enumerator); -#ifdef HPUX - hzz = sysconf(_SC_CLK_TCK); -#endif - ticpermin = hzz * 60; - - umin = tmsbuf.tms_utime / ticpermin; - usec = (tmsbuf.tms_utime % ticpermin) / (float)hzz; - smin = tmsbuf.tms_stime / ticpermin; - ssec = (tmsbuf.tms_stime % ticpermin) / (float)hzz; - secs = usec + ssec; - mins = (secs / 60) + umin + smin; - secs %= hzz; - - if (times(&tmsbuf) == -1) - return 0; - secs = tmsbuf.tms_utime + tmsbuf.tms_stime; - - sprintf(buf, "CPU Secs %d:%d User %d:%d System %d:%d", - mins, secs, umin, usec, smin, ssec); - (*enumerator)(cptr, buf); -#endif /* HAVE_TIMES */ -#endif /* HAVE_GETRUSAGE */ - return 1; -} - -int os_get_sockerr(int fd) -{ - int err = 0; -#if defined(SO_ERROR) - unsigned int len = sizeof(err); - getsockopt(fd, SOL_SOCKET, SO_ERROR, &err, &len); -#endif - return err; -} - -/* - * set_non_blocking - * - * Set the client connection into non-blocking mode. If your - * system doesn't support this, you can make this a dummy - * function (and get all the old problems that plagued the - * blocking version of IRC--not a problem if you are a - * lightly loaded node...) - */ -int os_set_nonblocking(int fd) -{ - int res; -#ifndef NBLOCK_SYSV - int nonb = 0; -#endif - - /* - * NOTE: consult ALL your relevant manual pages *BEFORE* changing - * these ioctl's. There are quite a few variations on them, - * as can be seen by the PCS one. They are *NOT* all the same. - * Heed this well. - Avalon. - */ -#ifdef NBLOCK_POSIX - nonb |= O_NONBLOCK; -#endif -#ifdef NBLOCK_BSD - nonb |= O_NDELAY; -#endif -#ifdef NBLOCK_SYSV - /* This portion of code might also apply to NeXT. -LynX */ - res = 1; - - if (ioctl(fd, FIONBIO, &res) == -1) - return 0; -#else - if ((res = fcntl(fd, F_GETFL, 0)) == -1) - return 0; - else if (fcntl(fd, F_SETFL, res | nonb) == -1) - return 0; -#endif - return 1; -} - - -/* - * set_sock_opts - */ -int os_set_reuseaddr(int fd) -{ - unsigned int opt = 1; - return (0 == setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, - (const char*) &opt, sizeof(opt))); -} - -int os_set_sockbufs(int fd, unsigned int ssize, unsigned int rsize) -{ - unsigned int sopt = ssize; - unsigned int ropt = rsize; - return (0 == setsockopt(fd, SOL_SOCKET, SO_RCVBUF, - (const char*) &ropt, sizeof(ropt)) && - 0 == setsockopt(fd, SOL_SOCKET, SO_SNDBUF, - (const char*) &sopt, sizeof(sopt))); -} - -int os_set_tos(int fd,int tos) -{ - unsigned int opt = tos; - return (0 == setsockopt(fd, IPPROTO_IP, IP_TOS, &opt, sizeof(opt))); -} - -int os_disable_options(int fd) -{ -#if defined(IP_OPTIONS) && defined(IPPROTO_IP) - return (0 == setsockopt(fd, IPPROTO_IP, IP_OPTIONS, NULL, 0)); -#else - return 1; -#endif -} - -/* - * Try and find the correct name to use with getrlimit() for setting the max. - * number of files allowed to be open by this process. - */ -#ifdef RLIMIT_FDMAX -#define RLIMIT_FD_MAX RLIMIT_FDMAX -#else -#ifdef RLIMIT_NOFILE -#define RLIMIT_FD_MAX RLIMIT_NOFILE -#else -#ifdef RLIMIT_OPEN_MAX -#define RLIMIT_FD_MAX RLIMIT_OPEN_MAX -#else -#undef RLIMIT_FD_MAX -#endif -#endif -#endif - -int os_set_fdlimit(unsigned int max_descriptors) -{ -#if defined(HAVE_SETRLIMIT) && defined(RLIMIT_FD_MAX) - struct rlimit limit; - - if (!getrlimit(RLIMIT_FD_MAX, &limit)) { - if (limit.rlim_max < MAXCONNECTIONS) - return limit.rlim_max; - limit.rlim_cur = limit.rlim_max; /* make soft limit the max */ - return setrlimit(RLIMIT_FD_MAX, &limit); - } -#endif /* defined(HAVE_SETRLIMIT) && defined(RLIMIT_FD_MAX) */ - return 0; -} - -IOResult os_recv_nonb(int fd, char* buf, unsigned int length, - unsigned int* count_out) -{ - int res; - assert(0 != buf); - assert(0 != count_out); - *count_out = 0; - errno = 0; - - if (0 < (res = recv(fd, buf, length, 0))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (res < 0) { - if (EWOULDBLOCK == errno || EAGAIN == errno) - return IO_BLOCKED; - else - return IO_FAILURE; - } - /* - * 0 == client closed the connection - * < 1 == error - */ - return IO_FAILURE; -} - -IOResult os_recvfrom_nonb(int fd, char* buf, unsigned int length, - unsigned int* length_out, struct sockaddr_in* sin_out) -{ - int res; - unsigned int len = sizeof(struct sockaddr_in); - assert(0 != buf); - assert(0 != length_out); - assert(0 != sin_out); - errno = 0; - *length_out = 0; - - res = recvfrom(fd, buf, length, 0, (struct sockaddr*) sin_out, &len); - if (-1 == res) { - if (EWOULDBLOCK == errno || ENOMEM == errno) - return IO_BLOCKED; - return IO_FAILURE; - } - *length_out = res; - return IO_SUCCESS; -} - -IOResult os_send_nonb(int fd, const char* buf, unsigned int length, - unsigned int* count_out) -{ - int res; - assert(0 != buf); - assert(0 != count_out); - *count_out = 0; - errno = 0; - - if (-1 < (res = send(fd, buf, length, 0))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (EWOULDBLOCK == errno || EAGAIN == errno || - ENOMEM == errno || ENOBUFS == errno) - return IO_BLOCKED; - return IO_FAILURE; -} - -IOResult os_sendv_nonb(int fd, struct MsgQ* buf, unsigned int* count_in, - unsigned int* count_out) -{ - int res; - int count; - struct iovec iov[IOV_MAX]; - - assert(0 != buf); - assert(0 != count_in); - assert(0 != count_out); - - *count_in = 0; - *count_out = 0; - errno = 0; - - count = msgq_mapiov(buf, iov, IOV_MAX, count_in); - - if (-1 < (res = writev(fd, iov, count))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (EWOULDBLOCK == errno || EAGAIN == errno || - ENOMEM == errno || ENOBUFS == errno) - return IO_BLOCKED; - - return IO_FAILURE; -} - -IOResult os_connect_nonb(int fd, const struct sockaddr_in* sin) -{ - if (connect(fd, (struct sockaddr*) sin, sizeof(struct sockaddr_in))) - return (errno == EINPROGRESS) ? IO_BLOCKED : IO_FAILURE; - return IO_SUCCESS; -} - -int os_get_sockname(int fd, struct sockaddr_in* sin_out) -{ - unsigned int len = sizeof(struct sockaddr_in); - assert(0 != sin_out); - return (0 == getsockname(fd, (struct sockaddr*) sin_out, &len)); -} - -int os_get_peername(int fd, struct sockaddr_in* sin_out) -{ - unsigned int len = sizeof(struct sockaddr_in); - assert(0 != sin_out); - return (0 == getpeername(fd, (struct sockaddr*) sin_out, &len)); -} - -int os_set_listen(int fd, int backlog) -{ - return (0 == listen(fd, backlog)); -} - - diff --git a/ircd/os_solaris.c b/ircd/os_solaris.c deleted file mode 100644 index 9452c0c..0000000 --- a/ircd/os_solaris.c +++ /dev/null @@ -1,283 +0,0 @@ -/* - * IRC - Internet Relay Chat, ircd/os_solaris.c - * Copyright (C) 1999 Thomas Helvey - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 1, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - * - * $Id$ - * - */ -#include "config.h" - -#include "ircd_osdep.h" -#include "msgq.h" - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -/* - * This is part of the STATS replies. There is no offical numeric for this - * since this isnt an official command, in much the same way as HASH isnt. - * It is also possible that some systems wont support this call or have - * different field names for "struct rusage". - * -avalon - */ -int os_get_rusage(struct Client *cptr, int uptime, EnumFn enumerator) -{ - char buf[256]; - struct rusage rus; - time_t secs; - int hz = HZ; - int upticks = uptime * hz; - - assert(0 != enumerator); - if (getrusage(RUSAGE_SELF, &rus) == -1) - return 0; - - secs = rus.ru_utime.tv_sec + rus.ru_stime.tv_sec; - if (secs == 0) - secs = 1; - - sprintf(buf, "CPU Secs %ld:%ld User %ld:%ld System %ld:%ld", - secs / 60, secs % 60, - rus.ru_utime.tv_sec / 60, rus.ru_utime.tv_sec % 60, - rus.ru_stime.tv_sec / 60, rus.ru_stime.tv_sec % 60); - (*enumerator)(cptr, buf); - - sprintf(buf, "RSS %ld ShMem %ld Data %ld Stack %ld", - rus.ru_maxrss, - rus.ru_ixrss / upticks, rus.ru_idrss / upticks, - rus.ru_isrss / upticks); - (*enumerator)(cptr, buf); - - sprintf(buf, "Swaps %ld Reclaims %ld Faults %ld", - rus.ru_nswap, rus.ru_minflt, rus.ru_majflt); - (*enumerator)(cptr, buf); - - sprintf(buf, "Block in %ld out %ld", rus.ru_inblock, rus.ru_oublock); - (*enumerator)(cptr, buf); - - sprintf(buf, "Msg Rcv %ld Send %ld", rus.ru_msgrcv, rus.ru_msgsnd); - (*enumerator)(cptr, buf); - - sprintf(buf, "Signals %ld Context Vol. %ld Invol %ld", - rus.ru_nsignals, rus.ru_nvcsw, rus.ru_nivcsw); - (*enumerator)(cptr, buf); - - return 1; -} - -int os_get_sockerr(int fd) -{ - int err = 0; - int len = sizeof(err); - getsockopt(fd, SOL_SOCKET, SO_ERROR, (void*) &err, &len); - return err; -} - -/* - * set_non_blocking - * - * Set the client connection into non-blocking mode. If your - * system doesn't support this, you can make this a dummy - * function (and get all the old problems that plagued the - * blocking version of IRC--not a problem if you are a - * lightly loaded node...) - */ -int os_set_nonblocking(int fd) -{ - int res = 1; - return (0 == ioctl(fd, FIONBIO, &res)); -} - -/* - * set_sock_opts - */ -int os_set_reuseaddr(int fd) -{ - unsigned int opt = 1; - return (0 == setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, - (const char*) &opt, sizeof(opt))); -} - -int os_set_sockbufs(int fd, unsigned int ssize, unsigned int rsize) -{ - unsigned int sopt = ssize; - unsigned int ropt = rsize; - return (0 == setsockopt(fd, SOL_SOCKET, SO_RCVBUF, - (const char*) &ropt, sizeof(ropt)) && - 0 == setsockopt(fd, SOL_SOCKET, SO_SNDBUF, - (const char*) &sopt, sizeof(sopt))); -} - -int os_set_tos(int fd,int tos) -{ - unsigned int opt = tos; - return (0 == setsockopt(fd, IPPROTO_IP, IP_TOS, &opt, sizeof(opt))); -} - -int os_disable_options(int fd) -{ - return (0 == setsockopt(fd, IPPROTO_IP, IP_OPTIONS, NULL, 0)); -} - -int os_set_fdlimit(unsigned int max_descriptors) -{ - struct rlimit limit; - - if (!getrlimit(RLIMIT_NOFILE, &limit)) { - if (limit.rlim_max < max_descriptors) - return limit.rlim_max; - limit.rlim_cur = limit.rlim_max; /* make soft limit the max */ - return setrlimit(RLIMIT_NOFILE, &limit); - } - return 0; -} - -IOResult os_recv_nonb(int fd, char* buf, unsigned int length, - unsigned int* count_out) -{ - int res; - assert(0 != buf); - assert(0 != count_out); - *count_out = 0; - errno = 0; - - if (0 < (res = recv(fd, buf, length, 0))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (res < 0) { - if (EAGAIN == errno || ENOBUFS == errno || - ENOMEM == errno || ENOSR == errno) - return IO_BLOCKED; - else - return IO_FAILURE; - } - /* - * 0 == client closed the connection - * < 1 == error - */ - return IO_FAILURE; -} - -IOResult os_recvfrom_nonb(int fd, char* buf, unsigned int length, - unsigned int* length_out, struct sockaddr_in* sin_out) -{ - int res; - unsigned int len = sizeof(struct sockaddr_in); - assert(0 != buf); - assert(0 != length_out); - assert(0 != sin_out); - errno = 0; - - res = recvfrom(fd, buf, length, 0, (struct sockaddr*) sin_out, &len); - if (-1 == res) { - if (EAGAIN == errno || ENOBUFS == errno || - ENOMEM == errno || ENOSR == errno) - return IO_BLOCKED; - return IO_FAILURE; - } - *length_out = res; - return IO_SUCCESS; -} - -IOResult os_send_nonb(int fd, const char* buf, unsigned int length, - unsigned int* count_out) -{ - int res; - assert(0 != buf); - assert(0 != count_out); - *count_out = 0; - errno = 0; - - if (-1 < (res = send(fd, buf, length, 0))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (EAGAIN == errno || ENOBUFS == errno || - ENOMEM == errno || ENOSR == errno) - return IO_BLOCKED; - - return IO_FAILURE; -} - -IOResult os_sendv_nonb(int fd, struct MsgQ* buf, unsigned int* count_in, - unsigned int* count_out) -{ - int res; - int count; - struct iovec iov[IOV_MAX]; - - assert(0 != buf); - assert(0 != count_in); - assert(0 != count_out); - - *count_in = 0; - *count_out = 0; - errno = 0; - - count = msgq_mapiov(buf, iov, IOV_MAX, count_in); - - if (-1 < (res = writev(fd, iov, count))) { - *count_out = (unsigned) res; - return IO_SUCCESS; - } - else if (EAGAIN == errno || ENOBUFS == errno || - ENOMEM == errno || ENOSR == errno) - return IO_BLOCKED; - - return IO_FAILURE; -} - -IOResult os_connect_nonb(int fd, const struct sockaddr_in* sin) -{ - if (connect(fd, (struct sockaddr*) sin, sizeof(struct sockaddr_in))) - return (errno == EINPROGRESS) ? IO_BLOCKED : IO_FAILURE; - return IO_SUCCESS; -} - -int os_get_sockname(int fd, struct sockaddr_in* sin_out) -{ - int len = sizeof(struct sockaddr_in); - assert(0 != sin_out); - return (0 == getsockname(fd, (struct sockaddr*) sin_out, &len)); -} - -int os_get_peername(int fd, struct sockaddr_in* sin_out) -{ - int len = sizeof(struct sockaddr_in); - assert(0 != sin_out); - return (0 == getpeername(fd, (struct sockaddr*) sin_out, &len)); -} - -int os_set_listen(int fd, int backlog) -{ - return (0 == listen(fd, backlog)); -} - diff --git a/ircd/res_adns.c b/ircd/res_adns.c deleted file mode 100644 index d64ea6b..0000000 --- a/ircd/res_adns.c +++ /dev/null @@ -1,786 +0,0 @@ -/* - * src/res.c (C)opyright 1992 Darren Reed. All rights reserved. - * This file may not be distributed without the author's permission in any - * shape or form. The author takes no responsibility for any damage or loss - * of property which results from the use of this software. - * - * $Id$ - * - * July 1999 - Rewrote a bunch of stuff here. Change hostent builder code, - * added callbacks and reference counting of returned hostents. - * --Bleep (Thomas Helvey ) - */ -#include "config.h" - -#include "adns.h" -#include "res.h" -#include "client.h" -#include "ircd.h" -#include "ircd_alloc.h" -#include "ircd_events.h" -#include "ircd_log.h" -#include "ircd_osdep.h" -#include "ircd_reply.h" -#include "ircd_snprintf.h" -#include "ircd_string.h" -#include "msg.h" -#include "numeric.h" -#include "s_bsd.h" -#include "s_debug.h" -#include "s_misc.h" -#include "send.h" -#include "struct.h" -#include "support.h" -#include "sys.h" - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include - -#include -#if (CHAR_BIT != 8) -#error this code needs to be able to address individual octets -#endif - -/* - * Some systems do not define INADDR_NONE (255.255.255.255) - * INADDR_NONE is actually a valid address, but it should never - * be returned from any nameserver. - * NOTE: The bit pattern for INADDR_NONE and INADDR_ANY (0.0.0.0) should be - * the same on all hosts so we shouldn't need to use htonl or ntohl to - * compare or set the values. - */ -#ifndef INADDR_NONE -#define INADDR_NONE ((unsigned int) 0xffffffff) -#endif - -#define MAXPACKET 1024 /* rfc sez 512 but we expand names so ... */ -#define RES_MAXALIASES 35 /* maximum aliases allowed */ -#define RES_MAXADDRS 35 /* maximum addresses allowed */ -/* - * OSF1 doesn't have RES_NOALIASES - */ -#ifndef RES_NOALIASES -#define RES_NOALIASES 0 -#endif - -/* - * macros used to calulate offsets into fixed query buffer - */ -#define ALIAS_BLEN ((RES_MAXALIASES + 1) * sizeof(char*)) -#define ADDRS_BLEN ((RES_MAXADDRS + 1) * sizeof(struct in_addr*)) - -#define ADDRS_OFFSET (ALIAS_BLEN + ADDRS_BLEN) -#define ADDRS_DLEN (RES_MAXADDRS * sizeof(struct in_addr)) -#define NAMES_OFFSET (ADDRS_OFFSET + ADDRS_DLEN) -#define MAXGETHOSTLEN (NAMES_OFFSET + MAXPACKET) - -#define AR_TTL 600 /* TTL in seconds for dns cache entries */ - -/* - * the following values should be prime - */ -#define ARES_CACSIZE 307 -#define MAXCACHED 17 -//#define MAXCACHED 281 - -/* - * Building the Hostent - * The Hostent struct is arranged like this: - * +-------------------------------+ - * Hostent: | struct hostent h | - * |-------------------------------| - * | char *buf | - * +-------------------------------+ - * - * allocated: - * - * +-------------------------------+ - * buf: | h_aliases pointer array | Max size: ALIAS_BLEN; - * | NULL | contains `char *'s - * |-------------------------------| - * | h_addr_list pointer array | Max size: ADDRS_BLEN; - * | NULL | contains `struct in_addr *'s - * |-------------------------------| - * | h_addr_list addresses | Max size: ADDRS_DLEN; - * | | contains `struct in_addr's - * |-------------------------------| - * | storage for hostname strings | Max size: ALIAS_DLEN; - * +-------------------------------+ contains `char's - * - * For requests the size of the h_aliases, and h_addr_list pointer - * array sizes are set to MAXALISES and MAXADDRS respectively, and - * buf is a fixed size with enough space to hold the largest expected - * reply from a nameserver, see RFC 1034 and RFC 1035. - * For cached entries the sizes are dependent on the actual number - * of aliases and addresses. If new aliases and addresses are found - * for cached entries, the buffer is grown and the new entries are added. - * The hostent struct is filled in with the addresses of the entries in - * the Hostent buf as follows: - * h_name - contains a pointer to the start of the hostname string area, - * or NULL if none is set. The h_name is followed by the - * aliases, in the storage for hostname strings area. - * h_aliases - contains a pointer to the start of h_aliases pointer array. - * This array contains pointers to the storage for hostname - * strings area and is terminated with a NULL. The first alias - * is stored directly after the h_name. - * h_addr_list - contains a pointer to the start of h_addr_list pointer array. - * This array contains pointers to in_addr structures in the - * h_addr_list addresses area and is terminated with a NULL. - * - * Filling the buffer this way allows for proper alignment of the h_addr_list - * addresses. - * - * This arrangement allows us to alias a Hostent struct pointer as a - * real struct hostent* without lying. It also allows us to change the - * values contained in the cached entries and requests without changing - * the actual hostent pointer, which is saved in a client struct and can't - * be changed without blowing things up or a lot more fiddling around. - * It also allows for defered allocation of the fixed size buffers until - * they are really needed. - * Nov. 17, 1997 --Bleep - */ - -struct Hostent { - struct hostent h; /* the hostent struct we are passing around */ - char buf[1]; /* buffer for data pointed to from hostent */ -}; - -struct ResRequest { - struct ResRequest* next; - - adns_rrtype type; - adns_query aq; - - struct in_addr addr; - char* name; - struct DNSQuery query; /* query callback for this request */ - struct hostent he; - char* buf; -}; - -int ResolverFileDescriptor = -1; /* GLOBAL - used in s_bsd.c */ - -static struct Socket resSock; /* Socket describing resolver */ -static struct Timer resExpireDNS; /* Timer for DNS expiration */ -static adns_state adns = NULL; - -/* - * Keep a spare file descriptor open. res_init calls fopen to read the - * resolv.conf file. If ircd is hogging all the file descriptors below 256, - * on systems with crippled FILE structures this will cause wierd bugs. - * This is definitely needed for Solaris which uses an unsigned char to - * hold the file descriptor. --Dianora - */ -static int spare_fd = -1; - -static struct ResRequest* requestListHead; /* head of resolver request list */ -static struct ResRequest* requestListTail; /* tail of resolver request list */ - - -static void add_request(struct ResRequest* request); -static void rem_request(struct ResRequest* request); -static struct ResRequest* make_request(const struct DNSQuery* query); -static time_t timeout_query_list(time_t now); -static void do_query_name(const struct DNSQuery* query, - const char* name, - struct ResRequest* request); -static void do_query_number(const struct DNSQuery* query, - const struct in_addr*, - struct ResRequest* request); -static void res_adns_callback(adns_state state, adns_query q, void *context); - -static struct resinfo { - int re_errors; - int re_nu_look; - int re_na_look; - int re_replies; - int re_requests; - int re_resends; - int re_sent; - int re_timeouts; - int re_shortttl; - int re_unkrep; -} reinfo; - - -/* Socket callback for resolver */ -static void res_socket_callback(struct Event* ev) -{ - struct timeval tv; - - assert(ev_type(ev) == ET_READ || ev_type(ev) == ET_ERROR); - - tv.tv_sec = CurrentTime; - tv.tv_usec = 0; - adns_processreadable(adns, ResolverFileDescriptor, &tv); -} - -/* - * start_resolver - do everything we need to read the resolv.conf file - * and initialize the resolver file descriptor if needed - */ -static void start_resolver(void) -{ - int res; - - Debug((DEBUG_DNS, "Resolver: start_resolver")); - /* - * close the spare file descriptor so res_init can read resolv.conf - * successfully. Needed on Solaris - */ - if (spare_fd > -1) - close(spare_fd); - - /* - * make sure we have a valid file descriptor below 256 so we can - * do this again. Needed on Solaris - */ - spare_fd = open("/dev/null",O_RDONLY,0); - if ((spare_fd < 0) || (spare_fd > 255)) { - char sparemsg[80]; - ircd_snprintf(0, sparemsg, sizeof(sparemsg), "invalid spare_fd %d", - spare_fd); - server_restart(sparemsg); - } - - if (adns) - return; - - if ((res = adns_init(&adns, adns_if_debug /*| adns_if_noautosys*/, NULL))) { - report_error("Resolver: error initializing adns for %s: %s", - cli_name(&me), res); - errno = res; - return; - } - errno = 0; - - ResolverFileDescriptor = adns_get_fd(adns); - - if (!socket_add(&resSock, res_socket_callback, 0, SS_DATAGRAM, - SOCK_EVENT_READABLE, ResolverFileDescriptor)) - report_error("Resolver: unable to queue resolver file descriptor for %s", - cli_name(&me), ENFILE); -} - -/* Call the query timeout function */ -static void expire_DNS_callback(struct Event* ev) -{ - time_t next; - - next = timeout_query_list(CurrentTime); - - timer_add(&resExpireDNS, expire_DNS_callback, 0, TT_ABSOLUTE, next); -} - -/* - * init_resolver - initialize resolver and resolver library - */ -int init_resolver(void) -{ - Debug((DEBUG_DNS, "Resolver: init_resolver")); -#ifdef LRAND48 - srand48(CurrentTime); -#endif - memset(&reinfo, 0, sizeof(reinfo)); - - requestListHead = requestListTail = 0; - - /* initiate the resolver timers */ - timer_add(timer_init(&resExpireDNS), expire_DNS_callback, 0, - TT_RELATIVE, 1); - - errno = h_errno = 0; - - start_resolver(); - Debug((DEBUG_DNS, "Resolver: fd %d errno: %d h_errno: %d: %s", - ResolverFileDescriptor, errno, h_errno, - (strerror(errno)) ? strerror(errno) : "Unknown")); - return ResolverFileDescriptor; -} - -/* - * restart_resolver - flush the cache, reread resolv.conf, reopen socket - */ -void restart_resolver(void) -{ - start_resolver(); -} - -/* - * add_request - place a new request in the request list - */ -static void add_request(struct ResRequest* request) -{ - assert(0 != request); - if (!requestListHead) - requestListHead = requestListTail = request; - else { - requestListTail->next = request; - requestListTail = request; - } - request->next = NULL; - ++reinfo.re_requests; -} - -/* - * rem_request - remove a request from the list. - * This must also free any memory that has been allocated for - * temporary storage of DNS results. - */ -static void rem_request(struct ResRequest* request) -{ - struct ResRequest** current; - struct ResRequest* prev = NULL; - - assert(0 != request); - for (current = &requestListHead; *current; ) { - if (*current == request) { - *current = request->next; - if (requestListTail == request) - requestListTail = prev; - break; - } - prev = *current; - current = &(*current)->next; - } - if (request->aq) - adns_cancel(request->aq); - MyFree(request->buf); - MyFree(request->name); - MyFree(request); -} - -/* - * make_request - Create a DNS request record for the server. - */ -static struct ResRequest* make_request(const struct DNSQuery* query) -{ - struct ResRequest* request; - assert(0 != query); - request = (struct ResRequest*) MyMalloc(sizeof(struct ResRequest)); - memset(request, 0, sizeof(struct ResRequest)); - - request->addr.s_addr = INADDR_NONE; - request->he.h_addrtype = AF_INET; - request->he.h_length = sizeof(struct in_addr); - request->query.vptr = query->vptr; - request->query.callback = query->callback; - - add_request(request); - return request; -} - -/* - * timeout_query_list - Remove queries from the list which have been - * there too long without being resolved. - */ -static time_t timeout_query_list(time_t now) -{ - struct timeval tv, tv_buf, *tv_mod = NULL; - time_t next; - - Debug((DEBUG_DNS, "Resolver: timeout_query_list at %s", myctime(now))); - - tv.tv_sec = now; - tv.tv_usec = 0; - adns_processtimeouts(adns, &tv); - adns_firsttimeout(adns, &tv_mod, &tv_buf, tv); - next = tv_mod ? tv_mod->tv_sec : AR_TTL; - if (!next) - next = 1; - - Debug((DEBUG_DNS, "Resolver: next timeout_query_list in %d seconds", next)); - return now + next; -} - -/* - * delete_resolver_queries - cleanup outstanding queries - * for which there no longer exist clients or conf lines. - */ -void delete_resolver_queries(const void* vptr) -{ - struct ResRequest* request; - struct ResRequest* next_request; - - for (request = requestListHead; request; request = next_request) { - next_request = request->next; - if (vptr == request->query.vptr) - rem_request(request); - } -} - -/* - * gethost_byname - get host address from name - */ -void gethost_byname(const char* name, const struct DNSQuery* query) -{ - assert(0 != name); - - Debug((DEBUG_DNS, "Resolver: gethost_byname %s", name)); - ++reinfo.re_na_look; - do_query_name(query, name, NULL); -} - -/* - * gethost_byaddr - get host name from address - */ -void gethost_byaddr(const char* addr, const struct DNSQuery* query) -{ - assert(0 != addr); - Debug((DEBUG_DNS, "Resolver: gethost_byaddr %s", ircd_ntoa(addr))); - ++reinfo.re_nu_look; - do_query_number(query, (const struct in_addr*) addr, NULL); -} - -/* - * do_query_name - nameserver lookup name - */ -static void do_query_name(const struct DNSQuery* query, - const char* name, struct ResRequest* request) -{ - char hname[HOSTLEN + 1]; - int res; - assert(0 != name); - - ircd_strncpy(hname, name, HOSTLEN); - hname[HOSTLEN] = '\0'; - - if (!request) { - request = make_request(query); - request->type = adns_r_a; - request->name = (char*) MyMalloc(strlen(hname) + 1); - strcpy(request->name, hname); - } - res = adns_submit_callback(adns, hname, adns_r_a, adns_qf_owner, - request, &request->aq, res_adns_callback); - assert(!res); - timer_chg(&resExpireDNS, TT_RELATIVE, 1); -} - -/* - * do_query_number - Use this to do reverse IP# lookups. - */ -static void do_query_number(const struct DNSQuery* query, - const struct in_addr* addr, - struct ResRequest* request) -{ - char ipbuf[32]; - const unsigned char* cp; - int res; - - assert(0 != addr); - cp = (const unsigned char*) &addr->s_addr; - ircd_snprintf(0, ipbuf, sizeof(ipbuf), "%u.%u.%u.%u.in-addr.arpa.", - (unsigned int)(cp[3]), (unsigned int)(cp[2]), - (unsigned int)(cp[1]), (unsigned int)(cp[0])); - - if (!request) { - request = make_request(query); - request->type = adns_r_ptr; - request->addr.s_addr = addr->s_addr; - } - res = adns_submit_callback(adns, ipbuf, adns_r_ptr, adns_qf_owner, - request, &request->aq, res_adns_callback); - assert(!res); - timer_chg(&resExpireDNS, TT_RELATIVE, 1); -} - -/* - * dup_hostent - Duplicate a hostent struct, allocate only enough memory for - * the data we're putting in it. - */ -static struct hostent* dup_hostent(struct hostent* hp) -{ - char* p; - char** ap; - char** pp; - int alias_count = 0; - int addr_count = 0; - size_t bytes_needed = 0; - struct Hostent* new_hp = 0; - - assert(0 != hp); - - /* how much buffer do we need? */ - bytes_needed += (strlen(hp->h_name) + 1); - - pp = hp->h_aliases; - while (*pp) { - bytes_needed += (strlen(*pp++) + 1 + sizeof(char*)); - ++alias_count; - } - pp = hp->h_addr_list; - while (*pp++) { - bytes_needed += (hp->h_length + sizeof(char*)); - ++addr_count; - } - /* Reserve space for 2 nulls to terminate h_aliases and h_addr_list */ - bytes_needed += (2 * sizeof(char*)); - - /* Allocate memory */ - new_hp = (struct Hostent*) MyMalloc(sizeof(struct Hostent) + bytes_needed); - - new_hp->h.h_addrtype = hp->h_addrtype; - new_hp->h.h_length = hp->h_length; - - /* first write the address list */ - pp = hp->h_addr_list; - ap = new_hp->h.h_addr_list = - (char**)(new_hp->buf + ((alias_count + 1) * sizeof(char*))); - p = (char*)ap + ((addr_count + 1) * sizeof(char*)); - while (*pp) - { - *ap++ = p; - memcpy(p, *pp++, hp->h_length); - p += hp->h_length; - } - *ap = 0; - /* next write the name */ - new_hp->h.h_name = p; - strcpy(p, hp->h_name); - p += (strlen(p) + 1); - - /* last write the alias list */ - pp = hp->h_aliases; - ap = new_hp->h.h_aliases = (char**) new_hp->buf; - while (*pp) { - *ap++ = p; - strcpy(p, *pp++); - p += (strlen(p) + 1); - } - *ap = 0; - return (struct hostent*) new_hp; -} - -static void res_adns_callback(adns_state state, adns_query q, void *context) -{ - struct ResRequest *request = (struct ResRequest *) context; - adns_answer *answer = NULL; - int res, k; - struct hostent* hp; /* hostent getting filled */ - char** alias; /* alias list */ - char** addr; /* address list */ - char** base_addr; /* original pointer to address list */ - char* name; /* pointer to name string */ - char* address; /* pointer to address */ - char* base_address; /* original pointer to address */ - char* endp; /* end of our buffer */ - int addr_count = 0; /* number of addresses in hostent */ - int alias_count = 0; /* number of aliases in hostent */ - - assert(request); - assert(q); - assert(request->aq == q); - res = adns_check(adns, &q, &answer, NULL); - request->aq = NULL; - - if (res) { - /* adns_check returned an error, bail */ - Debug((DEBUG_DNS, "Resolver: adns_check result %d", res)); - - (*request->query.callback)(request->query.vptr, 0); - rem_request(request); - return; - } - - Debug((DEBUG_DNS, "Resolver: adns_check status %d nrrs %d", - answer->status, answer->nrrs)); - - /* No error, we have a valid answer structure */ - if (answer->status != adns_s_ok || !answer->nrrs) { - /* Status is not 'ok', or there were no RRs found */ - ++reinfo.re_errors; - (*request->query.callback)(request->query.vptr, 0); - } else { - ++reinfo.re_replies; - hp = &(request->he); - if (!request->buf) { - request->buf = (char*) MyMalloc(MAXGETHOSTLEN + 1); - request->buf[MAXGETHOSTLEN] = '\0'; - /* - * array of alias list pointers starts at beginning of buf - */ - hp->h_aliases = (char**) request->buf; - hp->h_aliases[0] = NULL; - /* - * array of address list pointers starts after alias list pointers - * the actual addresses follow the the address list pointers - */ - hp->h_addr_list = (char**)(request->buf + ALIAS_BLEN); - /* - * don't copy the host address to the beginning of h_addr_list - */ - hp->h_addr_list[0] = NULL; - } - - hp->h_addrtype = AF_INET; - - endp = request->buf + MAXGETHOSTLEN; - /* - * find the end of the address list - */ - addr = hp->h_addr_list; - while (*addr) { - ++addr; - ++addr_count; - } - base_addr = addr; - /* - * make address point to first available address slot - */ - address = request->buf + ADDRS_OFFSET + - (sizeof(struct in_addr) * addr_count); - base_address = address; - - /* - * find the end of the alias list - */ - alias = hp->h_aliases; - while (*alias) { - ++alias; - ++alias_count; - } - /* - * make name point to first available space in request->buf - */ - if (alias_count > 0) { - name = hp->h_aliases[alias_count - 1]; - name += (strlen(name) + 1); - } - else if (hp->h_name) - name = hp->h_name + strlen(hp->h_name) + 1; - else - name = request->buf + ADDRS_OFFSET + ADDRS_DLEN; - - switch (request->type) { - case adns_r_a: - for (k = 0; k < answer->nrrs; k++) { - if (++addr_count < RES_MAXADDRS) { - memcpy(address, &answer->rrs.inaddr[k], sizeof(struct in_addr)); - *addr++ = address; - *addr = 0; - address += sizeof(struct in_addr); - } - Debug((DEBUG_DNS, "Resolver: A %s for %s", - ircd_ntoa((char*) &answer->rrs.inaddr[k]), answer->owner)); - } - if (!hp->h_name) { - strcpy(name, answer->owner); - hp->h_name = name; - name += strlen(name) + 1; - } - break; - case adns_r_ptr: - strcpy(name, answer->rrs.str[0]); - hp->h_name = name; - name += strlen(name) + 1; - - Debug((DEBUG_DNS, "Resolver: PTR %s for %s", hp->h_name, answer->owner)); - break; - default: - /* ignore */ - break; - } - - if (answer->cname) { - alias_count++; - ircd_strncpy(name, answer->cname, endp - name); - *alias++ = name; - *alias = 0; - name += strlen(name) + 1; - Debug((DEBUG_DNS, "Resolver: CNAME %s for %s", - answer->cname, answer->owner)); - } - - if (request->type == adns_r_ptr) { - - Debug((DEBUG_DNS, "relookup %s <-> %s", - request->he.h_name, ircd_ntoa((char*) &request->addr))); - /* - * Lookup the 'authoritive' name that we were given for the - * ip#. By using this call rather than regenerating the - * type we automatically gain the use of the cache with no - * extra kludges. - */ - gethost_byname(request->he.h_name, &request->query); - /* - * If name wasn't found, a request has been queued and it will - * be the last one queued. This is rather nasty way to keep - * a host alias with the query. -avalon - */ - MyFree(requestListTail->buf); - requestListTail->buf = request->buf; - request->buf = 0; - memcpy(&requestListTail->he, &request->he, sizeof(struct hostent)); - } else { - /* - * got a name and address response, client resolved - * XXX - Bug found here by Dianora - - * make_cache() occasionally returns a NULL pointer when a - * PTR returned a CNAME, cp was not checked before so the - * callback was being called with a value of 0x2C != NULL. - */ - struct hostent* he = dup_hostent(&request->he); - (*request->query.callback)(request->query.vptr, he); - } - } - - rem_request(request); - - /* - * adns doesn't use MyMalloc, so we don't use MyFree - */ - free(answer); -} - -/* - * m_dns - dns status query - */ -int m_dns(struct Client *cptr, struct Client *sptr, int parc, char *parv[]) -{ -#if !defined(NDEBUG) - sendcmdto_one(&me, CMD_NOTICE, sptr,"%C :Errors %d Lookups %d/%d Replies %d Requests %d", - sptr, reinfo.re_errors, reinfo.re_nu_look, - reinfo.re_na_look, reinfo.re_replies, reinfo.re_requests); - sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :Unknown Reply %d Short TTL(<10m) %d Sent %d Resends %d Timeouts %d", sptr, - reinfo.re_unkrep, reinfo.re_shortttl, reinfo.re_sent, - reinfo.re_resends, reinfo.re_timeouts); - sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :ResolverFileDescriptor = %d", - sptr, ResolverFileDescriptor); -#endif - return 0; -} - -size_t cres_mem(struct Client* sptr) -{ - struct ResRequest* request; - size_t request_mem = 0; - int request_count = 0; - - for (request = requestListHead; request; request = request->next) { - request_mem += sizeof(struct ResRequest); - if (request->name) - request_mem += strlen(request->name) + 1; - if (request->buf) - request_mem += MAXGETHOSTLEN + 1; - ++request_count; - } - - send_reply(sptr, SND_EXPLICIT | RPL_STATSDEBUG, - ":Resolver: requests %d(%d)", request_count, request_mem); - return request_mem; -} - diff --git a/ircd/res_libresolv.c b/ircd/res_libresolv.c deleted file mode 100644 index d964eb9..0000000 --- a/ircd/res_libresolv.c +++ /dev/null @@ -1,1201 +0,0 @@ -/* - * src/res.c (C)opyright 1992 Darren Reed. All rights reserved. - * This file may not be distributed without the author's permission in any - * shape or form. The author takes no responsibility for any damage or loss - * of property which results from the use of this software. - * - * $Id$ - * - * July 1999 - Rewrote a bunch of stuff here. Change hostent builder code, - * added callbacks and reference counting of returned hostents. - * --Bleep (Thomas Helvey ) - */ -#include "config.h" - -#include "res.h" -#include "client.h" -#include "ircd.h" -#include "ircd_alloc.h" -#include "ircd_events.h" -#include "ircd_features.h" -#include "ircd_log.h" -#include "ircd_osdep.h" -#include "ircd_reply.h" -#include "ircd_snprintf.h" -#include "ircd_string.h" -#include "msg.h" -#include "numeric.h" -#include "s_bsd.h" -#include "s_debug.h" -#include "s_misc.h" -#include "send.h" -#include "struct.h" -#include "support.h" -#include "sys.h" - -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include - -#include -#if (CHAR_BIT != 8) -#error this code needs to be able to address individual octets -#endif - -/* - * Some systems do not define INADDR_NONE (255.255.255.255) - * INADDR_NONE is actually a valid address, but it should never - * be returned from any nameserver. - * NOTE: The bit pattern for INADDR_NONE and INADDR_ANY (0.0.0.0) should be - * the same on all hosts so we shouldn't need to use htonl or ntohl to - * compare or set the values. - */ -#ifndef INADDR_NONE -#define INADDR_NONE ((unsigned int) 0xffffffff) -#endif - -#define MAXPACKET 1024 /* rfc sez 512 but we expand names so ... */ -#define RES_MAXALIASES 35 /* maximum aliases allowed */ -#define RES_MAXADDRS 35 /* maximum addresses allowed */ -/* - * OSF1 doesn't have RES_NOALIASES - */ -#ifndef RES_NOALIASES -#define RES_NOALIASES 0 -#endif - -/* - * macros used to calulate offsets into fixed query buffer - */ -#define ALIAS_BLEN ((RES_MAXALIASES + 1) * sizeof(char*)) -#define ADDRS_BLEN ((RES_MAXADDRS + 1) * sizeof(struct in_addr*)) - -#define ADDRS_OFFSET (ALIAS_BLEN + ADDRS_BLEN) -#define ADDRS_DLEN (RES_MAXADDRS * sizeof(struct in_addr)) -#define NAMES_OFFSET (ADDRS_OFFSET + ADDRS_DLEN) -#define MAXGETHOSTLEN (NAMES_OFFSET + MAXPACKET) - -#define AR_TTL 600 /* TTL in seconds for dns cache entries */ - -/* - * RFC 1104/1105 wasn't very helpful about what these fields - * should be named, so for now, we'll just name them this way. - * we probably should look at what named calls them or something. - */ -#define TYPE_SIZE 2 -#define CLASS_SIZE 2 -#define TTL_SIZE 4 -#define RDLENGTH_SIZE 2 -#define ANSWER_FIXED_SIZE (TYPE_SIZE + CLASS_SIZE + TTL_SIZE + RDLENGTH_SIZE) - -/* - * Building the Hostent - * The Hostent struct is arranged like this: - * +-------------------------------+ - * Hostent: | struct hostent h | - * |-------------------------------| - * | char *buf | - * +-------------------------------+ - * - * allocated: - * - * +-------------------------------+ - * buf: | h_aliases pointer array | Max size: ALIAS_BLEN; - * | NULL | contains `char *'s - * |-------------------------------| - * | h_addr_list pointer array | Max size: ADDRS_BLEN; - * | NULL | contains `struct in_addr *'s - * |-------------------------------| - * | h_addr_list addresses | Max size: ADDRS_DLEN; - * | | contains `struct in_addr's - * |-------------------------------| - * | storage for hostname strings | Max size: ALIAS_DLEN; - * +-------------------------------+ contains `char's - * - * For requests the size of the h_aliases, and h_addr_list pointer - * array sizes are set to MAXALISES and MAXADDRS respectively, and - * buf is a fixed size with enough space to hold the largest expected - * reply from a nameserver, see RFC 1034 and RFC 1035. - * For cached entries the sizes are dependent on the actual number - * of aliases and addresses. If new aliases and addresses are found - * for cached entries, the buffer is grown and the new entries are added. - * The hostent struct is filled in with the addresses of the entries in - * the Hostent buf as follows: - * h_name - contains a pointer to the start of the hostname string area, - * or NULL if none is set. The h_name is followed by the - * aliases, in the storage for hostname strings area. - * h_aliases - contains a pointer to the start of h_aliases pointer array. - * This array contains pointers to the storage for hostname - * strings area and is terminated with a NULL. The first alias - * is stored directly after the h_name. - * h_addr_list - contains a pointer to the start of h_addr_list pointer array. - * This array contains pointers to in_addr structures in the - * h_addr_list addresses area and is terminated with a NULL. - * - * Filling the buffer this way allows for proper alignment of the h_addr_list - * addresses. - * - * This arrangement allows us to alias a Hostent struct pointer as a - * real struct hostent* without lying. It also allows us to change the - * values contained in the cached entries and requests without changing - * the actual hostent pointer, which is saved in a client struct and can't - * be changed without blowing things up or a lot more fiddling around. - * It also allows for defered allocation of the fixed size buffers until - * they are really needed. - * Nov. 17, 1997 --Bleep - */ - -struct Hostent { - struct hostent h; /* the hostent struct we are passing around */ - char buf[1]; /* buffer for data pointed to from hostent */ -}; - -struct ResRequest { - struct ResRequest* next; - int id; - int sent; /* number of requests sent */ - time_t ttl; - char type; - char retries; /* retry counter */ - char sends; /* number of sends (>1 means resent) */ - char resend; /* send flag. 0 == dont resend */ - time_t sentat; - time_t timeout; - struct in_addr addr; - char* name; - struct DNSQuery query; /* query callback for this request */ - struct hostent he; - char* buf; -}; - - -int ResolverFileDescriptor = -1; /* GLOBAL - used in s_bsd.c */ - -static struct Socket resSock; /* Socket describing resolver */ -static struct Timer resExpireDNS; /* Timer for DNS expiration */ - -static time_t nextDNSCheck = 0; - -/* - * Keep a spare file descriptor open. res_init calls fopen to read the - * resolv.conf file. If ircd is hogging all the file descriptors below 256, - * on systems with crippled FILE structures this will cause wierd bugs. - * This is definitely needed for Solaris which uses an unsigned char to - * hold the file descriptor. --Dianora - */ -static int spare_fd = -1; - -static struct ResRequest* requestListHead; /* head of resolver request list */ -static struct ResRequest* requestListTail; /* tail of resolver request list */ - - -static void add_request(struct ResRequest* request); -static void rem_request(struct ResRequest* request); -static struct ResRequest* make_request(const struct DNSQuery* query); -static time_t timeout_query_list(time_t now); -static void do_query_name(const struct DNSQuery* query, - const char* name, - struct ResRequest* request); -static void do_query_number(const struct DNSQuery* query, - const struct in_addr*, - struct ResRequest* request); -static void query_name(const char* name, - int query_class, - int query_type, - struct ResRequest* request); -static void resend_query(struct ResRequest* request); -static struct ResRequest* find_id(int); - -static struct resinfo { - int re_errors; - int re_nu_look; - int re_na_look; - int re_replies; - int re_requests; - int re_resends; - int re_sent; - int re_timeouts; - int re_shortttl; - int re_unkrep; -} reinfo; - - -/* - * From bind 8.3, these aren't declared in earlier versions of bind - */ -extern u_short _getshort(const u_char *); -extern u_int _getlong(const u_char *); -/* - * int - * res_isourserver(ina) - * looks up "ina" in _res.ns_addr_list[] - * returns: - * 0 : not found - * >0 : found - * author: - * paul vixie, 29may94 - */ -static int -res_ourserver(const struct __res_state* statp, const struct sockaddr_in* inp) -{ - struct sockaddr_in ina; - int ns; - - ina = *inp; - for (ns = 0; ns < statp->nscount; ns++) { - const struct sockaddr_in *srv = &statp->nsaddr_list[ns]; - - if (srv->sin_family == ina.sin_family && - srv->sin_port == ina.sin_port && - (srv->sin_addr.s_addr == INADDR_ANY || - srv->sin_addr.s_addr == ina.sin_addr.s_addr)) - return (1); - } - return (0); -} - -/* Socket callback for resolver */ -static void res_callback(struct Event* ev) -{ - assert(ev_type(ev) == ET_READ || ev_type(ev) == ET_ERROR); - - resolver_read(); -} - -/* - * start_resolver - do everything we need to read the resolv.conf file - * and initialize the resolver file descriptor if needed - */ -static void start_resolver(void) -{ - Debug((DEBUG_DNS, "Resolver: start_resolver")); - /* - * close the spare file descriptor so res_init can read resolv.conf - * successfully. Needed on Solaris - */ - if (spare_fd > -1) - close(spare_fd); - - res_init(); /* res_init always returns 0 */ - /* - * make sure we have a valid file descriptor below 256 so we can - * do this again. Needed on Solaris - */ - spare_fd = open("/dev/null",O_RDONLY,0); - if ((spare_fd < 0) || (spare_fd > 255)) { - char sparemsg[80]; - ircd_snprintf(0, sparemsg, sizeof(sparemsg), "invalid spare_fd %d", - spare_fd); - server_restart(sparemsg); - } - - if (!_res.nscount) { - _res.nscount = 1; - _res.nsaddr_list[0].sin_addr.s_addr = inet_addr("127.0.0.1"); - } - _res.options |= RES_NOALIASES; - - if (ResolverFileDescriptor < 0) { - ResolverFileDescriptor = socket(AF_INET, SOCK_DGRAM, 0); - if (-1 == ResolverFileDescriptor) { - report_error("Resolver: error creating socket for %s: %s", - cli_name(&me), errno); - return; - } - if (!os_set_nonblocking(ResolverFileDescriptor)) - report_error("Resolver: error setting non-blocking for %s: %s", - cli_name(&me), errno); - if (!socket_add(&resSock, res_callback, 0, SS_DATAGRAM, - SOCK_EVENT_READABLE, ResolverFileDescriptor)) - report_error("Resolver: unable to queue resolver file descriptor for %s", - cli_name(&me), ENFILE); - } -} - -/* Call the query timeout function */ -static void expire_DNS_callback(struct Event* ev) -{ - time_t next; - - next = timeout_query_list(CurrentTime); - - timer_add(&resExpireDNS, expire_DNS_callback, 0, TT_ABSOLUTE, next); -} - -/* - * init_resolver - initialize resolver and resolver library - */ -int init_resolver(void) -{ - Debug((DEBUG_DNS, "Resolver: init_resolver")); -#ifdef LRAND48 - srand48(CurrentTime); -#endif - memset(&reinfo, 0, sizeof(reinfo)); - requestListHead = requestListTail = 0; - - /* initiate the resolver timers */ - timer_add(timer_init(&resExpireDNS), expire_DNS_callback, 0, - TT_RELATIVE, 1); - - errno = h_errno = 0; - - start_resolver(); - Debug((DEBUG_DNS, "Resolver: fd %d errno: %d h_errno: %d: %s", - ResolverFileDescriptor, errno, h_errno, - (strerror(errno)) ? strerror(errno) : "Unknown")); - return ResolverFileDescriptor; -} - -/* - * restart_resolver - flush the cache, reread resolv.conf, reopen socket - */ -void restart_resolver(void) -{ - /* flush_cache(); flush the dns cache */ - start_resolver(); -} - -static int validate_hostent(const struct hostent* hp) -{ - const char* name; - int i = 0; - assert(0 != hp); - for (name = hp->h_name; name; name = hp->h_aliases[i++]) { - if (!string_is_hostname(name)) - return 0; - } - return 1; -} - -/* - * add_request - place a new request in the request list - */ -static void add_request(struct ResRequest* request) -{ - assert(0 != request); - if (!requestListHead) - requestListHead = requestListTail = request; - else { - requestListTail->next = request; - requestListTail = request; - } - request->next = NULL; - ++reinfo.re_requests; -} - -/* - * rem_request - remove a request from the list. - * This must also free any memory that has been allocated for - * temporary storage of DNS results. - */ -static void rem_request(struct ResRequest* request) -{ - struct ResRequest** current; - struct ResRequest* prev = NULL; - - assert(0 != request); - for (current = &requestListHead; *current; ) { - if (*current == request) { - *current = request->next; - if (requestListTail == request) - requestListTail = prev; - break; - } - prev = *current; - current = &(*current)->next; - } - MyFree(request->buf); - MyFree(request->name); - MyFree(request); -} - -/* - * make_request - Create a DNS request record for the server. - */ -static struct ResRequest* make_request(const struct DNSQuery* query) -{ - struct ResRequest* request; - assert(0 != query); - request = (struct ResRequest*) MyMalloc(sizeof(struct ResRequest)); - memset(request, 0, sizeof(struct ResRequest)); - - request->sentat = CurrentTime; - request->retries = feature_int(FEAT_IRCD_RES_RETRIES); - request->resend = 1; - request->timeout = feature_int(FEAT_IRCD_RES_TIMEOUT); - request->addr.s_addr = INADDR_NONE; - request->he.h_addrtype = AF_INET; - request->he.h_length = sizeof(struct in_addr); - request->query.vptr = query->vptr; - request->query.callback = query->callback; - - add_request(request); - return request; -} - -/* - * timeout_query_list - Remove queries from the list which have been - * there too long without being resolved. - */ -static time_t timeout_query_list(time_t now) -{ - struct ResRequest* request; - struct ResRequest* next_request = 0; - time_t next_time = 0; - time_t timeout = 0; - - Debug((DEBUG_DNS, "Resolver: timeout_query_list at %s", myctime(now))); - for (request = requestListHead; request; request = next_request) { - next_request = request->next; - timeout = request->sentat + request->timeout; - if (timeout < now) { - if (--request->retries <= 0) { - ++reinfo.re_timeouts; - (*request->query.callback)(request->query.vptr, 0); - rem_request(request); - continue; - } - else { - request->sentat = now; - request->timeout += request->timeout; - resend_query(request); - } - } - if (!next_time || timeout < next_time) { - next_time = timeout; - } - } - return (next_time > now) ? next_time : (now + AR_TTL); -} - -/* - * timeout_resolver - check request list and cache for expired entries - */ -time_t timeout_resolver(time_t now) -{ - if (nextDNSCheck < now) - nextDNSCheck = timeout_query_list(now); - return nextDNSCheck; -} - - -/* - * delete_resolver_queries - cleanup outstanding queries - * for which there no longer exist clients or conf lines. - */ -void delete_resolver_queries(const void* vptr) -{ - struct ResRequest* request; - struct ResRequest* next_request; - - for (request = requestListHead; request; request = next_request) { - next_request = request->next; - if (vptr == request->query.vptr) - rem_request(request); - } -} - -/* - * send_res_msg - sends msg to all nameservers found in the "_res" structure. - * This should reflect /etc/resolv.conf. We will get responses - * which arent needed but is easier than checking to see if nameserver - * isnt present. Returns number of messages successfully sent to - * nameservers or -1 if no successful sends. - */ -static int send_res_msg(const u_char* msg, int len, int rcount) -{ - int i; - int sent = 0; - int max_queries = IRCD_MIN(_res.nscount, rcount); - - assert(0 != msg); - /* - * RES_PRIMARY option is not implemented - * if (_res.options & RES_PRIMARY || 0 == max_queries) - */ - if (0 == max_queries) - max_queries = 1; - - Debug((DEBUG_DNS, "Resolver: sendto %d", max_queries)); - - for (i = 0; i < max_queries; i++) { - if (sendto(ResolverFileDescriptor, msg, len, 0, - (struct sockaddr*) &(_res.nsaddr_list[i]), - sizeof(struct sockaddr_in)) == len) { - ++reinfo.re_sent; - ++sent; - } - else - log_write(LS_RESOLVER, L_ERROR, 0, "Resolver: send failed %m"); - } - return sent; -} - -/* - * find_id - find a dns request id (id is determined by dn_mkquery) - */ -static struct ResRequest* find_id(int id) -{ - struct ResRequest* request; - - for (request = requestListHead; request; request = request->next) { - if (request->id == id) - return request; - } - return NULL; -} - -/* - * gethost_byname - get host address from name - */ -void gethost_byname(const char* name, const struct DNSQuery* query) -{ - assert(0 != name); - - Debug((DEBUG_DNS, "Resolver: gethost_byname %s", name)); - ++reinfo.re_na_look; -#if 0 - if ((cp = find_cache_name(name))) - return &(cp->reply); -#endif - do_query_name(query, name, NULL); - nextDNSCheck = 1; -} - -/* - * gethost_byaddr - get host name from address - */ -void gethost_byaddr(const char* addr, const struct DNSQuery* query) -{ - assert(0 != addr); - - Debug((DEBUG_DNS, "Resolver: gethost_byaddr %s", ircd_ntoa(addr))); - - ++reinfo.re_nu_look; - do_query_number(query, (const struct in_addr*) addr, NULL); - nextDNSCheck = 1; -} - -/* - * do_query_name - nameserver lookup name - */ -static void do_query_name(const struct DNSQuery* query, - const char* name, struct ResRequest* request) -{ - char hname[HOSTLEN + 1]; - assert(0 != name); - - ircd_strncpy(hname, name, HOSTLEN); - hname[HOSTLEN] = '\0'; - - if (!request) { - request = make_request(query); - request->type = T_A; - request->name = (char*) MyMalloc(strlen(hname) + 1); - strcpy(request->name, hname); - } - query_name(hname, C_IN, T_A, request); -} - -/* - * do_query_number - Use this to do reverse IP# lookups. - */ -static void do_query_number(const struct DNSQuery* query, - const struct in_addr* addr, - struct ResRequest* request) -{ - char ipbuf[32]; - const unsigned char* cp; - - assert(0 != addr); - cp = (const unsigned char*) &addr->s_addr; - ircd_snprintf(0, ipbuf, sizeof(ipbuf), "%u.%u.%u.%u.in-addr.arpa.", - (unsigned int)(cp[3]), (unsigned int)(cp[2]), - (unsigned int)(cp[1]), (unsigned int)(cp[0])); - - if (!request) { - request = make_request(query); - request->type = T_PTR; - request->addr.s_addr = addr->s_addr; - } - query_name(ipbuf, C_IN, T_PTR, request); -} - -/* - * query_name - generate a query based on class, type and name. - */ -static void query_name(const char* name, int query_class, - int type, struct ResRequest* request) -{ - unsigned char buf[MAXPACKET + 1]; - int request_len = 0; - - assert(0 != name); - assert(0 != request); - - Debug((DEBUG_DNS, "Resolver: query_name: %s %d %d", name, query_class, type)); - memset(buf, 0, sizeof(buf)); - if ((request_len = res_mkquery(QUERY, name, query_class, type, - 0, 0, 0, - buf, sizeof(buf) - 1)) > 0) { - HEADER* header = (HEADER*) buf; -#ifndef LRAND48 - int k = 0; - struct timeval tv; -#endif - /* - * generate a unique id - * NOTE: we don't have to worry about converting this to and from - * network byte order, the nameserver does not interpret this value - * and returns it unchanged - */ -#ifdef LRAND48 - do { - header->id = (header->id + lrand48()) & 0xffff; - } while (find_id(header->id)); -#else - gettimeofday(&tv, NULL); - do { - header->id = (header->id + k + tv.tv_usec) & 0xffff; - ++k; - } while (find_id(header->id)); -#endif /* LRAND48 */ - request->id = header->id; - ++request->sends; - Debug((DEBUG_DNS, "Resolver: query_name %d: %s %d %d", request->id, - name, query_class, type)); - request->sent += send_res_msg(buf, request_len, request->sends); - } -} - -static void resend_query(struct ResRequest* request) -{ - assert(request); - - if (request->resend == 0) - return; - ++reinfo.re_resends; - switch(request->type) { - case T_PTR: - do_query_number(NULL, &request->addr, request); - break; - case T_A: - do_query_name(NULL, request->name, request); - break; - default: - break; - } -} - -/* - * proc_answer - process name server reply - * build a hostent struct in the passed request - */ -static int proc_answer(struct ResRequest* request, HEADER* header, - u_char* buf, u_char* eob) -{ - char hostbuf[HOSTLEN + 1]; /* working buffer */ - u_char* current; /* current position in buf */ - char** alias; /* alias list */ - char** addr; /* address list */ - char** base_addr; /* original pointer to address list */ - char* name; /* pointer to name string */ - char* address; /* pointer to address */ - char* base_address; /* original pointer to address */ - char* endp; /* end of our buffer */ - int query_class; /* answer class */ - int type; /* answer type */ - int rd_length; /* record data length */ - int answer_count = 0; /* answer counter */ - int n; /* temp count */ - int addr_count = 0; /* number of addresses in hostent */ - int alias_count = 0; /* number of aliases in hostent */ - int t_ptr_seen = 0; /* Seen a T_PTR in proc_answer? */ - struct hostent* hp; /* hostent getting filled */ - - assert(request); - assert(header); - assert(buf); - assert(eob); - - current = buf + sizeof(HEADER); - hp = &(request->he); - /* - * lazy allocation of request->he.buf, we don't allocate a buffer - * unless there is something to put in it. - */ - if (!request->buf) { - request->buf = (char*) MyMalloc(MAXGETHOSTLEN + 1); - request->buf[MAXGETHOSTLEN] = '\0'; - /* - * array of alias list pointers starts at beginning of buf - */ - hp->h_aliases = (char**) request->buf; - hp->h_aliases[0] = NULL; - /* - * array of address list pointers starts after alias list pointers - * the actual addresses follow the the address list pointers - */ - hp->h_addr_list = (char**)(request->buf + ALIAS_BLEN); - /* - * don't copy the host address to the beginning of h_addr_list - */ - hp->h_addr_list[0] = NULL; - } - endp = request->buf + MAXGETHOSTLEN; - /* - * find the end of the address list - */ - addr = hp->h_addr_list; - while (*addr) { - ++addr; - ++addr_count; - } - base_addr = addr; - /* - * make address point to first available address slot - */ - address = request->buf + ADDRS_OFFSET + - (sizeof(struct in_addr) * addr_count); - base_address = address; - - /* - * find the end of the alias list - */ - alias = hp->h_aliases; - while (*alias) { - ++alias; - ++alias_count; - } - /* - * make name point to first available space in request->buf - */ - if (alias_count > 0) { - name = hp->h_aliases[alias_count - 1]; - name += (strlen(name) + 1); - } - else if (hp->h_name) - name = hp->h_name + strlen(hp->h_name) + 1; - else - name = request->buf + ADDRS_OFFSET + ADDRS_DLEN; - - /* - * skip past queries - */ - while (header->qdcount-- > 0) { - if ((n = dn_skipname(current, eob)) < 0) - break; - current += (n + QFIXEDSZ); - } - /* - * process each answer sent to us blech. - */ - while (header->ancount-- > 0 && current < eob && name < endp) { - n = dn_expand(buf, eob, current, hostbuf, sizeof(hostbuf)); - if (n <= 0) { - /* - * no more answers left - */ - return answer_count; - } - hostbuf[HOSTLEN] = '\0'; - /* - * With Address arithmetic you have to be very anal - * this code was not working on alpha due to that - * (spotted by rodder/jailbird/dianora) - */ - current += (size_t) n; - - if (!((current + ANSWER_FIXED_SIZE) < eob)) - break; - - type = _getshort(current); - current += TYPE_SIZE; - - query_class = _getshort(current); - current += CLASS_SIZE; - - request->ttl = _getlong(current); - current += TTL_SIZE; - - rd_length = _getshort(current); - current += RDLENGTH_SIZE; - - /* - * Wait to set request->type until we verify this structure - */ - switch(type) { - case T_A: - /* - * check for invalid rd_length or too many addresses - * ignore T_A relies if looking for a T_PTR - */ - if (t_ptr_seen) - return answer_count; - if (rd_length != sizeof(struct in_addr)) - return answer_count; - if (++addr_count < RES_MAXADDRS) { - if (answer_count == 1) - hp->h_addrtype = (query_class == C_IN) ? AF_INET : AF_UNSPEC; - - memcpy(address, current, sizeof(struct in_addr)); - *addr++ = address; - *addr = 0; - address += sizeof(struct in_addr); - - if (!hp->h_name) { - strcpy(name, hostbuf); - hp->h_name = name; - name += strlen(name) + 1; - } - Debug((DEBUG_DNS, "Resolver: A %s for %s", - ircd_ntoa((char*) hp->h_addr_list[addr_count - 1]), hostbuf)); - } - current += rd_length; - ++answer_count; - break; - case T_PTR: - t_ptr_seen = 1; - addr_count = 0; - addr = base_addr; - *addr = 0; - address = base_address; - n = dn_expand(buf, eob, current, hostbuf, sizeof(hostbuf)); - if (n < 0) { - /* - * broken message - */ - return 0; - } - else if (n == 0) { - /* - * no more answers left - */ - return answer_count; - } - /* - * This comment is based on analysis by Shadowfax, Wohali and johan, - * not me. (Dianora) I am only commenting it. - * - * dn_expand is guaranteed to not return more than sizeof(hostbuf) - * but do all implementations of dn_expand also guarantee - * buffer is terminated with null byte? Lets not take chances. - * -Dianora - */ - hostbuf[HOSTLEN] = '\0'; - current += (size_t) n; - - Debug((DEBUG_DNS, "Resolver: PTR %s", hostbuf)); - /* - * copy the returned hostname into the host name - * ignore duplicate ptr records - */ - if (!hp->h_name) { - strcpy(name, hostbuf); - hp->h_name = name; - name += strlen(name) + 1; - } - ++answer_count; - break; - case T_CNAME: - Debug((DEBUG_DNS, "Resolver: CNAME %s", hostbuf)); - if (++alias_count < RES_MAXALIASES) { - ircd_strncpy(name, hostbuf, endp - name); - *alias++ = name; - *alias = 0; - name += strlen(name) + 1; - } - current += rd_length; - ++answer_count; - break; - default : - Debug((DEBUG_DNS,"Resolver: proc_answer type: %d for: %s", type, hostbuf)); - break; - } - } - return answer_count; -} - -/* - * dup_hostent - Duplicate a hostent struct, allocate only enough memory for - * the data we're putting in it. - */ -static struct hostent* dup_hostent(struct hostent* hp) -{ - char* p; - char** ap; - char** pp; - int alias_count = 0; - int addr_count = 0; - size_t bytes_needed = 0; - struct Hostent* new_hp = 0; - - assert(0 != hp); - - /* how much buffer do we need? */ - bytes_needed += (strlen(hp->h_name) + 1); - - pp = hp->h_aliases; - while (*pp) { - bytes_needed += (strlen(*pp++) + 1 + sizeof(char*)); - ++alias_count; - } - pp = hp->h_addr_list; - while (*pp++) { - bytes_needed += (hp->h_length + sizeof(char*)); - ++addr_count; - } - /* Reserve space for 2 nulls to terminate h_aliases and h_addr_list */ - bytes_needed += (2 * sizeof(char*)); - - /* Allocate memory */ - new_hp = (struct Hostent*) MyMalloc(sizeof(struct Hostent) + bytes_needed); - - new_hp->h.h_addrtype = hp->h_addrtype; - new_hp->h.h_length = hp->h_length; - - /* first write the address list */ - pp = hp->h_addr_list; - ap = new_hp->h.h_addr_list = - (char**)(new_hp->buf + ((alias_count + 1) * sizeof(char*))); - p = (char*)ap + ((addr_count + 1) * sizeof(char*)); - while (*pp) - { - *ap++ = p; - memcpy(p, *pp++, hp->h_length); - p += hp->h_length; - } - *ap = 0; - /* next write the name */ - new_hp->h.h_name = p; - strcpy(p, hp->h_name); - p += (strlen(p) + 1); - - /* last write the alias list */ - pp = hp->h_aliases; - ap = new_hp->h.h_aliases = (char**) new_hp->buf; - while (*pp) { - *ap++ = p; - strcpy(p, *pp++); - p += (strlen(p) + 1); - } - *ap = 0; - return (struct hostent*) new_hp; -} - -/* - * resolver_read - read a dns reply from the nameserver and process it. - * return 0 if nothing was read from the socket, otherwise return 1 - */ -int resolver_read(void) -{ - unsigned char buf[sizeof(HEADER) + MAXPACKET]; - HEADER* header = 0; - struct ResRequest* request = 0; - unsigned int rc = 0; - int answer_count = 0; - struct sockaddr_in sin; - - Debug((DEBUG_DNS, "Resolver: read")); - if (IO_SUCCESS != os_recvfrom_nonb(ResolverFileDescriptor, - (char*) buf, sizeof(buf), &rc, &sin)) { - return 0; - } - if (rc < sizeof(HEADER)) { - Debug((DEBUG_DNS, "Resolver: short reply %d: %s", rc, - (strerror(errno)) ? strerror(errno) : "Unknown")); - return 0; - } - /* - * convert DNS reply reader from Network byte order to CPU byte order. - */ - header = (HEADER*) buf; - /* header->id = ntohs(header->id); */ - header->ancount = ntohs(header->ancount); - header->qdcount = ntohs(header->qdcount); - header->nscount = ntohs(header->nscount); - header->arcount = ntohs(header->arcount); - ++reinfo.re_replies; - /* - * response for an id which we have already received an answer for - * just ignore this response. - */ - if (0 == (request = find_id(header->id))) { - Debug((DEBUG_DNS, "Resolver: can't find request id: %d", header->id)); - return 1; - } - /* - * check against possibly fake replies - */ - if (!res_ourserver(&_res, &sin)) { - Debug((DEBUG_DNS, "Resolver: fake reply from: %s", - (const char*) &sin.sin_addr)); - ++reinfo.re_unkrep; - return 1; - } - - if ((header->rcode != NOERROR) || (header->ancount == 0)) { - ++reinfo.re_errors; - if (SERVFAIL == header->rcode) - resend_query(request); - else { - /* - * If a bad error was returned, we stop here and dont send - * send any more (no retries granted). - * Isomer: Perhaps we should return these error messages back to - * the client? - */ -#ifdef DEBUGMODE - switch (header->rcode) { - case NOERROR: - Debug((DEBUG_DNS, "Fatal DNS error: No Error")); - break; - case FORMERR: - Debug((DEBUG_DNS, "Fatal DNS error: Format Error")); - break; - case SERVFAIL: - Debug((DEBUG_DNS, "Fatal DNS error: Server Failure")); - break; - case NXDOMAIN: - Debug((DEBUG_DNS, "DNS error: Non Existant Domain")); - break; - case NOTIMP: - Debug((DEBUG_DNS, "Fatal DNS error: Not Implemented")); - break; - case REFUSED: - Debug((DEBUG_DNS, "Fatal DNS error: Query Refused")); - break; - default: - Debug((DEBUG_DNS, "Unassigned fatal DNS error: %i", header->rcode)); - break; - } -#endif /* DEBUGMODE */ - (*request->query.callback)(request->query.vptr, 0); - rem_request(request); - } - return 1; - } - /* - * If this fails there was an error decoding the received packet, - * try it again and hope it works the next time. - */ - answer_count = proc_answer(request, header, buf, buf + rc); - if (answer_count) { - struct hostent* hp = 0; - if (T_PTR == request->type) { - if (0 == request->he.h_name) { - /* - * got a PTR response with no name, something bogus is happening - * don't bother trying again, the client address doesn't resolve - */ - (*request->query.callback)(request->query.vptr, hp); - rem_request(request); - return 1; - } - Debug((DEBUG_DNS, "relookup %s <-> %s", - request->he.h_name, ircd_ntoa((char*) &request->addr))); - /* - * Lookup the 'authoritive' name that we were given for the - * ip#. By using this call rather than regenerating the - * type we automatically gain the use of the cache with no - * extra kludges. - */ - gethost_byname(request->he.h_name, &request->query); - /* - * If name wasn't found, a request has been queued and it will - * be the last one queued. This is rather nasty way to keep - * a host alias with the query. -avalon - */ - MyFree(requestListTail->buf); - requestListTail->buf = request->buf; - request->buf = 0; - memcpy(&requestListTail->he, &request->he, sizeof(struct hostent)); - rem_request(request); - } - else { - /* - * got a name and address response, client resolved - * XXX - Bug found here by Dianora - - * make_cache() occasionally returns a NULL pointer when a - * PTR returned a CNAME, cp was not checked before so the - * callback was being called with a value of 0x2C != NULL. - */ - if (validate_hostent(&request->he)) - hp = dup_hostent(&request->he); - (*request->query.callback)(request->query.vptr, hp); - rem_request(request); - } - } - else if (!request->sent) { - /* - * XXX - we got a response for a query we didn't send with a valid id? - * this should never happen, bail here and leave the client unresolved - */ - (*request->query.callback)(request->query.vptr, 0); - rem_request(request); - } - return 1; -} - -/* - * resolver_read_multiple - process up to count reads - */ -void resolver_read_multiple(int count) -{ - int i = 0; - for ( ; i < count; ++i) { - if (0 == resolver_read()) - return; - } -} - -/* - * m_dns - dns status query - */ -int m_dns(struct Client *cptr, struct Client *sptr, int parc, char *parv[]) -{ -#if !defined(NDEBUG) - sendcmdto_one(&me, CMD_NOTICE, sptr,"%C :Errors %d Lookups %d/%d Replies %d Requests %d", - sptr, reinfo.re_errors, reinfo.re_nu_look, - reinfo.re_na_look, reinfo.re_replies, reinfo.re_requests); - sendcmdto_one(&me, CMD_NOTICE, sptr,"%C :Unknown Reply %d Short TTL(<10m) %d Sent %d Resends %d Timeouts %d", sptr, - reinfo.re_unkrep, reinfo.re_shortttl, reinfo.re_sent, - reinfo.re_resends, reinfo.re_timeouts); - sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :ResolverFileDescriptor = %d", - sptr, ResolverFileDescriptor); -#endif - return 0; -} - -size_t cres_mem(struct Client* sptr) -{ - struct ResRequest* request; - size_t request_mem = 0; - int request_count = 0; - - for (request = requestListHead; request; request = request->next) { - request_mem += sizeof(struct ResRequest); - if (request->name) - request_mem += strlen(request->name) + 1; - if (request->buf) - request_mem += MAXGETHOSTLEN + 1; - ++request_count; - } - - send_reply(sptr, SND_EXPLICIT | RPL_STATSDEBUG, - ":Resolver: requests %d(%d)", request_count, request_mem); - return request_mem; -} - diff --git a/ircd/s_auth.c b/ircd/s_auth.c index 6428692..552e112 100644 --- a/ircd/s_auth.c +++ b/ircd/s_auth.c @@ -312,7 +312,7 @@ static void release_auth_client(struct Client* client) Debug((DEBUG_INFO, "Auth: release_auth_client %s@%s[%s]", cli_username(client), cli_sockhost(client), cli_sock_ip(client))); } - + static void auth_kill_client(struct AuthRequest* auth) { assert(0 != auth); @@ -347,17 +347,16 @@ static void auth_dns_callback(void* vptr, struct DNSReply* hp) ClearDNSPending(auth); if (hp) { - struct sockaddr_in *sin = (struct sockaddr_in*)&hp->addr; /* * Verify that the host to ip mapping is correct both ways and that * the ip#(s) for the socket is listed for the host. */ - if (memcmp(&sin->sin_addr, &cli_ip(auth->client), sizeof(struct in_addr))) { + if (irc_in_addr_cmp(&hp->addr, &cli_ip(auth->client))) { if (IsUserPort(auth->client)) sendheader(auth->client, REPORT_IP_MISMATCH); sendto_opmask_butone(0, SNO_IPMISMATCH, "IP# Mismatch: %s != %s[%s]", - cli_sock_ip(auth->client), hp->h_name, - ircd_ntoa((const char*)&sin->sin_addr)); + cli_sock_ip(auth->client), hp->h_name, + ircd_ntoa(&hp->addr)); if (feature_bool(FEAT_KILL_IPMISMATCH)) { auth_kill_client(auth); return; @@ -430,55 +429,39 @@ static void auth_error(struct AuthRequest* auth, int kill) } /* - * start_auth_query - Flag the client to show that an attempt to + * start_auth_query - Flag the client to show that an attempt to * contact the ident server on the client's host. The connect and - * subsequently the socket are all put into 'non-blocking' mode. + * subsequently the socket are all put into 'non-blocking' mode. * Should the connect or any later phase of the identifing process fail, * it is aborted and the user is given a username of "unknown". */ static int start_auth_query(struct AuthRequest* auth) { - struct sockaddr_in remote_addr; - struct sockaddr_in local_addr; + struct irc_sockaddr remote_addr; + struct irc_sockaddr local_addr; int fd; IOResult result; assert(0 != auth); assert(0 != auth->client); - if ((fd = socket(AF_INET, SOCK_STREAM, 0)) == -1) { - ++ServerStats->is_abad; - return 0; - } - if ((MAXCONNECTIONS - 10) < fd) { - close(fd); - return 0; - } - if (!os_set_nonblocking(fd)) { - close(fd); - return 0; - } - if (IsUserPort(auth->client)) - sendheader(auth->client, REPORT_DO_ID); - /* + /* * get the local address of the client and bind to that to * make the auth request. This used to be done only for * ifdef VIRTTUAL_HOST, but needs to be done for all clients * since the ident request must originate from that same address-- * and machines with multiple IP addresses are common now */ - memset(&local_addr, 0, sizeof(struct sockaddr_in)); + memset(&local_addr, 0, sizeof(local_addr)); os_get_sockname(cli_fd(auth->client), &local_addr); - local_addr.sin_port = htons(0); - - if (bind(fd, (struct sockaddr*) &local_addr, sizeof(struct sockaddr_in))) { - close(fd); + local_addr.port = 0; + fd = os_socket(&local_addr, SOCK_STREAM, "auth query"); + if (fd < 0) return 0; - } - - remote_addr.sin_addr.s_addr = (cli_ip(auth->client)).s_addr; - remote_addr.sin_port = htons(113); - remote_addr.sin_family = AF_INET; + if (IsUserPort(auth->client)) + sendheader(auth->client, REPORT_DO_ID); + memcpy(&remote_addr.addr, &cli_ip(auth->client), sizeof(remote_addr.addr)); + remote_addr.port = 113; if ((result = os_connect_nonb(fd, &remote_addr)) == IO_FAILURE || !socket_add(&auth->socket, auth_sock_callback, (void*) auth, @@ -598,7 +581,7 @@ void start_auth(struct Client* client) Debug((DEBUG_INFO, "Beginning auth request on client %p", client)); if (!feature_bool(FEAT_NODNS)) { - if (LOOPBACK == inet_netof(cli_ip(client))) + if (irc_in_addr_is_loopback(&cli_ip(client))) strcpy(cli_sockhost(client), cli_name(&me)); else { struct DNSQuery query; @@ -609,7 +592,7 @@ void start_auth(struct Client* client) if (IsUserPort(auth->client)) sendheader(client, REPORT_DO_DNS); - gethost_byinaddr(&(cli_ip(client)), &query); + gethost_byaddr(&cli_ip(client), &query); SetDNSPending(auth); } } @@ -639,8 +622,8 @@ void start_auth(struct Client* client) */ void send_auth_query(struct AuthRequest* auth) { - struct sockaddr_in us; - struct sockaddr_in them; + struct irc_sockaddr us; + struct irc_sockaddr them; char authbuf[32]; unsigned int count; @@ -653,8 +636,8 @@ void send_auth_query(struct AuthRequest* auth) return; } ircd_snprintf(0, authbuf, sizeof(authbuf), "%u , %u\r\n", - (unsigned int) ntohs(them.sin_port), - (unsigned int) ntohs(us.sin_port)); + (unsigned int) them.port, + (unsigned int) us.port); if (IO_SUCCESS == os_send_nonb(auth->fd, authbuf, strlen(authbuf), &count)) { ClearAuthConnect(auth); diff --git a/ircd/s_bsd.c b/ircd/s_bsd.c index 0d460ba..f863713 100644 --- a/ircd/s_bsd.c +++ b/ircd/s_bsd.c @@ -75,13 +75,9 @@ #include #endif /* USE_POLL */ -#ifndef INADDR_NONE -#define INADDR_NONE 0xffffffff -#endif - struct Client* LocalClientArray[MAXCONNECTIONS]; int HighestFd = -1; -struct sockaddr_in VirtualHost; +struct irc_sockaddr VirtualHost; static char readbuf[SERVER_TCP_WINDOW]; /* @@ -181,8 +177,7 @@ static void connect_dns_callback(void* vptr, struct DNSReply* hp) assert(aconf); aconf->dns_pending = 0; if (hp) { - struct sockaddr_in *sin = (struct sockaddr_in*)&hp->addr; - memcpy(&aconf->ipnum, &sin->sin_addr, sizeof(struct in_addr)); + memcpy(&aconf->address, &hp->addr, sizeof(aconf->address)); MyFree(hp); connect_server(aconf, 0); } @@ -231,7 +226,6 @@ int init_connection_limits(void) */ static int connect_inet(struct ConfItem* aconf, struct Client* cptr) { - static struct sockaddr_in sin; IOResult result; assert(0 != aconf); assert(0 != cptr); @@ -239,53 +233,16 @@ static int connect_inet(struct ConfItem* aconf, struct Client* cptr) * Might as well get sockhost from here, the connection is attempted * with it so if it fails its useless. */ - cli_fd(cptr) = socket(AF_INET, SOCK_STREAM, 0); - if (-1 == cli_fd(cptr)) { - cli_error(cptr) = errno; - report_error(SOCKET_ERROR_MSG, cli_name(cptr), errno); - return 0; - } - if (cli_fd(cptr) >= MAXCLIENTS) { - report_error(CONNLIMIT_ERROR_MSG, cli_name(cptr), 0); - close(cli_fd(cptr)); - cli_fd(cptr) = -1; + cli_fd(cptr) = os_socket((feature_bool(FEAT_VIRTUAL_HOST) ? &VirtualHost : NULL), SOCK_STREAM, cli_name(cptr)); + if (cli_fd(cptr) < 0) return 0; - } - /* - * Bind to a local IP# (with unknown port - let unix decide) so - * we have some chance of knowing the IP# that gets used for a host - * with more than one IP#. - * - * No we don't bind it, not all OS's can handle connecting with - * an already bound socket, different ip# might occur anyway - * leading to a freezing select() on this side for some time. - * I had this on my Linux 1.1.88 --Run - */ - /* - * No, we do bind it if we have virtual host support. If we don't - * explicitly bind it, it will default to IN_ADDR_ANY and we lose - * due to the other server not allowing our base IP --smg - */ - if (feature_bool(FEAT_VIRTUAL_HOST) && - bind(cli_fd(cptr), (struct sockaddr*) &VirtualHost, - sizeof(VirtualHost))) { - report_error(BIND_ERROR_MSG, cli_name(cptr), errno); - close(cli_fd(cptr)); - cli_fd(cptr) = -1; - return 0; - } - - memset(&sin, 0, sizeof(sin)); - sin.sin_family = AF_INET; - sin.sin_addr.s_addr = aconf->ipnum.s_addr; - sin.sin_port = htons(aconf->port); /* * save connection info in client */ - (cli_ip(cptr)).s_addr = aconf->ipnum.s_addr; - cli_port(cptr) = aconf->port; - ircd_ntoa_r(cli_sock_ip(cptr), (const char*) &(cli_ip(cptr))); + memcpy(&cli_ip(cptr), &aconf->address.addr, sizeof(cli_ip(cptr))); + cli_port(cptr) = aconf->address.port; + ircd_ntoa_r(cli_sock_ip(cptr), &cli_ip(cptr)); /* * we want a big buffer for server connections */ @@ -296,17 +253,7 @@ static int connect_inet(struct ConfItem* aconf, struct Client* cptr) cli_fd(cptr) = -1; return 0; } - /* - * ALWAYS set sockets non-blocking - */ - if (!os_set_nonblocking(cli_fd(cptr))) { - cli_error(cptr) = errno; - report_error(NONB_ERROR_MSG, cli_name(cptr), errno); - close(cli_fd(cptr)); - cli_fd(cptr) = -1; - return 0; - } - if ((result = os_connect_nonb(cli_fd(cptr), &sin)) == IO_FAILURE) { + if ((result = os_connect_nonb(cli_fd(cptr), &aconf->address)) == IO_FAILURE) { cli_error(cptr) = errno; report_error(CONNECT_ERROR_MSG, cli_name(cptr), errno); close(cli_fd(cptr)); @@ -587,7 +534,7 @@ int net_close_unregistered_connections(struct Client* source) * passed off to the auth handler for dns and ident queries. *--------------------------------------------------------------------------*/ void add_connection(struct Listener* listener, int fd) { - struct sockaddr_in addr; + struct irc_sockaddr addr; struct Client *new_client; time_t next_target = 0; @@ -596,14 +543,13 @@ void add_connection(struct Listener* listener, int fd) { /* 12345678901234567890123456789012345679012345678901234567890123456 */ const char* const register_message = "ERROR :Unable to complete your registration\r\n"; - + assert(0 != listener); - /* * Removed preliminary access check. Full check is performed in m_server and * m_user instead. Also connection time out help to get rid of unwanted - * connections. + * connections. */ if (!os_get_peername(fd, &addr) || !os_set_nonblocking(fd)) { ++ServerStats->is_ref; @@ -626,7 +572,7 @@ void add_connection(struct Listener* listener, int fd) { * * If they're throttled, murder them, but tell them why first. */ - if (!IPcheck_local_connect(addr.sin_addr, &next_target) && !listener->server) + if (!IPcheck_local_connect(&addr.addr, &next_target) && !listener->server) { ++ServerStats->is_ref; write(fd, throttle_message, strlen(throttle_message)); @@ -634,18 +580,18 @@ void add_connection(struct Listener* listener, int fd) { return; } - new_client = make_client(0, ((listener->server) ? + new_client = make_client(0, ((listener->server) ? STAT_UNKNOWN_SERVER : STAT_UNKNOWN_USER)); /* * Copy ascii address to 'sockhost' just in case. Then we have something - * valid to put into error messages... + * valid to put into error messages... */ SetIPChecked(new_client); - ircd_ntoa_r(cli_sock_ip(new_client), (const char*) &addr.sin_addr); + ircd_ntoa_r(cli_sock_ip(new_client), &addr.addr); strcpy(cli_sockhost(new_client), cli_sock_ip(new_client)); - (cli_ip(new_client)).s_addr = addr.sin_addr.s_addr; - cli_port(new_client) = ntohs(addr.sin_port); + memcpy(&cli_ip(new_client), &addr.addr, sizeof(cli_ip(new_client))); + cli_port(new_client) = addr.port; if (next_target) cli_nexttarget(new_client) = next_target; @@ -829,7 +775,7 @@ int connect_server(struct ConfItem* aconf, struct Client* by) return 0; } Debug((DEBUG_NOTICE, "Connect to %s[@%s]", aconf->name, - ircd_ntoa((const char*) &aconf->ipnum))); + ircd_ntoa(&aconf->address.addr))); if ((cptr = FindClient(aconf->name))) { if (IsServer(cptr) || IsMe(cptr)) { @@ -850,22 +796,21 @@ int connect_server(struct ConfItem* aconf, struct Client* by) } } /* - * If we dont know the IP# for this host and itis a hostname and + * If we dont know the IP# for this host and it is a hostname and * not a ip# string, then try and find the appropriate host record. */ - if (INADDR_NONE == aconf->ipnum.s_addr) { - if (INADDR_NONE == (aconf->ipnum.s_addr = inet_addr(aconf->host))) { - char buf[HOSTLEN + 1]; - struct DNSQuery query; - - query.vptr = aconf; - query.callback = connect_dns_callback; - host_from_uh(buf, aconf->host, HOSTLEN); - buf[HOSTLEN] = '\0'; - - gethost_byname(buf, &query); - aconf->dns_pending = 1; - } + if (!irc_in_addr_valid(&aconf->address.addr) + && !ircd_aton(&aconf->address.addr, aconf->host)) { + char buf[HOSTLEN + 1]; + struct DNSQuery query; + + query.vptr = aconf; + query.callback = connect_dns_callback; + host_from_uh(buf, aconf->host, HOSTLEN); + buf[HOSTLEN] = '\0'; + + gethost_byname(buf, &query); + aconf->dns_pending = 1; return 0; } cptr = make_client(NULL, STAT_UNKNOWN_SERVER); @@ -949,12 +894,11 @@ int connect_server(struct ConfItem* aconf, struct Client* by) /* * Setup local socket structure to use for binding to. */ -void set_virtual_host(struct in_addr addr) +void set_virtual_host(const struct irc_in_addr *addr) { memset(&VirtualHost, 0, sizeof(VirtualHost)); - VirtualHost.sin_family = AF_INET; - VirtualHost.sin_addr.s_addr = addr.s_addr; -} + memcpy(&VirtualHost.addr, addr, sizeof(VirtualHost.addr)); +} /* * Find the real hostname for the host running the server (or one which diff --git a/ircd/s_conf.c b/ircd/s_conf.c index 8d6d6b2..6b60d7f 100644 --- a/ircd/s_conf.c +++ b/ircd/s_conf.c @@ -66,10 +66,6 @@ #include #include -#ifndef INADDR_NONE -#define INADDR_NONE 0xffffffff -#endif - struct ConfItem *GlobalConfList = 0; int GlobalConfCount = 0; struct s_map *GlobalServiceMapList = 0; @@ -130,7 +126,6 @@ struct ConfItem* make_conf(void) #endif memset(aconf, 0, sizeof(struct ConfItem)); aconf->status = CONF_ILLEGAL; - aconf->ipnum.s_addr = INADDR_NONE; return aconf; } @@ -153,7 +148,7 @@ void free_conf(struct ConfItem *aconf) Debug((DEBUG_DEBUG, "free_conf: %s %s %d", aconf->host ? aconf->host : "*", aconf->name ? aconf->name : "*", - aconf->port)); + aconf->address.port)); if (aconf->dns_pending) delete_resolver_queries(aconf); MyFree(aconf->host); @@ -210,8 +205,7 @@ static void conf_dns_callback(void* vptr, struct DNSReply* hp) assert(aconf); aconf->dns_pending = 0; if (hp) { - struct sockaddr_in *sin = (struct sockaddr_in*)&hp->addr; - memcpy(&aconf->ipnum, &sin->sin_addr, sizeof(struct in_addr)); + memcpy(&aconf->address.addr, &hp->addr, sizeof(aconf->address.addr)); MyFree(hp); } } @@ -255,18 +249,13 @@ lookup_confhost(struct ConfItem *aconf) * Do name lookup now on hostnames given and store the * ip numbers in conf structure. */ - if (IsDigit(*aconf->host)) { - /* - * rfc 1035 sez host names may not start with a digit - * XXX - this has changed code needs to be updated - */ - aconf->ipnum.s_addr = inet_addr(aconf->host); - if (INADDR_NONE == aconf->ipnum.s_addr) { + if (IsIP6Char(*aconf->host)) { + if (!ircd_aton(&aconf->address.addr, aconf->host)) { Debug((DEBUG_ERROR, "Host/server name error: (%s) (%s)", - aconf->host, aconf->name)); + aconf->host, aconf->name)); } } - else + else conf_dns_lookup(aconf); } @@ -380,7 +369,7 @@ enum AuthorizationCheckResult attach_iline(struct Client* cptr) for (aconf = GlobalConfList; aconf; aconf = aconf->next) { if (aconf->status != CONF_CLIENT) continue; - if (aconf->port && aconf->port != cli_listener(cptr)->port) + if (aconf->address.port && aconf->address.port != cli_listener(cptr)->addr.port) continue; if (!aconf->host || !aconf->name) continue; @@ -609,17 +598,16 @@ struct ConfItem* find_conf_byhost(struct SLink* lp, const char* host, * Find a conf line using the IP# stored in it to search upon. * Added 1/8/92 by Avalon. */ -struct ConfItem* find_conf_byip(struct SLink* lp, const char* ip, +struct ConfItem* find_conf_byip(struct SLink* lp, const struct irc_in_addr* ip, int statmask) { struct ConfItem* tmp; for (; lp; lp = lp->next) { tmp = lp->value.aconf; - if (0 != (tmp->status & statmask)) { - if (0 == memcmp(&tmp->ipnum, ip, sizeof(struct in_addr))) - return tmp; - } + if (0 != (tmp->status & statmask) + && 0 == memcmp(&tmp->address.addr, ip, sizeof(*ip))) + return tmp; } return 0; } @@ -803,106 +791,6 @@ const struct CRuleConf* conf_get_crule_list(void) return cruleConfList; } -#if 0 -void conf_add_server(const char* const* fields, int count) -{ - struct ServerConf* server; - struct in_addr addr; - assert(0 != fields); - /* - * missing host, password, or alias? - */ - if (count < 6 || EmptyString(fields[1]) || EmptyString(fields[2]) || EmptyString(fields[3])) - return; - /* - * check the host - */ - if (string_is_hostname(fields[1])) - addr.s_addr = INADDR_NONE; - else if (INADDR_NONE == (addr.s_addr = inet_addr(fields[1]))) - return; - - server = (struct ServerConf*) MyMalloc(sizeof(struct ServerConf)); - assert(0 != server); - DupString(server->hostname, fields[1]); - DupString(server->passwd, fields[2]); - DupString(server->alias, fields[3]); - server->address.s_addr = addr.s_addr; - server->port = atoi(fields[4]); - server->dns_pending = 0; - server->connected = 0; - server->hold = 0; - server->conn_class = find_class(atoi(fields[5])); - - server->next = serverConfList; - serverConfList = server; - - /* if (INADDR_NONE == server->address.s_addr) */ - /* lookup_confhost(server); */ -} - -void conf_add_deny(const char* const* fields, int count, int ip_kill) -{ - struct DenyConf* conf; - - if (count < 4 || EmptyString(fields[1]) || EmptyString(fields[3])) - return; - - conf = (struct DenyConf*) MyMalloc(sizeof(struct DenyConf)); - assert(0 != conf); - memset(conf, 0, sizeof(struct DenyConf)); - - if (fields[1][0] == '$' && fields[1][1] == 'R') - conf->flags |= DENY_FLAGS_REALNAME; - - DupString(conf->hostmask, fields[1]); - collapse(conf->hostmask); - - if (!EmptyString(fields[2])) { - const char* p = fields[2]; - if ('!' == *p) { - conf->flags |= DENY_FLAGS_FILE; - ++p; - } - DupString(conf->message, p); - } - DupString(conf->usermask, fields[3]); - collapse(conf->usermask); - - if (ip_kill) { - /* - * Here we use the same kludge as in listener.c to parse - * a.b.c.d, or a.b.c.*, or a.b.c.d/e. - */ - int c_class; - char ipname[16]; - int ad[4] = { 0 }; - int bits2 = 0; - c_class = sscanf(conf->hostmask, "%d.%d.%d.%d/%d", - &ad[0], &ad[1], &ad[2], &ad[3], &bits2); - if (c_class != 5) { - conf->bits = c_class * 8; - } - else { - conf->bits = bits2; - } - ircd_snprintf(0, ipname, sizeof(ipname), "%d.%d.%d.%d", ad[0], ad[1], - ad[2], ad[3]); - - /* - * This ensures endian correctness - */ - conf->address = inet_addr(ipname); - Debug((DEBUG_DEBUG, "IPkill: %s = %08x/%i (%08x)", ipname, - conf->address, conf->bits, NETMASK(conf->bits))); - conf->flags |= DENY_FLAGS_IP; - } - conf->next = denyConfList; - denyConfList = conf; -} -#endif - - void conf_erase_deny_list(void) { struct DenyConf* next; @@ -916,30 +804,17 @@ void conf_erase_deny_list(void) } denyConfList = 0; } - + const struct DenyConf* conf_get_deny_list(void) { return denyConfList; } -#if 0 -void conf_add_quarantine(const char *chname, const char *reason) -{ - struct qline *qline; - - qline = (struct qline *) MyMalloc(sizeof(struct qline)); - DupString(qline->chname, chname); - DupString(qline->reason, reason); - qline->next = GlobalQuarantineList; - GlobalQuarantineList = qline; -} -#endif - const char* find_quarantine(const char *chname) { struct qline *qline; - + for (qline = GlobalQuarantineList; qline; qline = qline->next) if (!ircd_strcmp(qline->chname, chname)) return qline->reason; @@ -1192,9 +1067,12 @@ int find_kill(struct Client *cptr) if (0 == match(deny->hostmask + 2, realname)) break; } else if (deny->flags & DENY_FLAGS_IP) { /* k: by IP */ - Debug((DEBUG_DEBUG, "ip: %08x network: %08x/%i mask: %08x", - cli_ip(cptr).s_addr, deny->address, deny->bits, NETMASK(deny->bits))); - if ((cli_ip(cptr).s_addr & NETMASK(deny->bits)) == deny->address) +#ifdef DEBUGMODE + char tbuf1[SOCKIPLEN], tbuf2[SOCKIPLEN]; + Debug((DEBUG_DEBUG, "ip: %s network: %s/%u", + ircd_ntoa_r(tbuf1, &cli_ip(cptr)), ircd_ntoa_r(tbuf2, &deny->address), deny->bits)); +#endif + if (ipmask_check(&cli_ip(cptr), &deny->address, deny->bits)) break; } else if (0 == match(deny->hostmask, host)) @@ -1300,7 +1178,7 @@ int conf_check_server(struct Client *cptr) if ((c_conf = find_conf_byhost(lp, hp->h_name, CONF_SERVER))) ircd_strncpy(cli_sockhost(cptr), name, HOSTLEN); else - c_conf = find_conf_byip(lp, (char*)&((struct sockaddr_in*)&hp->addr)->sin_addr, CONF_SERVER); + c_conf = find_conf_byip(lp, &hp->addr, CONF_SERVER); } else { /* @@ -1317,7 +1195,7 @@ int conf_check_server(struct Client *cptr) * happen when using DNS in the way the irc server does. -avalon */ if (!c_conf) - c_conf = find_conf_byip(lp, (const char*) &(cli_ip(cptr)), CONF_SERVER); + c_conf = find_conf_byip(lp, &cli_ip(cptr), CONF_SERVER); /* * detach all conf lines that got attached by attach_confs() */ @@ -1337,8 +1215,8 @@ int conf_check_server(struct Client *cptr) attach_conf(cptr, c_conf); attach_confs_byname(cptr, cli_name(cptr), CONF_HUB | CONF_LEAF | CONF_UWORLD); - if (INADDR_NONE == c_conf->ipnum.s_addr) - c_conf->ipnum.s_addr = cli_ip(cptr).s_addr; + if (!irc_in_addr_valid(&c_conf->address.addr)) + memcpy(&c_conf->address.addr, &cli_ip(cptr), sizeof(c_conf->address.addr)); Debug((DEBUG_DNS, "sv_cl: access ok: %s[%s]", cli_name(cptr), cli_sockhost(cptr))); diff --git a/ircd/s_misc.c b/ircd/s_misc.c index e2f56ae..16162a6 100644 --- a/ircd/s_misc.c +++ b/ircd/s_misc.c @@ -403,7 +403,7 @@ int exit_client(struct Client *cptr, /* Connection being handled by "Client exiting: %s (%s@%s) [%s] [%s] <%s%s>", cli_name(victim), cli_user(victim)->username, cli_user(victim)->host, comment, - ircd_ntoa((const char*) &(cli_ip(victim))), + ircd_ntoa(&cli_ip(victim)), NumNick(victim) /* two %s's */); update_load(); @@ -413,7 +413,7 @@ int exit_client(struct Client *cptr, /* Connection being handled by log_write(LS_USER, L_TRACE, 0, "%Tu %i %s@%s %s %s %s%s %s :%s", cli_firsttime(victim), on_for, cli_user(victim)->username, cli_sockhost(victim), - ircd_ntoa((const char*) &(cli_ip(victim))), + ircd_ntoa(&cli_ip(victim)), IsAccount(victim) ? cli_username(victim) : "0", NumNick(victim), /* two %s's */ cli_name(victim), cli_info(victim)); diff --git a/ircd/s_serv.c b/ircd/s_serv.c index 29da252..72d7be0 100644 --- a/ircd/s_serv.c +++ b/ircd/s_serv.c @@ -120,7 +120,7 @@ int server_estab(struct Client *cptr, struct ConfItem *aconf) * XXX - if this comes from a server port, it will not have been added * to the IP check registry, see add_connection in s_bsd.c */ - IPcheck_connect_fail(cli_ip(cptr)); + IPcheck_connect_fail(&cli_ip(cptr)); } det_confs_butmask(cptr, CONF_LEAF | CONF_HUB | CONF_SERVER | CONF_UWORLD); @@ -233,14 +233,14 @@ int server_estab(struct Client *cptr, struct ConfItem *aconf) continue; if (IsUser(acptr)) { - char xxx_buf[8]; + char xxx_buf[25]; char *s = umode_str(acptr); sendcmdto_one(cli_user(acptr)->server, CMD_NICK, cptr, "%s %d %Tu %s %s %s%s%s%s %s%s :%s", cli_name(acptr), cli_hopcount(acptr) + 1, cli_lastnick(acptr), cli_user(acptr)->username, cli_user(acptr)->realhost, *s ? "+" : "", s, *s ? " " : "", - inttobase64(xxx_buf, ntohl(cli_ip(acptr).s_addr), 6), + iptobase64(xxx_buf, &cli_ip(acptr), sizeof(xxx_buf)), NumNick(acptr), cli_info(acptr)); } } diff --git a/ircd/s_stats.c b/ircd/s_stats.c index 75d3b8a..89ef883 100644 --- a/ircd/s_stats.c +++ b/ircd/s_stats.c @@ -106,7 +106,7 @@ stats_configured_links(struct Client *sptr, struct StatDesc* sd, int stat, host = BadPtr(tmp->host) ? null : tmp->host; pass = BadPtr(tmp->passwd) ? null : tmp->passwd; name = BadPtr(tmp->name) ? null : tmp->name; - port = tmp->port; + port = tmp->address.port; /* * On K line the passwd contents can be * displayed on STATS reply. -Vesa @@ -181,7 +181,7 @@ stats_access(struct Client *to, struct StatDesc *sd, int stat, char *param) !mmatch(param, aconf->name)))) { send_reply(to, RPL_STATSILINE, 'I', aconf->host, aconf->name, - aconf->port, get_conf_class(aconf)); + aconf->address.port, get_conf_class(aconf)); if (--count == 0) break; } diff --git a/ircd/s_user.c b/ircd/s_user.c index 98f80b0..02571b0 100644 --- a/ircd/s_user.c +++ b/ircd/s_user.c @@ -364,7 +364,7 @@ int register_user(struct Client *cptr, struct Client *sptr, short digitgroups = 0; struct User* user = cli_user(sptr); int killreason; - char ip_base64[8]; + char ip_base64[25]; user->last = CurrentTime; parv[0] = cli_name(sptr); @@ -401,7 +401,7 @@ int register_user(struct Client *cptr, struct Client *sptr, get_client_name(sptr, SHOW_IP)); } ++ServerStats->is_ref; - IPcheck_connect_fail(cli_ip(sptr)); + IPcheck_connect_fail(&cli_ip(sptr)); return exit_client(cptr, sptr, &me, "Sorry, your connection class is full - try " "again later or try another server"); @@ -420,7 +420,7 @@ int register_user(struct Client *cptr, struct Client *sptr, /* Can this ever happen? */ case ACR_BAD_SOCKET: ++ServerStats->is_ref; - IPcheck_connect_fail(cli_ip(sptr)); + IPcheck_connect_fail(&cli_ip(sptr)); return exit_client(cptr, sptr, &me, "Unknown error -- Try again"); } ircd_strncpy(user->host, cli_sockhost(sptr), HOSTLEN); @@ -630,9 +630,9 @@ int register_user(struct Client *cptr, struct Client *sptr, nick, cli_hopcount(sptr) + 1, cli_lastnick(sptr), user->username, user->realhost, *tmpstr ? "+" : "", tmpstr, *tmpstr ? " " : "", - inttobase64(ip_base64, ntohl(cli_ip(sptr).s_addr), 6), + iptobase64(ip_base64, &cli_ip(sptr), sizeof(ip_base64)), NumNick(sptr), cli_info(sptr)); - + /* Send server notice mask to client */ if (MyUser(sptr) && (cli_snomask(sptr) != SNO_DEFAULT) && HasFlag(sptr, FLAG_SERVNOTICE)) send_reply(sptr, RPL_SNOMASK, cli_snomask(sptr), cli_snomask(sptr)); @@ -707,7 +707,7 @@ int set_nick_name(struct Client* cptr, struct Client* sptr, /* * IP# of remote client */ - cli_ip(new_client).s_addr = htonl(base64toint(parv[parc - 3])); + base64toip(parv[parc - 3], &cli_ip(new_client)); add_client_to_list(new_client); hAddClient(new_client); @@ -1619,7 +1619,7 @@ int is_silenced(struct Client *sptr, struct Client *acptr) ircd_snprintf(0, sender, sizeof(sender), "%s!%s@%s", cli_name(sptr), user->username, user->host); ircd_snprintf(0, senderip, sizeof(senderip), "%s!%s@%s", cli_name(sptr), - user->username, ircd_ntoa((const char*) &(cli_ip(sptr)))); + user->username, ircd_ntoa(&cli_ip(sptr))); if (HasHiddenHost(sptr)) ircd_snprintf(0, senderh, sizeof(senderh), "%s!%s@%s", cli_name(sptr), user->username, user->realhost); diff --git a/ircd/table_gen.c b/ircd/table_gen.c index a82ed93..cc2cc78 100644 --- a/ircd/table_gen.c +++ b/ircd/table_gen.c @@ -110,6 +110,9 @@ static void makeTables(void) moveMacro(NTL_DIGIT, NTL_IRCIP); markString(NTL_IRCIP, "."); + moveMacro(NTL_DIGIT, NTL_IRCIP6); + markString(NTL_IRCIP6, ":.ABCDEFabcdef"); + moveMacro(NTL_DIGIT | NTL_ALPHA, NTL_IRCNK); markString(NTL_IRCNK, "-_`"); diff --git a/ircd/uping.c b/ircd/uping.c index 3c9ea1e..f9a3759 100644 --- a/ircd/uping.c +++ b/ircd/uping.c @@ -53,10 +53,6 @@ #define UPINGTIMEOUT 60 /* Timeout waiting for ping responses */ -#ifndef INADDR_NONE -#define INADDR_NONE 0xffffffff -#endif - static struct UPing* pingList = 0; int UPingFileDescriptor = -1; /* UDP listener socket for upings */ @@ -104,42 +100,15 @@ static void uping_echo_callback(struct Event* ev) */ int uping_init(void) { - struct sockaddr_in from = { 0 }; + struct irc_sockaddr from; int fd; - memset(&from, 0, sizeof(from)); - from.sin_addr = VirtualHost.sin_addr; - from.sin_port = htons(atoi(UDP_PORT)); - from.sin_family = AF_INET; + memcpy(&from, &VirtualHost, sizeof(from)); + from.port = atoi(UDP_PORT); - if ((fd = socket(AF_INET, SOCK_DGRAM, 0)) == -1) { - Debug((DEBUG_ERROR, "UPING: UDP listener socket call failed: %s", - (strerror(errno)) ? strerror(errno) : "Unknown error")); + fd = os_socket(&from, SOCK_DGRAM, "UDP listener socket"); + if (fd < 0) return -1; - } - if (!os_set_reuseaddr(fd)) { - log_write(LS_SOCKET, L_ERROR, 0, - "UPING: set reuseaddr on UDP listener failed: %m (fd %d)", fd); - Debug((DEBUG_ERROR, "UPING: set reuseaddr on UDP listener failed: %s", - (strerror(errno)) ? strerror(errno) : "Unknown error")); - close(fd); - return -1; - } - if (bind(fd, (struct sockaddr*) &from, sizeof(from)) == -1) { - log_write(LS_SOCKET, L_ERROR, 0, - "UPING: bind on UDP listener (%d fd %d) failed: %m", - htons(from.sin_port), fd); - Debug((DEBUG_ERROR, "UPING: bind on UDP listener failed : %s", - (strerror(errno)) ? strerror(errno) : "Unknown error")); - close(fd); - return -1; - } - if (!os_set_nonblocking(fd)) { - Debug((DEBUG_ERROR, "UPING: set non-blocking: %s", - (strerror(errno)) ? strerror(errno) : "Unknown error")); - close(fd); - return -1; - } if (!socket_add(&upingSock, uping_echo_callback, 0, SS_DATAGRAM, SOCK_EVENT_READABLE, fd)) { Debug((DEBUG_ERROR, "UPING: Unable to queue fd to event system")); @@ -156,7 +125,7 @@ int uping_init(void) */ void uping_echo() { - struct sockaddr_in from = { 0 }; + struct irc_sockaddr from; unsigned int len = 0; static time_t last = 0; static int counter = 0; @@ -181,7 +150,7 @@ void uping_echo() } if (len < 19) return; - sendto(UPingFileDescriptor, buf, len, 0, (struct sockaddr*) &from, sizeof(from)); + os_sendto_nonb(UPingFileDescriptor, buf, len, NULL, 0, &from); } @@ -302,11 +271,10 @@ void uping_send(struct UPing* pptr) Debug((DEBUG_SEND, "send_ping: sending [%s %s] to %s.%d on %d", buf, &buf[12], - ircd_ntoa((const char*) &pptr->sin.sin_addr), ntohs(pptr->sin.sin_port), + ircd_ntoa(&pptr->addr.addr), pptr->addr.port, pptr->fd)); - if (sendto(pptr->fd, buf, BUFSIZE, 0, (struct sockaddr*) &pptr->sin, - sizeof(struct sockaddr_in)) != BUFSIZE) + if (os_sendto_nonb(pptr->fd, buf, BUFSIZE, NULL, 0, &pptr->addr) != IO_SUCCESS) { const char* msg = strerror(errno); if (!msg) @@ -326,7 +294,7 @@ void uping_send(struct UPing* pptr) */ void uping_read(struct UPing* pptr) { - struct sockaddr_in sin; + struct irc_sockaddr sin; struct timeval tv; unsigned int len; unsigned int pingtime; @@ -349,11 +317,11 @@ void uping_read(struct UPing* pptr) "%s", pptr->client, msg); uping_end(pptr); return; - } + } if (len < 19) return; /* Broken packet */ - + ++pptr->received; buf[len] = 0; @@ -384,7 +352,7 @@ int uping_server(struct Client* sptr, struct ConfItem* aconf, int port, int coun assert(0 != sptr); assert(0 != aconf); - if (INADDR_NONE == aconf->ipnum.s_addr) { + if (!irc_in_addr_valid(&aconf->address.addr)) { sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :UPING: Host lookup failed for " "%s", sptr, aconf->name); return 0; @@ -393,18 +361,10 @@ int uping_server(struct Client* sptr, struct ConfItem* aconf, int port, int coun if (IsUPing(sptr)) uping_cancel(sptr, sptr); /* Cancel previous ping request */ - if ((fd = socket(AF_INET, SOCK_DGRAM, 0)) == -1) { - sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :UPING: Unable to create udp " - "ping socket", sptr); + fd = os_socket(NULL, SOCK_DGRAM, "UDP ping socket"); + if (fd < 0) return 0; - } - if (!os_set_nonblocking(fd)) { - sendcmdto_one(&me, CMD_NOTICE, sptr, "%C :UPING: Can't set fd non-" - "blocking", sptr); - close(fd); - return 0; - } pptr = (struct UPing*) MyMalloc(sizeof(struct UPing)); assert(0 != pptr); memset(pptr, 0, sizeof(struct UPing)); @@ -419,9 +379,8 @@ int uping_server(struct Client* sptr, struct ConfItem* aconf, int port, int coun } pptr->fd = fd; - pptr->sin.sin_port = htons(port); - pptr->sin.sin_addr.s_addr = aconf->ipnum.s_addr; - pptr->sin.sin_family = AF_INET; + memcpy(&pptr->addr.addr, &aconf->address.addr, sizeof(pptr->addr.addr)); + pptr->addr.port = port; pptr->count = IRCD_MIN(20, count); pptr->client = sptr; pptr->index = -1; diff --git a/ircd/whocmds.c b/ircd/whocmds.c index 8a2f963..3e40dac 100644 --- a/ircd/whocmds.c +++ b/ircd/whocmds.c @@ -124,7 +124,7 @@ void do_who(struct Client* sptr, struct Client* acptr, struct Channel* repchan, { const char* p2 = HasHiddenHost(acptr) && !IsAnOper(sptr) ? feature_str(FEAT_HIDDEN_IP) : - ircd_ntoa((const char*) &(cli_ip(acptr))); + ircd_ntoa(&cli_ip(acptr)); *(p1++) = ' '; while ((*p2) && (*(p1++) = *(p2++))); } @@ -261,7 +261,7 @@ count_users(char *mask) ircd_snprintf(0, namebuf, sizeof(namebuf), "%s@%s", cli_user(acptr)->username, cli_user(acptr)->host); ircd_snprintf(0, ipbuf, sizeof(ipbuf), "%s@%s", cli_user(acptr)->username, - ircd_ntoa((const char *) &(cli_ip(acptr)))); + ircd_ntoa(&cli_ip(acptr))); if (!match(mask, namebuf) || !match(mask, ipbuf)) count++;