Merge branch 'authd-framework' of github.com:charybdis-ircd/charybdis into authd-framework
This commit is contained in:
commit
66e1914beb
230 changed files with 5098 additions and 12141 deletions
9
.appveyor-build.sh
Normal file
9
.appveyor-build.sh
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
set -v
|
||||||
|
|
||||||
|
export MSYSTEM=MINGW64
|
||||||
|
export PATH=/mingw64/bin:/usr/local/bin:/usr/bin:/bin:/c/Windows/system32:/c/Windows:/c/Windows/System32/Wbem:/c/Windows/System32/WindowsPowerShell/v1.0:/usr/bin/site_perl:/usr/bin/vendor_perl:/usr/bin/core_perl
|
||||||
|
|
||||||
|
sh ./autogen.sh
|
||||||
|
./configure --prefix=c:/projects/charybdis/build --enable-openssl=/mingw64
|
||||||
|
make -j2
|
||||||
|
make install
|
15
.appveyor.yml
Normal file
15
.appveyor.yml
Normal file
|
@ -0,0 +1,15 @@
|
||||||
|
version: 3.6-dev_{build}
|
||||||
|
clone_depth: 10
|
||||||
|
install:
|
||||||
|
- c:\msys64\usr\bin\sh.exe -lc "pacman -Sy --noconfirm git"
|
||||||
|
- c:\msys64\usr\bin\sh.exe -lc "uname -a"
|
||||||
|
- c:\msys64\usr\bin\sh.exe -lc "cat /proc/cpuinfo"
|
||||||
|
- c:\msys64\usr\bin\sh.exe -lc "cat /proc/meminfo"
|
||||||
|
- c:\msys64\usr\bin\sh.exe -lc "cygcheck -s -v > $APPVEYOR_BUILD_FOLDER/cygcheck.log 2>&1"
|
||||||
|
- ps: Push-AppveyorArtifact cygcheck.log
|
||||||
|
build_script:
|
||||||
|
- c:\msys64\usr\bin\sh.exe -lc "cd $APPVEYOR_BUILD_FOLDER; sh .appveyor-build.sh"
|
||||||
|
# - c:\msys64\usr\bin\sh.exe -lc "cd $APPVEYOR_BUILD_FOLDER/build/bin; ./charybdis -version"
|
||||||
|
on_failure:
|
||||||
|
- ps: Push-AppveyorArtifact config.log
|
||||||
|
- ps: Push-AppveyorArtifact librb\include\librb-config.h
|
30
.gitignore
vendored
30
.gitignore
vendored
|
@ -12,31 +12,48 @@ Makefile
|
||||||
.dirstamp
|
.dirstamp
|
||||||
.libs
|
.libs
|
||||||
authd/authd
|
authd/authd
|
||||||
autom4te.cache
|
|
||||||
bandb/bandb
|
bandb/bandb
|
||||||
bandb/bantool
|
bandb/bantool
|
||||||
|
autom4te.cache
|
||||||
|
aclocal.m4
|
||||||
|
compile
|
||||||
|
config.guess
|
||||||
|
config.sub
|
||||||
|
depcomp
|
||||||
|
ltmain.sh
|
||||||
|
missing
|
||||||
config.log
|
config.log
|
||||||
config.status
|
config.status
|
||||||
configure
|
configure
|
||||||
stamp-h1
|
stamp-h1
|
||||||
include/setup.h
|
|
||||||
libltdl/
|
libltdl/
|
||||||
librb/configure
|
librb/configure
|
||||||
librb/include/libratbox_config.h
|
librb/compile
|
||||||
|
librb/depcomp
|
||||||
|
librb/aclocal.m4
|
||||||
|
librb/include/librb_config.h
|
||||||
|
librb/include/librb_config.h.in
|
||||||
librb/include/librb-config.h
|
librb/include/librb-config.h
|
||||||
|
librb/include/serno.h
|
||||||
|
librb/librb.pc
|
||||||
|
librb/ltmain.sh
|
||||||
|
librb/missing
|
||||||
librb/libratbox.pc
|
librb/libratbox.pc
|
||||||
librb/libtool
|
librb/libtool
|
||||||
librb/src/version.c
|
librb/src/version.c
|
||||||
librb/src/version.c.last
|
librb/src/version.c.last
|
||||||
scripts/*.tar.bz2
|
scripts/*.tar.bz2
|
||||||
scripts/*.tar.gz
|
scripts/*.tar.gz
|
||||||
|
include/setup.h
|
||||||
|
include/setup.h.in
|
||||||
ircd/charybdis
|
ircd/charybdis
|
||||||
ircd/lex.yy.c
|
ircd/ircd_parser.c
|
||||||
|
ircd/ircd_parser.h
|
||||||
|
ircd/ircd_lexer.c
|
||||||
ircd/version.c
|
ircd/version.c
|
||||||
ircd/version.c.last
|
ircd/version.c.last
|
||||||
ircd/y.tab.h
|
|
||||||
ircd/y.tab.c
|
|
||||||
ssld/ssld
|
ssld/ssld
|
||||||
|
wsockd/wsockd
|
||||||
tools/charybdis-mkpasswd
|
tools/charybdis-mkpasswd
|
||||||
tools/genssl
|
tools/genssl
|
||||||
tools/mkpasswd
|
tools/mkpasswd
|
||||||
|
@ -47,6 +64,7 @@ ircd/version.c
|
||||||
ircd/version.c.last
|
ircd/version.c.last
|
||||||
/libtool
|
/libtool
|
||||||
Makefile.in
|
Makefile.in
|
||||||
|
m4/argz.m4
|
||||||
m4/libtool.m4
|
m4/libtool.m4
|
||||||
m4/ltargz.m4
|
m4/ltargz.m4
|
||||||
m4/ltdl.m4
|
m4/ltdl.m4
|
||||||
|
|
4
.mailmap
4
.mailmap
|
@ -17,5 +17,5 @@ Valeriy Yatsko <dwr@shadowircd.net> <darkwire@sellcenter.ru>
|
||||||
Valeriy Yatsko <dwr@shadowircd.net> <dwr@it-penza.org>
|
Valeriy Yatsko <dwr@shadowircd.net> <dwr@it-penza.org>
|
||||||
William Pitcock <nenolod@dereferenced.org> <nenolod@atheme.org>
|
William Pitcock <nenolod@dereferenced.org> <nenolod@atheme.org>
|
||||||
William Pitcock <nenolod@dereferenced.org> nenolod <devnull@localhost>
|
William Pitcock <nenolod@dereferenced.org> nenolod <devnull@localhost>
|
||||||
Sam Dodrill <shadow.h511@gmail.com> <quora@lavabit.com>
|
Christine Dodrill <shadow.h511@gmail.com> <quora@lavabit.com>
|
||||||
Sam Dodrill <shadow.h511@gmail.com> <quorawings@gmail.com>
|
Christine Dodrill <shadow.h511@gmail.com> <quorawings@gmail.com>
|
||||||
|
|
|
@ -44,9 +44,6 @@ matrix:
|
||||||
compiler: clang
|
compiler: clang
|
||||||
env: COMPILER=clang LIBTOOLIZE=glibtoolize
|
env: COMPILER=clang LIBTOOLIZE=glibtoolize
|
||||||
|
|
||||||
branches:
|
|
||||||
except:
|
|
||||||
- authd-framework
|
|
||||||
|
|
||||||
osx_image: xcode7.3
|
osx_image: xcode7.3
|
||||||
|
|
||||||
|
|
3
CREDITS
3
CREDITS
|
@ -26,6 +26,7 @@ in nick-alphabetical order:
|
||||||
AndroSyn, Aaron Sethman <androsyn -at- ratbox.org>
|
AndroSyn, Aaron Sethman <androsyn -at- ratbox.org>
|
||||||
anfl, Lee Hardy <lee -at- leeh.co.uk>
|
anfl, Lee Hardy <lee -at- leeh.co.uk>
|
||||||
beu, Elfyn McBratney <elfyn.mcbratney -at- gmail.com>
|
beu, Elfyn McBratney <elfyn.mcbratney -at- gmail.com>
|
||||||
|
BlindSight, Matt Ullman <matt -at- airraidsirens.com>
|
||||||
Entrope, Michael Poole <mdpoole -at- trolius.org>
|
Entrope, Michael Poole <mdpoole -at- trolius.org>
|
||||||
gxti, Michael Tharp <gxti -at- partiallystapled.com>
|
gxti, Michael Tharp <gxti -at- partiallystapled.com>
|
||||||
Taros, Brett Greenham <taros -at- shadowircd.net>
|
Taros, Brett Greenham <taros -at- shadowircd.net>
|
||||||
|
@ -33,7 +34,7 @@ ThaPrince, Jon Christopherson <jon -at- vile.com>
|
||||||
twincest, River Tarnell <river -at- attenuate.org>
|
twincest, River Tarnell <river -at- attenuate.org>
|
||||||
w00t, Robin Burchell <surreal.w00t -at- gmail.com>
|
w00t, Robin Burchell <surreal.w00t -at- gmail.com>
|
||||||
|
|
||||||
For a list of contributors to ircd-ratbox, ircd-hyrbid, and ircd2.8 (the
|
For a list of contributors to ircd-ratbox, ircd-hybrid, and ircd2.8 (the
|
||||||
predecessors to Charybdis), see the doc/credits-past.txt file in the Charybdis
|
predecessors to Charybdis), see the doc/credits-past.txt file in the Charybdis
|
||||||
distribution.
|
distribution.
|
||||||
|
|
||||||
|
|
12
Makefile.am
12
Makefile.am
|
@ -9,6 +9,7 @@ endif
|
||||||
|
|
||||||
SUBDIRS += ircd \
|
SUBDIRS += ircd \
|
||||||
ssld \
|
ssld \
|
||||||
|
wsockd \
|
||||||
authd \
|
authd \
|
||||||
bandb \
|
bandb \
|
||||||
tools \
|
tools \
|
||||||
|
@ -37,3 +38,14 @@ include/serno.h:
|
||||||
|
|
||||||
install-data-hook:
|
install-data-hook:
|
||||||
test -d ${DESTDIR}${logdir} || mkdir -p ${DESTDIR}${logdir}
|
test -d ${DESTDIR}${logdir} || mkdir -p ${DESTDIR}${logdir}
|
||||||
|
|
||||||
|
install-exec-hook:
|
||||||
|
rm -f ${DESTDIR}${moduledir}/*.la
|
||||||
|
rm -f ${DESTDIR}${moduledir}/autoload/*.la
|
||||||
|
rm -f ${DESTDIR}${moduledir}/extensions/*.la
|
||||||
|
rm -f ${DESTDIR}${moduledir}/*.dll.a
|
||||||
|
rm -f ${DESTDIR}${moduledir}/autoload/*.dll.a
|
||||||
|
rm -f ${DESTDIR}${moduledir}/extensions/*.dll.a
|
||||||
|
|
||||||
|
clean-local:
|
||||||
|
rm -f include/serno.h
|
||||||
|
|
5
NEWS.md
5
NEWS.md
|
@ -42,6 +42,11 @@ See LICENSE for licensing details (GPL v2).
|
||||||
stuff has been renamed and shuffled around to be more consistent.
|
stuff has been renamed and shuffled around to be more consistent.
|
||||||
|
|
||||||
### code
|
### code
|
||||||
|
- irc_dictionary and irc_radixtree stuff is now in librb, prefixed accordingly.
|
||||||
|
Typedefs have been added for consistency reasons. For example, now you would
|
||||||
|
write `rb_dictionary *foo` and `RB_DICTIONARY_FOREACH`.
|
||||||
|
- C99 bools have been added. Don't use ints as simple true/false flags anymore.
|
||||||
|
Accordingly, the `YES`/`NO` and `TRUE`/`FALSE` macros have been removed.
|
||||||
- libratbox has been renamed to librb, as we have diverged from upstream long
|
- libratbox has been renamed to librb, as we have diverged from upstream long
|
||||||
ago.
|
ago.
|
||||||
- Almost all 2.8-style hashtable structures have been moved to dictionaries or
|
- Almost all 2.8-style hashtable structures have been moved to dictionaries or
|
||||||
|
|
80
README.md
80
README.md
|
@ -1,4 +1,4 @@
|
||||||
# charybdis [![Build Status](https://travis-ci.org/charybdis-ircd/charybdis.svg?branch=master)](https://travis-ci.org/charybdis-ircd/charybdis)
|
# charybdis [![POSIX Build Status](https://travis-ci.org/charybdis-ircd/charybdis.svg?branch=master)](https://travis-ci.org/charybdis-ircd/charybdis) [![Windows Build Status](https://ci.appveyor.com/api/projects/status/is0obsml8xyq2qk7/branch/master?svg=true)](https://ci.appveyor.com/project/kaniini/charybdis/branch/master)
|
||||||
|
|
||||||
Charybdis is an IRCv3 server designed to be highly scalable. It implements IRCv3.1 and some parts of IRCv3.2.
|
Charybdis is an IRCv3 server designed to be highly scalable. It implements IRCv3.1 and some parts of IRCv3.2.
|
||||||
|
|
||||||
|
@ -10,8 +10,52 @@ It is meant to be used with an IRCv3-capable services implementation such as [At
|
||||||
# necessary requirements
|
# necessary requirements
|
||||||
|
|
||||||
* A supported platform
|
* A supported platform
|
||||||
* A working dynamic load library.
|
* A working dynamic library system
|
||||||
* A working lex. Solaris /usr/ccs/bin/lex appears to be broken, on this system flex should be used.
|
* A working lex and yacc - flex and bison should work
|
||||||
|
|
||||||
|
# platforms
|
||||||
|
|
||||||
|
Charybdis is designed with portability in mind, but does not target older systems nor those of solely academic
|
||||||
|
interest.
|
||||||
|
|
||||||
|
Do note that operating systems are only supported if they are supported by their vendor.
|
||||||
|
|
||||||
|
## Tier 1
|
||||||
|
|
||||||
|
These platforms are the best supported, and should always work. They are actively tested. If you encounter
|
||||||
|
problems, please file a bug.
|
||||||
|
|
||||||
|
* FreeBSD 10.x and above (i386 and amd64)
|
||||||
|
* Linux 2.6.x and above with glibc or musl (i386, x86_64, and ARM)
|
||||||
|
* Mac OS X 10.7 and above
|
||||||
|
* Windows Vista/Server 2008 and above (x86 or x64)
|
||||||
|
|
||||||
|
## Tier 2
|
||||||
|
|
||||||
|
These platforms are supported and occasionally tested, and most features should work, but this is not
|
||||||
|
guaranteed. If you find any problems, file a bug, but as these are not regularly tested platforms, a timely
|
||||||
|
resolution may not be possible.
|
||||||
|
|
||||||
|
* DragonflyBSD 4.4 and above (i386)
|
||||||
|
* Linux with uClibc (i386 or x86_64)
|
||||||
|
* NetBSD 6.1.x and above (i386, amd64)
|
||||||
|
* OpenBSD 5.6 and above (i386, amd64)
|
||||||
|
* Solaris 10 and above (i386)
|
||||||
|
|
||||||
|
## Tier 3
|
||||||
|
|
||||||
|
Anything else that hasn't been tested. Charybdis may or may not work on it; patches welcome if they don't.
|
||||||
|
|
||||||
|
# platform specific errata
|
||||||
|
|
||||||
|
These are known issues and workarounds for supported platforms.
|
||||||
|
|
||||||
|
* **FreeBSD**: if you are compiling with ipv6 you may experience
|
||||||
|
problems with ipv4 due to the way the socket code is written. To
|
||||||
|
fix this you must: "sysctl net.inet6.ip6.v6only=0"
|
||||||
|
|
||||||
|
* **Solaris**: you may have to set your PATH to include /usr/gnu/bin and /usr/gnu/sbin before /usr/bin
|
||||||
|
and /usr/sbin. Solaris's default tools don't seem to play nicely with the configure script.
|
||||||
|
|
||||||
# building from git
|
# building from git
|
||||||
|
|
||||||
|
@ -31,9 +75,8 @@ You will need to run `autogen.sh` to build the autotools files prior to building
|
||||||
(Using CHALLENGE is not recommended for new deployments, so if you want to use a different TLS library,
|
(Using CHALLENGE is not recommended for new deployments, so if you want to use a different TLS library,
|
||||||
feel free.)
|
feel free.)
|
||||||
|
|
||||||
* For ECDHE, OpenSSL 1.0.0 or newer is required. RHEL/Fedora and derivatives like CentOS
|
* For ECDHE, OpenSSL 1.0.0 or newer is required. Solaris; and RHEL/Fedora and its derivatives such as CentOS
|
||||||
will need to compile OpenSSL from source, as ECC/ECDHE-functionality is removed from
|
have removed support for ECC/ECDHE. You will need to compile your own OpenSSL on these systems.
|
||||||
the OpenSSL package in these distributions.
|
|
||||||
|
|
||||||
# tips
|
# tips
|
||||||
|
|
||||||
|
@ -41,31 +84,10 @@ You will need to run `autogen.sh` to build the autotools files prior to building
|
||||||
|
|
||||||
* Please read doc/index.txt to get an overview of the current documentation.
|
* Please read doc/index.txt to get an overview of the current documentation.
|
||||||
|
|
||||||
|
* Read the NEWS file for what's new in this release.
|
||||||
|
|
||||||
* The files, /etc/services, /etc/protocols, and /etc/resolv.conf, SHOULD be
|
* The files, /etc/services, /etc/protocols, and /etc/resolv.conf, SHOULD be
|
||||||
readable by the user running the server in order for ircd to start with
|
readable by the user running the server in order for ircd to start with
|
||||||
the correct settings. If these files are wrong, charybdis will try to use
|
the correct settings. If these files are wrong, charybdis will try to use
|
||||||
127.0.0.1 for a resolver as a last-ditch effort.
|
127.0.0.1 for a resolver as a last-ditch effort.
|
||||||
|
|
||||||
* FREEBSD USERS: if you are compiling with ipv6 you may experience
|
|
||||||
problems with ipv4 due to the way the socket code is written. To
|
|
||||||
fix this you must: "sysctl net.inet6.ip6.v6only=0"
|
|
||||||
|
|
||||||
* SOLARIS USERS: this code appears to tickle a bug in older gcc and
|
|
||||||
egcs ONLY on 64-bit Solaris7. gcc-2.95 and SunPro C on 64bit should
|
|
||||||
work fine, and any gcc or SunPro compiled on 32bit.
|
|
||||||
|
|
||||||
* SUPPORTED PLATFORMS: this code should compile without any warnings on:
|
|
||||||
|
|
||||||
* FreeBSD 10
|
|
||||||
* Gentoo & Gentoo Hardened ~x86/~amd64/~fbsd
|
|
||||||
* RHEL 6 / 7
|
|
||||||
* Debian Jessie
|
|
||||||
* OpenSuSE 11/12
|
|
||||||
* OpenSolaris 2008.x?
|
|
||||||
* Solaris 10 sparc.
|
|
||||||
|
|
||||||
Please let us know if you find otherwise. It may work on other platforms, but this is not guaranteed.
|
|
||||||
|
|
||||||
* Please read NEWS for information about what is in this release.
|
|
||||||
|
|
||||||
* Other files recommended for reading: BUGS, INSTALL
|
|
||||||
|
|
1221
aclocal.m4
vendored
1221
aclocal.m4
vendored
File diff suppressed because it is too large
Load diff
|
@ -2,13 +2,18 @@ pkglibexec_PROGRAMS = authd
|
||||||
AM_CFLAGS=$(WARNFLAGS)
|
AM_CFLAGS=$(WARNFLAGS)
|
||||||
AM_CPPFLAGS = -I../include -I../librb/include
|
AM_CPPFLAGS = -I../include -I../librb/include
|
||||||
|
|
||||||
|
authd_SOURCES = \
|
||||||
authd_SOURCES = provider.c \
|
|
||||||
authd.c \
|
authd.c \
|
||||||
|
dns.c \
|
||||||
|
getaddrinfo.c \
|
||||||
|
getnameinfo.c \
|
||||||
|
notice.c \
|
||||||
|
provider.c \
|
||||||
res.c \
|
res.c \
|
||||||
reslib.c \
|
reslib.c \
|
||||||
dns.c \
|
reslist.c \
|
||||||
providers/rdns.c \
|
providers/blacklist.c \
|
||||||
providers/ident.c
|
providers/ident.c \
|
||||||
|
providers/rdns.c
|
||||||
|
|
||||||
authd_LDADD = ../librb/src/librb.la
|
authd_LDADD = ../librb/src/librb.la
|
||||||
|
|
|
@ -21,17 +21,21 @@
|
||||||
#include "authd.h"
|
#include "authd.h"
|
||||||
#include "dns.h"
|
#include "dns.h"
|
||||||
#include "provider.h"
|
#include "provider.h"
|
||||||
|
#include "notice.h"
|
||||||
|
|
||||||
#define MAXPARA 10
|
#define MAXPARA 10
|
||||||
|
|
||||||
static void handle_reload(int parc, char *parv[]);
|
static void handle_reload(int parc, char *parv[]);
|
||||||
static void handle_stat(int parc, char *parv[]);
|
static void handle_stat(int parc, char *parv[]);
|
||||||
|
static void handle_options(int parc, char *parv[]);
|
||||||
|
|
||||||
rb_helper *authd_helper = NULL;
|
rb_helper *authd_helper = NULL;
|
||||||
authd_cmd_handler authd_cmd_handlers[256] = {
|
authd_cmd_handler authd_cmd_handlers[256] = {
|
||||||
['C'] = handle_new_connection,
|
['C'] = handle_new_connection,
|
||||||
['D'] = resolve_dns,
|
['D'] = handle_resolve_dns,
|
||||||
['H'] = handle_reload,
|
['E'] = handle_cancel_connection,
|
||||||
|
['O'] = handle_options,
|
||||||
|
['R'] = handle_reload,
|
||||||
['S'] = handle_stat,
|
['S'] = handle_stat,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -43,31 +47,69 @@ authd_reload_handler authd_reload_handlers[256] = {
|
||||||
['D'] = reload_nameservers,
|
['D'] = reload_nameservers,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
rb_dictionary *authd_option_handlers;
|
||||||
|
|
||||||
static void
|
static void
|
||||||
handle_stat(int parc, char *parv[])
|
handle_stat(int parc, char *parv[])
|
||||||
{
|
{
|
||||||
authd_stat_handler handler;
|
authd_stat_handler handler;
|
||||||
|
|
||||||
if(parc < 3)
|
if(parc < 3)
|
||||||
/* XXX Should log this somehow */
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: handle_stat received too few parameters (at least 3 expected, got %d)", parc);
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (!(handler = authd_stat_handlers[parv[2][0]]))
|
if (!(handler = authd_stat_handlers[(unsigned char)parv[2][0]]))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
handler(parv[1], parv[2][0]);
|
handler(parv[1], parv[2][0]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
handle_options(int parc, char *parv[])
|
||||||
|
{
|
||||||
|
struct auth_opts_handler *handler;
|
||||||
|
|
||||||
|
if(parc < 4)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: handle_options received too few parameters (at least 4 expected, got %d)", parc);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if((handler = rb_dictionary_retrieve(authd_option_handlers, parv[1])) == NULL)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: handle_options got a bad option type %s", parv[1]);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if((parc - 2) < handler->min_parc)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: handle_options received too few parameters (at least %d expected, got %d)", handler->min_parc, parc);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
handler->handler(parv[1], parc - 2, (const char **)&parv[2]);
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
handle_reload(int parc, char *parv[])
|
handle_reload(int parc, char *parv[])
|
||||||
{
|
{
|
||||||
authd_reload_handler handler;
|
authd_reload_handler handler;
|
||||||
|
|
||||||
if(parc < 2)
|
if(parc < 2)
|
||||||
/* XXX Should log this somehow */
|
{
|
||||||
return;
|
/* Reload all handlers */
|
||||||
|
for(size_t i = 0; i < 256; i++)
|
||||||
|
{
|
||||||
|
if ((handler = authd_reload_handlers[(unsigned char) i]) != NULL)
|
||||||
|
handler(parv[1][0]);
|
||||||
|
}
|
||||||
|
|
||||||
if (!(handler = authd_reload_handlers[parv[1][0]]))
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!(handler = authd_reload_handlers[(unsigned char)parv[1][0]]))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
handler(parv[1][0]);
|
handler(parv[1][0]);
|
||||||
|
@ -89,7 +131,7 @@ parse_request(rb_helper *helper)
|
||||||
if(parc < 1)
|
if(parc < 1)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
handler = authd_cmd_handlers[parv[0][0]];
|
handler = authd_cmd_handlers[(unsigned char)parv[0][0]];
|
||||||
if (handler != NULL)
|
if (handler != NULL)
|
||||||
handler(parc, parv);
|
handler(parc, parv);
|
||||||
}
|
}
|
||||||
|
@ -101,7 +143,7 @@ error_cb(rb_helper *helper)
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifndef WINDOWS
|
#ifndef _WIN32
|
||||||
static void
|
static void
|
||||||
dummy_handler(int sig)
|
dummy_handler(int sig)
|
||||||
{
|
{
|
||||||
|
@ -112,7 +154,7 @@ dummy_handler(int sig)
|
||||||
static void
|
static void
|
||||||
setup_signals(void)
|
setup_signals(void)
|
||||||
{
|
{
|
||||||
#ifndef WINDOWS
|
#ifndef _WIN32
|
||||||
struct sigaction act;
|
struct sigaction act;
|
||||||
|
|
||||||
act.sa_flags = 0;
|
act.sa_flags = 0;
|
||||||
|
@ -152,11 +194,16 @@ main(int argc, char *argv[])
|
||||||
|
|
||||||
rb_set_time();
|
rb_set_time();
|
||||||
setup_signals();
|
setup_signals();
|
||||||
|
|
||||||
|
authd_option_handlers = rb_dictionary_create("authd options handlers", strcasecmp);
|
||||||
|
|
||||||
init_resolver();
|
init_resolver();
|
||||||
init_providers();
|
init_providers();
|
||||||
rb_init_prng(NULL, RB_PRNG_DEFAULT);
|
rb_init_prng(NULL, RB_PRNG_DEFAULT);
|
||||||
|
|
||||||
rb_helper_loop(authd_helper, 0);
|
rb_helper_loop(authd_helper, 0);
|
||||||
|
|
||||||
|
destroy_providers();
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,11 +21,21 @@
|
||||||
#ifndef _AUTHD_H
|
#ifndef _AUTHD_H
|
||||||
#define _AUTHD_H
|
#define _AUTHD_H
|
||||||
|
|
||||||
#include <rb_lib.h>
|
#include "stdinc.h"
|
||||||
#include <stdio.h>
|
#include "rb_lib.h"
|
||||||
|
#include "rb_dictionary.h"
|
||||||
|
|
||||||
#include "setup.h"
|
#include "setup.h"
|
||||||
#include "common.h"
|
#include "ircd_defs.h"
|
||||||
|
|
||||||
|
typedef void (*provider_opts_handler_t)(const char *, int, const char **);
|
||||||
|
|
||||||
|
struct auth_opts_handler
|
||||||
|
{
|
||||||
|
const char *option;
|
||||||
|
int min_parc;
|
||||||
|
provider_opts_handler_t handler;
|
||||||
|
};
|
||||||
|
|
||||||
extern rb_helper *authd_helper;
|
extern rb_helper *authd_helper;
|
||||||
|
|
||||||
|
@ -37,4 +47,6 @@ extern authd_cmd_handler authd_cmd_handlers[256];
|
||||||
extern authd_stat_handler authd_stat_handlers[256];
|
extern authd_stat_handler authd_stat_handlers[256];
|
||||||
extern authd_reload_handler authd_reload_handlers[256];
|
extern authd_reload_handler authd_reload_handlers[256];
|
||||||
|
|
||||||
|
extern rb_dictionary *authd_option_handlers;
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
287
authd/dns.c
287
authd/dns.c
|
@ -1,4 +1,4 @@
|
||||||
/* authd/dns.h - header for authd DNS functions
|
/* authd/dns.c - authd DNS functions
|
||||||
* Copyright (c) 2016 William Pitcock <nenolod@dereferenced.org>
|
* Copyright (c) 2016 William Pitcock <nenolod@dereferenced.org>
|
||||||
*
|
*
|
||||||
* Permission to use, copy, modify, and/or distribute this software for any
|
* Permission to use, copy, modify, and/or distribute this software for any
|
||||||
|
@ -22,140 +22,238 @@
|
||||||
#include "dns.h"
|
#include "dns.h"
|
||||||
#include "res.h"
|
#include "res.h"
|
||||||
|
|
||||||
void
|
static void handle_lookup_ip_reply(void *data, struct DNSReply *reply);
|
||||||
format_address(struct rb_sockaddr_storage *addr, char *buffer, size_t length)
|
static void handle_lookup_hostname_reply(void *data, struct DNSReply *reply);
|
||||||
|
|
||||||
|
uint64_t query_count = 0;
|
||||||
|
|
||||||
|
/* A bit different from ircd... you just get a dns_query object.
|
||||||
|
*
|
||||||
|
* It gets freed whenever the res code gets back to us.
|
||||||
|
*/
|
||||||
|
struct dns_query *
|
||||||
|
lookup_ip(const char *host, int aftype, DNSCB callback, void *data)
|
||||||
{
|
{
|
||||||
if(GET_SS_FAMILY(addr) == AF_INET)
|
struct dns_query *query = rb_malloc(sizeof(struct dns_query));
|
||||||
|
int g_type;
|
||||||
|
|
||||||
|
if(aftype == AF_INET)
|
||||||
{
|
{
|
||||||
rb_inet_ntop_sock((struct sockaddr *)addr, buffer, length);
|
query->type = QUERY_A;
|
||||||
|
g_type = T_A;
|
||||||
}
|
}
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
else if(GET_SS_FAMILY(addr) == AF_INET6)
|
else if(aftype == AF_INET6)
|
||||||
{
|
{
|
||||||
char tmpbuf[length];
|
query->type = QUERY_AAAA;
|
||||||
|
g_type = T_AAAA;
|
||||||
rb_inet_ntop_sock((struct sockaddr *)addr, tmpbuf, length);
|
|
||||||
|
|
||||||
if(*tmpbuf == ':')
|
|
||||||
{
|
|
||||||
rb_strlcpy(buffer, "0", length);
|
|
||||||
rb_strlcat(buffer, tmpbuf, length);
|
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
else
|
else
|
||||||
rb_strlcpy(buffer, tmpbuf, length);
|
{
|
||||||
|
rb_free(query);
|
||||||
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
query->id = query_count++;
|
||||||
|
query->callback = callback;
|
||||||
|
query->data = data;
|
||||||
|
|
||||||
|
query->query.ptr = query;
|
||||||
|
query->query.callback = handle_lookup_ip_reply;
|
||||||
|
|
||||||
|
gethost_byname_type(host, &query->query, g_type);
|
||||||
|
|
||||||
|
return query;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* See lookup_ip's comment */
|
||||||
|
struct dns_query *
|
||||||
|
lookup_hostname(const char *ip, DNSCB callback, void *data)
|
||||||
|
{
|
||||||
|
struct dns_query *query = rb_malloc(sizeof(struct dns_query));
|
||||||
|
int aftype;
|
||||||
|
|
||||||
|
if(!rb_inet_pton_sock(ip, (struct sockaddr *)&query->addr))
|
||||||
|
{
|
||||||
|
rb_free(query);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
aftype = GET_SS_FAMILY(&query->addr);
|
||||||
|
|
||||||
|
if(aftype == AF_INET)
|
||||||
|
query->type = QUERY_PTR_A;
|
||||||
|
#ifdef RB_IPV6
|
||||||
|
else if(aftype == AF_INET6)
|
||||||
|
query->type = QUERY_PTR_AAAA;
|
||||||
#endif
|
#endif
|
||||||
|
else
|
||||||
|
{
|
||||||
|
rb_free(query);
|
||||||
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
query->id = query_count++;
|
||||||
sockcmp(struct rb_sockaddr_storage *addr, struct rb_sockaddr_storage *addr2, int family)
|
query->callback = callback;
|
||||||
{
|
query->data = data;
|
||||||
if(family == AF_INET)
|
|
||||||
{
|
|
||||||
struct sockaddr_in *ip, *ip2;
|
|
||||||
ip = (struct sockaddr_in *)addr;
|
|
||||||
ip2 = (struct sockaddr_in *)addr2;
|
|
||||||
|
|
||||||
return ip->sin_addr.s_addr == ip2->sin_addr.s_addr;
|
query->query.ptr = query;
|
||||||
|
query->query.callback = handle_lookup_hostname_reply;
|
||||||
|
|
||||||
|
gethost_byaddr(&query->addr, &query->query);
|
||||||
|
|
||||||
|
return query;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Cancel a pending query */
|
||||||
|
void
|
||||||
|
cancel_query(struct dns_query *query)
|
||||||
|
{
|
||||||
|
query->callback = query->data = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Callback from gethost_byname_type */
|
||||||
|
static void
|
||||||
|
handle_lookup_ip_reply(void *data, struct DNSReply *reply)
|
||||||
|
{
|
||||||
|
struct dns_query *query = data;
|
||||||
|
char ip[64] = "*";
|
||||||
|
|
||||||
|
if(query == NULL)
|
||||||
|
/* Shouldn't happen */
|
||||||
|
exit(2);
|
||||||
|
|
||||||
|
if(reply == NULL)
|
||||||
|
goto end;
|
||||||
|
|
||||||
|
switch(query->type)
|
||||||
|
{
|
||||||
|
case QUERY_A:
|
||||||
|
if(GET_SS_FAMILY(&reply->addr) == AF_INET)
|
||||||
|
rb_inet_ntop_sock((struct sockaddr *)&reply->addr, ip, sizeof(ip));
|
||||||
|
break;
|
||||||
|
#ifdef RB_IPV6
|
||||||
|
case QUERY_AAAA:
|
||||||
|
if(GET_SS_FAMILY(&reply->addr) == AF_INET6)
|
||||||
|
{
|
||||||
|
rb_inet_ntop_sock((struct sockaddr *)&reply->addr, ip, sizeof(ip));
|
||||||
|
if(ip[0] == ':')
|
||||||
|
{
|
||||||
|
memmove(&ip[1], ip, strlen(ip));
|
||||||
|
ip[0] = '0';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
#endif
|
||||||
|
default:
|
||||||
|
exit(3);
|
||||||
|
}
|
||||||
|
|
||||||
|
end:
|
||||||
|
if(query->callback)
|
||||||
|
query->callback(ip, ip[0] != '*', query->type, query->data);
|
||||||
|
|
||||||
|
rb_free(query);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Callback from gethost_byaddr */
|
||||||
|
static void
|
||||||
|
handle_lookup_hostname_reply(void *data, struct DNSReply *reply)
|
||||||
|
{
|
||||||
|
struct dns_query *query = data;
|
||||||
|
char *hostname = NULL;
|
||||||
|
|
||||||
|
if(query == NULL)
|
||||||
|
/* Shouldn't happen */
|
||||||
|
exit(4);
|
||||||
|
|
||||||
|
if(reply == NULL)
|
||||||
|
goto end;
|
||||||
|
|
||||||
|
if(query->type == QUERY_PTR_A)
|
||||||
|
{
|
||||||
|
struct sockaddr_in *ip, *ip_fwd;
|
||||||
|
ip = (struct sockaddr_in *) &query->addr;
|
||||||
|
ip_fwd = (struct sockaddr_in *) &reply->addr;
|
||||||
|
|
||||||
|
if(ip->sin_addr.s_addr == ip_fwd->sin_addr.s_addr)
|
||||||
|
hostname = reply->h_name;
|
||||||
}
|
}
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
else if(family == AF_INET6)
|
else if(query->type == QUERY_PTR_AAAA)
|
||||||
{
|
{
|
||||||
struct sockaddr_in6 *ip, *ip2;
|
struct sockaddr_in6 *ip, *ip_fwd;
|
||||||
ip = (struct sockaddr_in6 *) addr;
|
ip = (struct sockaddr_in6 *) &query->addr;
|
||||||
ip2 = (struct sockaddr_in6 *) addr2;
|
ip_fwd = (struct sockaddr_in6 *) &reply->addr;
|
||||||
|
|
||||||
return(memcmp(&ip->sin6_addr, &ip2->sin6_addr, sizeof(struct in6_addr)) == 0);
|
if(memcmp(&ip->sin6_addr, &ip_fwd->sin6_addr, sizeof(struct in6_addr)) == 0)
|
||||||
|
hostname = reply->h_name;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
else
|
||||||
|
/* Shouldn't happen */
|
||||||
|
exit(5);
|
||||||
|
end:
|
||||||
|
if(query->callback)
|
||||||
|
query->callback(hostname, hostname != NULL, query->type, query->data);
|
||||||
|
|
||||||
return false;
|
rb_free(query);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
submit_dns_answer(void *userdata, struct DNSReply *reply)
|
submit_dns_answer(const char *reply, bool status, query_type type, void *data)
|
||||||
{
|
{
|
||||||
struct dns_request *req = userdata;
|
char *id = data;
|
||||||
char response[64] = "*";
|
|
||||||
char status = 'E';
|
|
||||||
int family = AF_INET;
|
|
||||||
|
|
||||||
if (reply == NULL)
|
if(!id || type == QUERY_INVALID)
|
||||||
|
exit(6);
|
||||||
|
|
||||||
|
if(reply == NULL || status == false)
|
||||||
{
|
{
|
||||||
rb_helper_write(authd_helper, "E %s E %c *", req->reqid, req->type);
|
rb_helper_write(authd_helper, "E %s E %c *", id, type);
|
||||||
goto cleanup;
|
rb_free(id);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
switch (req->type)
|
rb_helper_write(authd_helper, "E %s O %c %s", id, type, reply);
|
||||||
|
rb_free(id);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
handle_resolve_dns(int parc, char *parv[])
|
||||||
|
{
|
||||||
|
char *id = rb_strdup(parv[1]);
|
||||||
|
char qtype = *parv[2];
|
||||||
|
char *record = parv[3];
|
||||||
|
int aftype = AF_INET;
|
||||||
|
|
||||||
|
switch(qtype)
|
||||||
{
|
{
|
||||||
case '4':
|
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
case '6':
|
case '6':
|
||||||
format_address(&reply->addr, response, sizeof(response));
|
aftype = AF_INET6;
|
||||||
break;
|
|
||||||
#endif
|
#endif
|
||||||
|
case '4':
|
||||||
|
if(!lookup_ip(record, aftype, submit_dns_answer, id))
|
||||||
|
submit_dns_answer(NULL, false, qtype, NULL);
|
||||||
|
break;
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
case 'S':
|
case 'S':
|
||||||
family = AF_INET6;
|
|
||||||
#endif
|
#endif
|
||||||
case 'R':
|
case 'R':
|
||||||
if(sockcmp(&req->addr, &reply->addr, family) && strlen(reply->h_name) < 63)
|
if(!lookup_hostname(record, submit_dns_answer, id))
|
||||||
{
|
submit_dns_answer(NULL, false, qtype, NULL);
|
||||||
rb_strlcpy(response, reply->h_name, sizeof(response));
|
|
||||||
status = 'O';
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
exit(7);
|
exit(7);
|
||||||
}
|
}
|
||||||
|
|
||||||
rb_helper_write(authd_helper, "E %s %c %c %s", req->reqid, status, req->type, response);
|
|
||||||
cleanup:
|
|
||||||
rb_free(req);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
resolve_dns(int parc, char *parv[])
|
|
||||||
{
|
|
||||||
struct dns_request *req;
|
|
||||||
char *requestid = parv[1];
|
|
||||||
char *qtype = parv[2];
|
|
||||||
char *rec = parv[3];
|
|
||||||
int type;
|
|
||||||
|
|
||||||
req = rb_malloc(sizeof(*req));
|
|
||||||
rb_strlcpy(req->reqid, requestid, sizeof(req->reqid));
|
|
||||||
req->type = *qtype;
|
|
||||||
|
|
||||||
switch (req->type)
|
|
||||||
{
|
|
||||||
case '4':
|
|
||||||
type = T_A;
|
|
||||||
break;
|
|
||||||
case '6':
|
|
||||||
type = T_AAAA;
|
|
||||||
break;
|
|
||||||
case 'R':
|
|
||||||
case 'S':
|
|
||||||
if(!rb_inet_pton_sock(rec, (struct sockaddr *) &req->addr))
|
|
||||||
exit(6);
|
|
||||||
type = T_PTR;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
req->query.ptr = req;
|
|
||||||
req->query.callback = submit_dns_answer;
|
|
||||||
|
|
||||||
if (type != T_PTR)
|
|
||||||
gethost_byname_type(rec, &req->query, type);
|
|
||||||
else
|
|
||||||
gethost_byaddr(&req->addr, &req->query);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
enumerate_nameservers(const char *rid, const char letter)
|
enumerate_nameservers(const char *rid, const char letter)
|
||||||
{
|
{
|
||||||
char buf[40 * IRCD_MAXNS]; /* Plenty */
|
char buf[(HOSTIPLEN + 1) * IRCD_MAXNS];
|
||||||
char *c = buf;
|
char *c = buf;
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
|
@ -168,8 +266,7 @@ enumerate_nameservers(const char *rid, const char letter)
|
||||||
|
|
||||||
for(i = 0; i < irc_nscount; i++)
|
for(i = 0; i < irc_nscount; i++)
|
||||||
{
|
{
|
||||||
char addr[40];
|
char addr[HOSTIPLEN];
|
||||||
int ret;
|
|
||||||
|
|
||||||
rb_inet_ntop_sock((struct sockaddr *)&irc_nsaddr_list[i], addr, sizeof(addr));
|
rb_inet_ntop_sock((struct sockaddr *)&irc_nsaddr_list[i], addr, sizeof(addr));
|
||||||
|
|
||||||
|
@ -180,8 +277,8 @@ enumerate_nameservers(const char *rid, const char letter)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
ret = snprintf(c, 40, "%s ", addr);
|
(void)snprintf(c, HOSTIPLEN + 1, "%s ", addr);
|
||||||
c += (size_t)ret;
|
c += strlen(addr) + 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
*(--c) = '\0';
|
*(--c) = '\0';
|
||||||
|
|
29
authd/dns.h
29
authd/dns.h
|
@ -27,17 +27,34 @@
|
||||||
#include "res.h"
|
#include "res.h"
|
||||||
#include "reslib.h"
|
#include "reslib.h"
|
||||||
|
|
||||||
struct dns_request
|
typedef enum
|
||||||
|
{
|
||||||
|
QUERY_INVALID = 0,
|
||||||
|
QUERY_A = '4',
|
||||||
|
QUERY_AAAA = '6',
|
||||||
|
QUERY_PTR_A = 'R',
|
||||||
|
QUERY_PTR_AAAA = 'S',
|
||||||
|
} query_type;
|
||||||
|
|
||||||
|
/* Similar to that in ircd */
|
||||||
|
typedef void (*DNSCB)(const char *res, bool status, query_type type, void *data);
|
||||||
|
|
||||||
|
struct dns_query
|
||||||
{
|
{
|
||||||
struct DNSQuery query;
|
struct DNSQuery query;
|
||||||
char reqid[DNS_REQ_IDLEN];
|
query_type type;
|
||||||
struct rb_sockaddr_storage addr;
|
struct rb_sockaddr_storage addr;
|
||||||
char type;
|
uint64_t id;
|
||||||
|
|
||||||
|
DNSCB callback;
|
||||||
|
void *data;
|
||||||
};
|
};
|
||||||
|
|
||||||
extern void format_address(struct rb_sockaddr_storage *addr, char *buffer, size_t length);
|
extern struct dns_query *lookup_hostname(const char *ip, DNSCB callback, void *data);
|
||||||
extern bool sockcmp(struct rb_sockaddr_storage *addr, struct rb_sockaddr_storage *addr2, int family);
|
extern struct dns_query *lookup_ip(const char *host, int aftype, DNSCB callback, void *data);
|
||||||
extern void resolve_dns(int parc, char *parv[]);
|
extern void cancel_query(struct dns_query *query);
|
||||||
|
|
||||||
|
extern void handle_resolve_dns(int parc, char *parv[]);
|
||||||
extern void enumerate_nameservers(const char *rid, const char letter);
|
extern void enumerate_nameservers(const char *rid, const char letter);
|
||||||
extern void reload_nameservers(const char letter);
|
extern void reload_nameservers(const char letter);
|
||||||
|
|
||||||
|
|
617
authd/getaddrinfo.c
Normal file
617
authd/getaddrinfo.c
Normal file
|
@ -0,0 +1,617 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
#include <rb_lib.h>
|
||||||
|
#include "getaddrinfo.h"
|
||||||
|
#include "stdinc.h"
|
||||||
|
|
||||||
|
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)
|
||||||
|
};
|
||||||
|
|
||||||
|
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 bool str_isnumber(const char *);
|
||||||
|
static int explore_null(const struct rb_addrinfo *,
|
||||||
|
const char *, struct rb_addrinfo **);
|
||||||
|
static int explore_numeric(const struct rb_addrinfo *, const char *,
|
||||||
|
const char *, struct rb_addrinfo **);
|
||||||
|
static struct rb_addrinfo *get_ai(const struct rb_addrinfo *,
|
||||||
|
const struct afd *, const char *);
|
||||||
|
static int get_portmatch(const struct rb_addrinfo *, const char *);
|
||||||
|
static int get_port(struct rb_addrinfo *, const char *, int);
|
||||||
|
static const struct afd *find_afd(int);
|
||||||
|
#if 0
|
||||||
|
/* We will need this should we ever want gai_strerror() */
|
||||||
|
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 *
|
||||||
|
gai_strerror(int ecode)
|
||||||
|
{
|
||||||
|
if (ecode < 0 || ecode > EAI_MAX)
|
||||||
|
ecode = EAI_MAX;
|
||||||
|
return ai_errlist[ecode];
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
void
|
||||||
|
rb_freeaddrinfo(struct rb_addrinfo *ai)
|
||||||
|
{
|
||||||
|
struct rb_addrinfo *next;
|
||||||
|
|
||||||
|
do {
|
||||||
|
next = ai->ai_next;
|
||||||
|
if (ai->ai_canonname)
|
||||||
|
rb_free(ai->ai_canonname);
|
||||||
|
/* no need to free(ai->ai_addr) */
|
||||||
|
rb_free(ai);
|
||||||
|
ai = next;
|
||||||
|
} while (ai);
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool
|
||||||
|
str_isnumber(const char *p)
|
||||||
|
{
|
||||||
|
char *ep;
|
||||||
|
|
||||||
|
if (*p == '\0')
|
||||||
|
return false;
|
||||||
|
|
||||||
|
ep = NULL;
|
||||||
|
errno = 0;
|
||||||
|
(void)strtoul(p, &ep, 10);
|
||||||
|
if (errno == 0 && ep && *ep == '\0')
|
||||||
|
return true;
|
||||||
|
else
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
rb_getaddrinfo(const char *hostname, const char *servname,
|
||||||
|
const struct rb_addrinfo *hints, struct rb_addrinfo **res)
|
||||||
|
{
|
||||||
|
struct rb_addrinfo sentinel;
|
||||||
|
struct rb_addrinfo *cur;
|
||||||
|
int error = 0;
|
||||||
|
struct rb_addrinfo ai;
|
||||||
|
struct rb_addrinfo ai0;
|
||||||
|
struct rb_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)
|
||||||
|
ERR(EAI_BADHINTS); /* xxx */
|
||||||
|
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) {
|
||||||
|
ERR(EAI_BADHINTS);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* 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 numreic 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 SUCCESS;
|
||||||
|
} else
|
||||||
|
error = EAI_FAIL;
|
||||||
|
}
|
||||||
|
free:
|
||||||
|
bad:
|
||||||
|
if (sentinel.ai_next)
|
||||||
|
rb_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 rb_addrinfo *pai, const char *servname, struct rb_addrinfo **res)
|
||||||
|
{
|
||||||
|
int s;
|
||||||
|
const struct afd *afd;
|
||||||
|
struct rb_addrinfo *cur;
|
||||||
|
struct rb_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) {
|
||||||
|
#ifdef _WIN32
|
||||||
|
errno = WSAGetLastError();
|
||||||
|
#endif
|
||||||
|
if (errno != EMFILE)
|
||||||
|
return 0;
|
||||||
|
} else
|
||||||
|
#ifdef _WIN32
|
||||||
|
closesocket(s);
|
||||||
|
#else
|
||||||
|
close(s);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/*
|
||||||
|
* 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)
|
||||||
|
rb_freeaddrinfo(sentinel.ai_next);
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* numeric hostname
|
||||||
|
*/
|
||||||
|
static int
|
||||||
|
explore_numeric(const struct rb_addrinfo *pai, const char *hostname,
|
||||||
|
const char *servname, struct rb_addrinfo **res)
|
||||||
|
{
|
||||||
|
const struct afd *afd;
|
||||||
|
struct rb_addrinfo *cur;
|
||||||
|
struct rb_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 0 /*X/Open spec*/
|
||||||
|
case AF_INET:
|
||||||
|
if (rb_inet_pton
|
||||||
|
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 (rb_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)
|
||||||
|
rb_freeaddrinfo(sentinel.ai_next);
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct rb_addrinfo *
|
||||||
|
get_ai(const struct rb_addrinfo *pai, const struct afd *afd, const char *addr)
|
||||||
|
{
|
||||||
|
char *p;
|
||||||
|
struct rb_addrinfo *ai;
|
||||||
|
|
||||||
|
ai = (struct rb_addrinfo *)rb_malloc(sizeof(struct rb_addrinfo)
|
||||||
|
+ (afd->a_socklen));
|
||||||
|
if (ai == NULL)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
memcpy(ai, pai, sizeof(struct rb_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 rb_addrinfo *ai, const char *servname)
|
||||||
|
{
|
||||||
|
struct rb_addrinfo xai;
|
||||||
|
memcpy(&xai, ai, sizeof(struct rb_addrinfo));
|
||||||
|
return(get_port(&xai, servname, 1));
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
get_port(struct rb_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);
|
||||||
|
}
|
||||||
|
#endif
|
127
authd/getaddrinfo.h
Normal file
127
authd/getaddrinfo.h
Normal file
|
@ -0,0 +1,127 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
struct rb_addrinfo {
|
||||||
|
int ai_flags;
|
||||||
|
int ai_family;
|
||||||
|
int ai_socktype;
|
||||||
|
int ai_protocol;
|
||||||
|
size_t ai_addrlen;
|
||||||
|
char *ai_canonname;
|
||||||
|
struct sockaddr *ai_addr;
|
||||||
|
struct rb_addrinfo *ai_next;
|
||||||
|
};
|
||||||
|
|
||||||
|
#ifndef AI_PASSIVE
|
||||||
|
#define AI_PASSIVE 0x00000001 /* get address to use bind() */
|
||||||
|
#endif /* AI_PASSIVE */
|
||||||
|
|
||||||
|
#ifndef AI_NUMERICHOST
|
||||||
|
#define AI_NUMERICHOST 0x00000004 /* prevent name resolution */
|
||||||
|
#endif /* AI_NUMERICHOST */
|
||||||
|
|
||||||
|
#ifndef EAI_FAIL
|
||||||
|
#define EAI_FAIL 4 /* non-recoverable failure in name resolution */
|
||||||
|
#endif /* EAI_FAIL */
|
||||||
|
|
||||||
|
#ifndef EAI_FAMILY
|
||||||
|
#define EAI_FAMILY 5 /* ai_family not supported */
|
||||||
|
#endif /* EAI_FAMILY */
|
||||||
|
|
||||||
|
#ifndef EAI_MEMORY
|
||||||
|
#define EAI_MEMORY 6 /* memory allocation failure */
|
||||||
|
#endif /* EAI_MEMORY */
|
||||||
|
|
||||||
|
#ifndef EAI_NONAME
|
||||||
|
#define EAI_NONAME 8 /* hostname nor servname provided, or not known */
|
||||||
|
#endif /* EAI_NONAME */
|
||||||
|
|
||||||
|
#ifndef EAI_SYSTEM
|
||||||
|
#define EAI_SYSTEM 11 /* system error returned in errno */
|
||||||
|
#endif /* EAI_SYSTEM */
|
||||||
|
|
||||||
|
#ifndef NI_NUMERICHOST
|
||||||
|
#define NI_NUMERICHOST 0x00000002
|
||||||
|
#endif /* NI_NUMERICHOST */
|
||||||
|
|
||||||
|
#ifndef NI_NAMEREQD
|
||||||
|
#define NI_NAMEREQD 0x00000004
|
||||||
|
#endif /* NI_NAMEREQD */
|
||||||
|
|
||||||
|
#ifndef NI_NUMERICSERV
|
||||||
|
#define NI_NUMERICSERV 0x00000008
|
||||||
|
#endif /* NI_NUMERICSERV */
|
||||||
|
|
||||||
|
#ifndef NI_DGRAM
|
||||||
|
#define NI_DGRAM 0x00000010
|
||||||
|
#endif /* NI_DGRAM */
|
||||||
|
|
||||||
|
#ifndef INADDR_NONE
|
||||||
|
#define INADDR_NONE ((unsigned int) 0xffffffff)
|
||||||
|
#endif /* INADDR_NONE */
|
||||||
|
|
||||||
|
int rb_getaddrinfo(const char *hostname, const char *servname,
|
||||||
|
const struct rb_addrinfo *hints, struct rb_addrinfo **res);
|
||||||
|
void rb_freeaddrinfo(struct rb_addrinfo *ai);
|
||||||
|
|
||||||
|
#define SUCCESS 0
|
||||||
|
#define ANY 0
|
||||||
|
|
||||||
|
#undef EAI_ADDRFAMILY
|
||||||
|
#undef EAI_AGAIN
|
||||||
|
#undef EAI_BADFLAGS
|
||||||
|
#undef EAI_FAIL
|
||||||
|
#undef EAI_FAMILY
|
||||||
|
#undef EAI_MEMORY
|
||||||
|
#undef EAI_NODATA
|
||||||
|
#undef EAI_NONAME
|
||||||
|
#undef EAI_SERVICE
|
||||||
|
#undef EAI_SOCKTYPE
|
||||||
|
#undef EAI_SYSTEM
|
||||||
|
#undef EAI_BADHINTS
|
||||||
|
#undef EAI_PROTOCOL
|
||||||
|
#undef EAI_MAX
|
||||||
|
#undef AI_MASK
|
||||||
|
|
||||||
|
#define EAI_ADDRFAMILY 1 /* address family for hostname not supported */
|
||||||
|
#define EAI_AGAIN 2 /* temporary failure in name resolution */
|
||||||
|
#define EAI_BADFLAGS 3 /* invalid value for ai_flags */
|
||||||
|
#define EAI_FAIL 4 /* non-recoverable failure in name resolution */
|
||||||
|
#define EAI_FAMILY 5 /* ai_family not supported */
|
||||||
|
#define EAI_MEMORY 6 /* memory allocation failure */
|
||||||
|
#define EAI_NODATA 7 /* no address associated with hostname */
|
||||||
|
#define EAI_NONAME 8 /* hostname nor servname provided, or not known */
|
||||||
|
#define EAI_SERVICE 9 /* servname not supported for ai_socktype */
|
||||||
|
#define EAI_SOCKTYPE 10 /* ai_socktype not supported */
|
||||||
|
#define EAI_SYSTEM 11 /* system error returned in errno */
|
||||||
|
#define EAI_BADHINTS 12
|
||||||
|
#define EAI_PROTOCOL 13
|
||||||
|
#define EAI_MAX 14
|
||||||
|
#define AI_MASK (AI_PASSIVE | AI_NUMERICHOST)
|
240
authd/getnameinfo.c
Normal file
240
authd/getnameinfo.c
Normal file
|
@ -0,0 +1,240 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
#include <rb_lib.h>
|
||||||
|
#include "getaddrinfo.h"
|
||||||
|
#include "getnameinfo.h"
|
||||||
|
|
||||||
|
static const struct afd {
|
||||||
|
int a_af;
|
||||||
|
int a_addrlen;
|
||||||
|
rb_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
|
||||||
|
rb_getnameinfo(const struct sockaddr *sa, rb_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;
|
||||||
|
rb_strlcpy(serv, sp->s_name, servlen);
|
||||||
|
} else {
|
||||||
|
snprintf(numserv, sizeof(numserv), "%u", ntohs(port));
|
||||||
|
if (strlen(numserv) + 1 > servlen)
|
||||||
|
return EAI_MEMORY;
|
||||||
|
rb_strlcpy(serv, numserv, servlen);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (sa->sa_family) {
|
||||||
|
case AF_INET:
|
||||||
|
v4a = (uint32_t)
|
||||||
|
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 (rb_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;
|
||||||
|
rb_strlcpy(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 (rb_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';
|
||||||
|
rb_strlcpy(host+1, numaddr, hostlen-1);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
rb_strlcpy(host, numaddr, hostlen);
|
||||||
|
|
||||||
|
return(0);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
#endif
|
40
authd/getnameinfo.h
Normal file
40
authd/getnameinfo.h
Normal file
|
@ -0,0 +1,40 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
int rb_getnameinfo(const struct sockaddr *sa, rb_socklen_t salen, char *host,
|
||||||
|
size_t hostlen, char *serv, size_t servlen, int flags);
|
||||||
|
|
||||||
|
#ifndef IN_MULTICAST
|
||||||
|
#define IN_MULTICAST(a) ((((long int) (a)) & 0xf0000000) == 0xe0000000)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef IN_EXPERIMENTAL
|
||||||
|
#define IN_EXPERIMENTAL(a) ((((long int) (a)) & 0xe0000000) == 0xe0000000)
|
||||||
|
#endif
|
48
authd/notice.c
Normal file
48
authd/notice.c
Normal file
|
@ -0,0 +1,48 @@
|
||||||
|
/* authd/notice.c - send notices back to the ircd and to clients
|
||||||
|
* Copyright (c) 2016 Elizabeth Myers <elizabeth@interlinked.me>
|
||||||
|
*
|
||||||
|
* Permission to use, copy, modify, and/or distribute this software for any
|
||||||
|
* purpose with or without fee is hereby granted, provided that the above
|
||||||
|
* copyright notice and this permission notice is present in all copies.
|
||||||
|
*
|
||||||
|
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``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 AUTHOR 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 "authd.h"
|
||||||
|
#include "notice.h"
|
||||||
|
|
||||||
|
/* Send a notice to a client */
|
||||||
|
void notice_client(uint32_t cid, const char *fmt, ...)
|
||||||
|
{
|
||||||
|
char buf[BUFSIZE];
|
||||||
|
va_list args;
|
||||||
|
|
||||||
|
va_start(args, fmt);
|
||||||
|
vsnprintf(buf, sizeof(buf), fmt, args);
|
||||||
|
va_end(args);
|
||||||
|
|
||||||
|
rb_helper_write(authd_helper, "N %x :%s", cid, buf);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Send a warning to the IRC daemon for logging, etc. */
|
||||||
|
void warn_opers(notice_level_t level, const char *fmt, ...)
|
||||||
|
{
|
||||||
|
char buf[BUFSIZE];
|
||||||
|
va_list args;
|
||||||
|
|
||||||
|
va_start(args, fmt);
|
||||||
|
vsnprintf(buf, sizeof(buf), fmt, args);
|
||||||
|
va_end(args);
|
||||||
|
|
||||||
|
rb_helper_write(authd_helper, "W %c :%s", level, buf);
|
||||||
|
}
|
35
authd/notice.h
Normal file
35
authd/notice.h
Normal file
|
@ -0,0 +1,35 @@
|
||||||
|
/* authd/notice.h - send notices back to the ircd and to clients
|
||||||
|
* Copyright (c) 2016 Elizabeth Myers <elizabeth@interlinked.me>
|
||||||
|
*
|
||||||
|
* Permission to use, copy, modify, and/or distribute this software for any
|
||||||
|
* purpose with or without fee is hereby granted, provided that the above
|
||||||
|
* copyright notice and this permission notice is present in all copies.
|
||||||
|
*
|
||||||
|
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``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 AUTHOR 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __CHARYBDIS_AUTHD_NOTICE_H__
|
||||||
|
#define __CHARYBDIS_AUTHD_NOTICE_H__
|
||||||
|
|
||||||
|
typedef enum
|
||||||
|
{
|
||||||
|
L_DEBUG = 'D',
|
||||||
|
L_INFO = 'I',
|
||||||
|
L_WARN = 'W',
|
||||||
|
L_CRIT ='C',
|
||||||
|
} notice_level_t;
|
||||||
|
|
||||||
|
void notice_client(uint32_t cid, const char *fmt, ...);
|
||||||
|
void warn_opers(notice_level_t level, const char *fmt, ...);
|
||||||
|
|
||||||
|
#endif /* __CHARYBDIS_AUTHD_NOTICE_H__ */
|
209
authd/provider.c
209
authd/provider.c
|
@ -18,16 +18,17 @@
|
||||||
* POSSIBILITY OF SUCH DAMAGE.
|
* POSSIBILITY OF SUCH DAMAGE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* So the basic design here is to have "authentication providers" that do
|
/* The basic design here is to have "authentication providers" that do things
|
||||||
* things like query ident and blacklists and even open proxies.
|
* like query ident and blacklists and even open proxies.
|
||||||
*
|
*
|
||||||
* Providers are registered statically in the struct auth_providers array. You will
|
* Providers are registered in the auth_providers linked list. It is planned to
|
||||||
* probably want to add an item to the provider_t enum also.
|
* use a bitmap to store provider ID's later.
|
||||||
*
|
*
|
||||||
* Providers can either return failure immediately, immediate acceptance, or
|
* Providers can either return failure immediately, immediate acceptance, or do
|
||||||
* do work in the background (calling set_provider to signal this).
|
* work in the background (calling set_provider to signal this).
|
||||||
*
|
*
|
||||||
* It is up to providers to keep their own state on clients if they need to.
|
* Provider-specific data for each client can be kept in an index of the data
|
||||||
|
* struct member (using the provider's ID).
|
||||||
*
|
*
|
||||||
* All providers must implement at a minimum a perform_provider function. You
|
* All providers must implement at a minimum a perform_provider function. You
|
||||||
* don't have to implement the others if you don't need them.
|
* don't have to implement the others if you don't need them.
|
||||||
|
@ -39,53 +40,82 @@
|
||||||
* should call provider_done. Do NOT call this if you have accepted or rejected
|
* should call provider_done. Do NOT call this if you have accepted or rejected
|
||||||
* the client.
|
* the client.
|
||||||
*
|
*
|
||||||
|
* Eventually, stuff like *:line handling will be moved here, but that means we
|
||||||
|
* have to talk to bandb directly first.
|
||||||
|
*
|
||||||
* --Elizafox, 9 March 2016
|
* --Elizafox, 9 March 2016
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "rb_dictionary.h"
|
||||||
#include "authd.h"
|
#include "authd.h"
|
||||||
#include "provider.h"
|
#include "provider.h"
|
||||||
|
#include "notice.h"
|
||||||
|
|
||||||
rb_dlink_list auth_providers;
|
rb_dlink_list auth_providers;
|
||||||
|
|
||||||
/* Clients waiting */
|
/* Clients waiting */
|
||||||
struct auth_client auth_clients[MAX_CLIENTS];
|
rb_dictionary *auth_clients;
|
||||||
|
|
||||||
/* Load a provider */
|
/* Load a provider */
|
||||||
void load_provider(struct auth_provider *provider)
|
void
|
||||||
|
load_provider(struct auth_provider *provider)
|
||||||
{
|
{
|
||||||
|
if(rb_dlink_list_length(&auth_providers) >= MAX_PROVIDERS)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "Exceeded maximum level of authd providers (%d max)", MAX_PROVIDERS);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(provider->opt_handlers != NULL)
|
||||||
|
{
|
||||||
|
struct auth_opts_handler *handler;
|
||||||
|
|
||||||
|
for(handler = provider->opt_handlers; handler->option != NULL; handler++)
|
||||||
|
rb_dictionary_add(authd_option_handlers, handler->option, handler);
|
||||||
|
}
|
||||||
|
|
||||||
provider->init();
|
provider->init();
|
||||||
rb_dlinkAdd(provider, &provider->node, &auth_providers);
|
rb_dlinkAdd(provider, &provider->node, &auth_providers);
|
||||||
}
|
}
|
||||||
|
|
||||||
void unload_provider(struct auth_provider *provider)
|
void
|
||||||
|
unload_provider(struct auth_provider *provider)
|
||||||
{
|
{
|
||||||
|
if(provider->opt_handlers != NULL)
|
||||||
|
{
|
||||||
|
struct auth_opts_handler *handler;
|
||||||
|
|
||||||
|
for(handler = provider->opt_handlers; handler->option != NULL; handler++)
|
||||||
|
rb_dictionary_delete(authd_option_handlers, handler->option);
|
||||||
|
}
|
||||||
provider->destroy();
|
provider->destroy();
|
||||||
rb_dlinkDelete(&provider->node, &auth_providers);
|
rb_dlinkDelete(&provider->node, &auth_providers);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Initalise all providers */
|
/* Initalise all providers */
|
||||||
void init_providers(void)
|
void
|
||||||
|
init_providers(void)
|
||||||
{
|
{
|
||||||
|
auth_clients = rb_dictionary_create("pending auth clients", rb_uint32cmp);
|
||||||
load_provider(&rdns_provider);
|
load_provider(&rdns_provider);
|
||||||
load_provider(&ident_provider);
|
load_provider(&ident_provider);
|
||||||
|
load_provider(&blacklist_provider);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Terminate all providers */
|
/* Terminate all providers */
|
||||||
void destroy_providers(void)
|
void
|
||||||
|
destroy_providers(void)
|
||||||
{
|
{
|
||||||
rb_dlink_node *ptr;
|
rb_dlink_node *ptr;
|
||||||
|
rb_dictionary_iter iter;
|
||||||
|
struct auth_client *auth;
|
||||||
struct auth_provider *provider;
|
struct auth_provider *provider;
|
||||||
|
|
||||||
/* Cancel outstanding connections */
|
/* Cancel outstanding connections */
|
||||||
for (size_t i = 0; i < MAX_CLIENTS; i++)
|
RB_DICTIONARY_FOREACH(auth, &iter, auth_clients)
|
||||||
{
|
{
|
||||||
if(auth_clients[i].cid)
|
/* TBD - is this the right thing? */
|
||||||
{
|
reject_client(auth, 0, "Authentication system is down... try reconnecting in a few seconds");
|
||||||
/* TBD - is this the right thing?
|
|
||||||
* (NOTE - this error message is designed for morons) */
|
|
||||||
reject_client(&auth_clients[i], 0, true,
|
|
||||||
"IRC server reloading... try reconnecting in a few seconds");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
RB_DLINK_FOREACH(ptr, auth_providers.head)
|
RB_DLINK_FOREACH(ptr, auth_providers.head)
|
||||||
|
@ -98,7 +128,8 @@ void destroy_providers(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Cancel outstanding providers for a client */
|
/* Cancel outstanding providers for a client */
|
||||||
void cancel_providers(struct auth_client *auth)
|
void
|
||||||
|
cancel_providers(struct auth_client *auth)
|
||||||
{
|
{
|
||||||
rb_dlink_node *ptr;
|
rb_dlink_node *ptr;
|
||||||
struct auth_provider *provider;
|
struct auth_provider *provider;
|
||||||
|
@ -107,23 +138,29 @@ void cancel_providers(struct auth_client *auth)
|
||||||
{
|
{
|
||||||
provider = ptr->data;
|
provider = ptr->data;
|
||||||
|
|
||||||
if(provider->cancel && is_provider(auth, provider->id))
|
if(provider->cancel && is_provider_on(auth, provider->id))
|
||||||
/* Cancel if required */
|
/* Cancel if required */
|
||||||
provider->cancel(auth);
|
provider->cancel(auth);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
rb_dictionary_delete(auth_clients, RB_UINT_TO_POINTER(auth->cid));
|
||||||
|
rb_free(auth);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Provider is done */
|
/* Provider is done - WARNING: do not use auth instance after calling! */
|
||||||
void provider_done(struct auth_client *auth, provider_t id)
|
void
|
||||||
|
provider_done(struct auth_client *auth, provider_t id)
|
||||||
{
|
{
|
||||||
rb_dlink_node *ptr;
|
rb_dlink_node *ptr;
|
||||||
struct auth_provider *provider;
|
struct auth_provider *provider;
|
||||||
|
|
||||||
unset_provider(auth, id);
|
set_provider_off(auth, id);
|
||||||
|
set_provider_done(auth, id);
|
||||||
|
|
||||||
if(!auth->providers)
|
if(!auth->providers)
|
||||||
{
|
{
|
||||||
/* No more providers, done */
|
if(!auth->providers_starting)
|
||||||
|
/* Only do this when there are no providers left */
|
||||||
accept_client(auth, 0);
|
accept_client(auth, 0);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -132,16 +169,16 @@ void provider_done(struct auth_client *auth, provider_t id)
|
||||||
{
|
{
|
||||||
provider = ptr->data;
|
provider = ptr->data;
|
||||||
|
|
||||||
if(provider->completed && is_provider(auth, provider->id))
|
if(provider->completed && is_provider_on(auth, provider->id))
|
||||||
/* Notify pending clients who asked for it */
|
/* Notify pending clients who asked for it */
|
||||||
provider->completed(auth, id);
|
provider->completed(auth, id);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Reject a client, cancel outstanding providers if any if hard set to true */
|
/* Reject a client - WARNING: do not use auth instance after calling! */
|
||||||
void reject_client(struct auth_client *auth, provider_t id, bool hard, const char *reason)
|
void
|
||||||
|
reject_client(struct auth_client *auth, provider_t id, const char *reason)
|
||||||
{
|
{
|
||||||
uint16_t cid = auth->cid;
|
|
||||||
char reject;
|
char reject;
|
||||||
|
|
||||||
switch(id)
|
switch(id)
|
||||||
|
@ -155,83 +192,87 @@ void reject_client(struct auth_client *auth, provider_t id, bool hard, const cha
|
||||||
case PROVIDER_BLACKLIST:
|
case PROVIDER_BLACKLIST:
|
||||||
reject = 'B';
|
reject = 'B';
|
||||||
break;
|
break;
|
||||||
case PROVIDER_NULL:
|
|
||||||
default:
|
default:
|
||||||
reject = 'N';
|
reject = 'N';
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
rb_helper_write(authd_helper, "R %x %c :%s", auth->cid, reject, reason);
|
/* We send back username and hostname in case ircd wants to overrule our decision.
|
||||||
|
* In the future this may not be the case.
|
||||||
|
* --Elizafox
|
||||||
|
*/
|
||||||
|
rb_helper_write(authd_helper, "R %x %c %s %s :%s", auth->cid, reject, auth->username, auth->hostname, reason);
|
||||||
|
|
||||||
unset_provider(auth, id);
|
set_provider_off(auth, id);
|
||||||
|
|
||||||
if(hard && auth->providers)
|
|
||||||
{
|
|
||||||
cancel_providers(auth);
|
cancel_providers(auth);
|
||||||
memset(&auth_clients[cid], 0, sizeof(struct auth_client));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Accept a client, cancel outstanding providers if any */
|
/* Accept a client, cancel outstanding providers if any - WARNING: do nto use auth instance after calling! */
|
||||||
void accept_client(struct auth_client *auth, provider_t id)
|
void
|
||||||
|
accept_client(struct auth_client *auth, provider_t id)
|
||||||
{
|
{
|
||||||
uint16_t cid = auth->cid;
|
uint32_t cid = auth->cid;
|
||||||
|
|
||||||
rb_helper_write(authd_helper, "A %x %s %s", auth->cid, auth->username, auth->hostname);
|
rb_helper_write(authd_helper, "A %x %s %s", auth->cid, auth->username, auth->hostname);
|
||||||
|
|
||||||
unset_provider(auth, id);
|
set_provider_off(auth, id);
|
||||||
|
|
||||||
if(auth->providers)
|
|
||||||
cancel_providers(auth);
|
cancel_providers(auth);
|
||||||
|
|
||||||
memset(&auth_clients[cid], 0, sizeof(struct auth_client));
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Send a notice to a client */
|
|
||||||
void notice_client(struct auth_client *auth, const char *notice)
|
|
||||||
{
|
|
||||||
rb_helper_write(authd_helper, "N %x :%s", auth->cid, notice);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Begin authenticating user */
|
/* Begin authenticating user */
|
||||||
static void start_auth(const char *cid, const char *l_ip, const char *l_port, const char *c_ip, const char *c_port)
|
static void
|
||||||
|
start_auth(const char *cid, const char *l_ip, const char *l_port, const char *c_ip, const char *c_port)
|
||||||
{
|
{
|
||||||
rb_dlink_node *ptr;
|
|
||||||
struct auth_provider *provider;
|
struct auth_provider *provider;
|
||||||
struct auth_client *auth;
|
struct auth_client *auth = rb_malloc(sizeof(struct auth_client));
|
||||||
long lcid = strtol(cid, NULL, 16);
|
long lcid = strtol(cid, NULL, 16);
|
||||||
|
rb_dlink_node *ptr;
|
||||||
|
|
||||||
if(lcid >= MAX_CLIENTS)
|
if(lcid >= UINT32_MAX)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
auth = &auth_clients[lcid];
|
auth->cid = (uint32_t)lcid;
|
||||||
if(auth->cid != 0)
|
|
||||||
/* Shouldn't get here */
|
if(rb_dictionary_find(auth_clients, RB_UINT_TO_POINTER(auth->cid)) == NULL)
|
||||||
|
rb_dictionary_add(auth_clients, RB_UINT_TO_POINTER(auth->cid), auth);
|
||||||
|
else
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: duplicate client added via start_auth: %x", auth->cid);
|
||||||
|
rb_free(auth);
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
auth->cid = (uint16_t)lcid;
|
rb_strlcpy(auth->l_ip, l_ip, sizeof(auth->l_ip));
|
||||||
|
auth->l_port = (uint16_t)atoi(l_port); /* should be safe */
|
||||||
(void) rb_inet_pton_sock(l_ip, (struct sockaddr *)&auth->l_addr);
|
(void) rb_inet_pton_sock(l_ip, (struct sockaddr *)&auth->l_addr);
|
||||||
|
|
||||||
|
rb_strlcpy(auth->c_ip, c_ip, sizeof(auth->c_ip));
|
||||||
|
auth->c_port = (uint16_t)atoi(c_port);
|
||||||
|
(void) rb_inet_pton_sock(c_ip, (struct sockaddr *)&auth->c_addr);
|
||||||
|
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
if(GET_SS_FAMILY(&auth->l_addr) == AF_INET6)
|
if(GET_SS_FAMILY(&auth->l_addr) == AF_INET6)
|
||||||
((struct sockaddr_in6 *)&auth->l_addr)->sin6_port = htons(atoi(l_ip));
|
((struct sockaddr_in6 *)&auth->l_addr)->sin6_port = htons(auth->l_port);
|
||||||
else
|
else
|
||||||
#endif
|
#endif
|
||||||
((struct sockaddr_in *)&auth->l_addr)->sin_port = htons(atoi(l_ip));
|
((struct sockaddr_in *)&auth->l_addr)->sin_port = htons(auth->l_port);
|
||||||
|
|
||||||
(void)rb_inet_pton_sock(c_ip, (struct sockaddr *)&auth->c_addr);
|
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
if(GET_SS_FAMILY(&auth->c_addr) == AF_INET6)
|
if(GET_SS_FAMILY(&auth->c_addr) == AF_INET6)
|
||||||
((struct sockaddr_in6 *)&auth->c_addr)->sin6_port = htons(atoi(c_ip));
|
((struct sockaddr_in6 *)&auth->c_addr)->sin6_port = htons(auth->c_port);
|
||||||
else
|
else
|
||||||
#endif
|
#endif
|
||||||
((struct sockaddr_in *)&auth->c_addr)->sin_port = htons(atoi(c_ip));
|
((struct sockaddr_in *)&auth->c_addr)->sin_port = htons(auth->c_port);
|
||||||
|
|
||||||
|
memset(auth->data, 0, sizeof(auth->data));
|
||||||
|
|
||||||
|
auth->providers_starting = true;
|
||||||
RB_DLINK_FOREACH(ptr, auth_providers.head)
|
RB_DLINK_FOREACH(ptr, auth_providers.head)
|
||||||
{
|
{
|
||||||
provider = ptr->data;
|
provider = ptr->data;
|
||||||
|
|
||||||
|
lrb_assert(provider->start != NULL);
|
||||||
|
|
||||||
/* Execute providers */
|
/* Execute providers */
|
||||||
if(!provider->start(auth))
|
if(!provider->start(auth))
|
||||||
{
|
{
|
||||||
|
@ -240,6 +281,7 @@ static void start_auth(const char *cid, const char *l_ip, const char *l_port, co
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
auth->providers_starting = false;
|
||||||
|
|
||||||
/* If no providers are running, accept the client */
|
/* If no providers are running, accept the client */
|
||||||
if(!auth->providers)
|
if(!auth->providers)
|
||||||
|
@ -247,10 +289,41 @@ static void start_auth(const char *cid, const char *l_ip, const char *l_port, co
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Callback for the initiation */
|
/* Callback for the initiation */
|
||||||
void handle_new_connection(int parc, char *parv[])
|
void
|
||||||
|
handle_new_connection(int parc, char *parv[])
|
||||||
{
|
{
|
||||||
if(parc < 7)
|
if(parc < 6)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: received too few params for new connection (6 expected, got %d)", parc);
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
start_auth(parv[1], parv[2], parv[3], parv[4], parv[5]);
|
start_auth(parv[1], parv[2], parv[3], parv[4], parv[5]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
handle_cancel_connection(int parc, char *parv[])
|
||||||
|
{
|
||||||
|
struct auth_client *auth;
|
||||||
|
long lcid;
|
||||||
|
|
||||||
|
if(parc < 2)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: received too few params for new connection (2 expected, got %d)", parc);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if((lcid = strtol(parv[1], NULL, 16)) > UINT32_MAX)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: got a request to cancel a connection that can't exist: %lx", lcid);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if((auth = rb_dictionary_retrieve(auth_clients, RB_UINT_TO_POINTER((uint32_t)lcid))) == NULL)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: tried to cancel nonexistent connection %lx", lcid);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
cancel_providers(auth);
|
||||||
|
}
|
||||||
|
|
|
@ -22,39 +22,49 @@
|
||||||
#define __CHARYBDIS_AUTHD_PROVIDER_H__
|
#define __CHARYBDIS_AUTHD_PROVIDER_H__
|
||||||
|
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
|
#include "authd.h"
|
||||||
|
#include "rb_dictionary.h"
|
||||||
|
|
||||||
/* Arbitrary limit */
|
#define MAX_PROVIDERS 32 /* This should be enough */
|
||||||
#define MAX_CLIENTS 4096
|
|
||||||
|
|
||||||
/* Registered providers */
|
/* Registered providers */
|
||||||
typedef enum
|
typedef enum
|
||||||
{
|
{
|
||||||
PROVIDER_NULL = 0x0, /* Dummy value */
|
PROVIDER_RDNS,
|
||||||
PROVIDER_RDNS = 0x1,
|
PROVIDER_IDENT,
|
||||||
PROVIDER_IDENT = 0x2,
|
PROVIDER_BLACKLIST,
|
||||||
PROVIDER_BLACKLIST = 0x4,
|
|
||||||
} provider_t;
|
} provider_t;
|
||||||
|
|
||||||
struct auth_client
|
struct auth_client
|
||||||
{
|
{
|
||||||
uint16_t cid; /* Client ID */
|
uint16_t cid; /* Client ID */
|
||||||
|
|
||||||
struct rb_sockaddr_storage l_addr; /* Listener IP address */
|
char l_ip[HOSTIPLEN + 1]; /* Listener IP address */
|
||||||
struct rb_sockaddr_storage c_addr; /* Client IP address */
|
uint16_t l_port; /* Listener port */
|
||||||
|
struct rb_sockaddr_storage l_addr; /* Listener address/port */
|
||||||
|
|
||||||
|
char c_ip[HOSTIPLEN + 1]; /* Client IP address */
|
||||||
|
uint16_t c_port; /* Client port */
|
||||||
|
struct rb_sockaddr_storage c_addr; /* Client address/port */
|
||||||
|
|
||||||
char hostname[HOSTLEN + 1]; /* Used for DNS lookup */
|
char hostname[HOSTLEN + 1]; /* Used for DNS lookup */
|
||||||
char username[USERLEN + 1]; /* Used for ident lookup */
|
char username[USERLEN + 1]; /* Used for ident lookup */
|
||||||
|
|
||||||
unsigned int providers; /* Providers at work,
|
uint32_t providers; /* Providers at work,
|
||||||
* none left when set to 0 */
|
* none left when set to 0 */
|
||||||
|
uint32_t providers_done; /* Providers completed */
|
||||||
|
bool providers_starting; /* Providers are still warming up */
|
||||||
|
|
||||||
|
void *data[MAX_PROVIDERS]; /* Provider-specific data slots */
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef bool (*provider_init_t)(void);
|
typedef bool (*provider_init_t)(void);
|
||||||
typedef bool (*provider_perform_t)(struct auth_client *);
|
|
||||||
typedef void (*provider_complete_t)(struct auth_client *, provider_t provider);
|
|
||||||
typedef void (*provider_cancel_t)(struct auth_client *);
|
|
||||||
typedef void (*provider_destroy_t)(void);
|
typedef void (*provider_destroy_t)(void);
|
||||||
|
|
||||||
|
typedef bool (*provider_start_t)(struct auth_client *);
|
||||||
|
typedef void (*provider_cancel_t)(struct auth_client *);
|
||||||
|
typedef void (*provider_complete_t)(struct auth_client *, provider_t);
|
||||||
|
|
||||||
struct auth_provider
|
struct auth_provider
|
||||||
{
|
{
|
||||||
rb_dlink_node node;
|
rb_dlink_node node;
|
||||||
|
@ -64,16 +74,19 @@ struct auth_provider
|
||||||
provider_init_t init; /* Initalise the provider */
|
provider_init_t init; /* Initalise the provider */
|
||||||
provider_destroy_t destroy; /* Terminate the provider */
|
provider_destroy_t destroy; /* Terminate the provider */
|
||||||
|
|
||||||
provider_perform_t start; /* Perform authentication */
|
provider_start_t start; /* Perform authentication */
|
||||||
provider_cancel_t cancel; /* Authentication cancelled */
|
provider_cancel_t cancel; /* Authentication cancelled */
|
||||||
provider_complete_t completed; /* Callback for when other performers complete (think dependency chains) */
|
provider_complete_t completed; /* Callback for when other performers complete (think dependency chains) */
|
||||||
|
|
||||||
|
struct auth_opts_handler *opt_handlers;
|
||||||
};
|
};
|
||||||
|
|
||||||
extern rb_dlink_list auth_providers;
|
extern rb_dlink_list auth_providers;
|
||||||
|
extern rb_dictionary *auth_clients;
|
||||||
|
|
||||||
extern struct auth_provider rdns_provider;
|
extern struct auth_provider rdns_provider;
|
||||||
extern struct auth_provider ident_provider;
|
extern struct auth_provider ident_provider;
|
||||||
|
extern struct auth_provider blacklist_provider;
|
||||||
extern struct auth_client auth_clients[MAX_CLIENTS];
|
|
||||||
|
|
||||||
void load_provider(struct auth_provider *provider);
|
void load_provider(struct auth_provider *provider);
|
||||||
void unload_provider(struct auth_provider *provider);
|
void unload_provider(struct auth_provider *provider);
|
||||||
|
@ -84,28 +97,43 @@ void cancel_providers(struct auth_client *auth);
|
||||||
|
|
||||||
void provider_done(struct auth_client *auth, provider_t id);
|
void provider_done(struct auth_client *auth, provider_t id);
|
||||||
void accept_client(struct auth_client *auth, provider_t id);
|
void accept_client(struct auth_client *auth, provider_t id);
|
||||||
void reject_client(struct auth_client *auth, provider_t id, bool hard, const char *reason);
|
void reject_client(struct auth_client *auth, provider_t id, const char *reason);
|
||||||
|
|
||||||
void notice_client(struct auth_client *auth, const char *notice);
|
|
||||||
|
|
||||||
void handle_new_connection(int parc, char *parv[]);
|
void handle_new_connection(int parc, char *parv[]);
|
||||||
|
void handle_cancel_connection(int parc, char *parv[]);
|
||||||
|
|
||||||
/* Provider is operating on this auth_client (set this if you have async work to do) */
|
/* Provider is operating on this auth_client (set this if you have async work to do) */
|
||||||
static inline void set_provider(struct auth_client *auth, provider_t provider)
|
static inline void
|
||||||
|
set_provider_on(struct auth_client *auth, provider_t provider)
|
||||||
{
|
{
|
||||||
auth->providers |= provider;
|
auth->providers |= (1 << provider);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Provider is no longer operating on this auth client (you should use provider_done) */
|
/* Provider is no longer operating on this auth client (you should use provider_done) */
|
||||||
static inline void unset_provider(struct auth_client *auth, provider_t provider)
|
static inline void
|
||||||
|
set_provider_off(struct auth_client *auth, provider_t provider)
|
||||||
{
|
{
|
||||||
auth->providers &= ~provider;
|
auth->providers &= ~(1 << provider);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Set the provider to done (you should use provider_done) */
|
||||||
|
static inline void
|
||||||
|
set_provider_done(struct auth_client *auth, provider_t provider)
|
||||||
|
{
|
||||||
|
auth->providers_done |= (1 << provider);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Check if provider is operating on this auth client */
|
/* Check if provider is operating on this auth client */
|
||||||
static inline bool is_provider(struct auth_client *auth, provider_t provider)
|
static inline bool
|
||||||
|
is_provider_on(struct auth_client *auth, provider_t provider)
|
||||||
{
|
{
|
||||||
return auth->providers & provider;
|
return auth->providers & (1 << provider);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline bool
|
||||||
|
is_provider_done(struct auth_client *auth, provider_t provider)
|
||||||
|
{
|
||||||
|
return auth->providers_done & (1 << provider);
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif /* __CHARYBDIS_AUTHD_PROVIDER_H__ */
|
#endif /* __CHARYBDIS_AUTHD_PROVIDER_H__ */
|
||||||
|
|
565
authd/providers/blacklist.c
Normal file
565
authd/providers/blacklist.c
Normal file
|
@ -0,0 +1,565 @@
|
||||||
|
/*
|
||||||
|
* charybdis: A slightly useful ircd.
|
||||||
|
* blacklist.c: Manages DNS blacklist entries and lookups
|
||||||
|
*
|
||||||
|
* Copyright (C) 2006-2011 charybdis development team
|
||||||
|
*
|
||||||
|
* 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. The name of the author may not be used to endorse or promote products
|
||||||
|
* derived from this software without specific prior written permission.
|
||||||
|
*
|
||||||
|
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``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 AUTHOR 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Originally written for charybdis circa 2006 (by nenolod?).
|
||||||
|
* Tweaked for authd. Some functions and structs renamed. Public/private
|
||||||
|
* interfaces have been shifted around. Some code has been cleaned up too.
|
||||||
|
* -- Elizafox 24 March 2016
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "authd.h"
|
||||||
|
#include "provider.h"
|
||||||
|
#include "notice.h"
|
||||||
|
#include "stdinc.h"
|
||||||
|
#include "dns.h"
|
||||||
|
|
||||||
|
typedef enum filter_t
|
||||||
|
{
|
||||||
|
FILTER_ALL = 1,
|
||||||
|
FILTER_LAST = 2,
|
||||||
|
} filter_t;
|
||||||
|
|
||||||
|
/* Blacklist accepted IP types */
|
||||||
|
#define IPTYPE_IPV4 1
|
||||||
|
#define IPTYPE_IPV6 2
|
||||||
|
|
||||||
|
/* A configured DNSBL */
|
||||||
|
struct blacklist
|
||||||
|
{
|
||||||
|
char host[IRCD_RES_HOSTLEN + 1];
|
||||||
|
char reason[BUFSIZE]; /* Reason template (ircd fills in the blanks) */
|
||||||
|
unsigned char iptype; /* IP types supported */
|
||||||
|
rb_dlink_list filters; /* Filters for queries */
|
||||||
|
|
||||||
|
bool delete; /* If true delete when no clients */
|
||||||
|
int refcount; /* When 0 and delete is set, remove this blacklist */
|
||||||
|
|
||||||
|
time_t lastwarning; /* Last warning about garbage replies sent */
|
||||||
|
};
|
||||||
|
|
||||||
|
/* A lookup in progress for a particular DNSBL for a particular client */
|
||||||
|
struct blacklist_lookup
|
||||||
|
{
|
||||||
|
struct blacklist *bl; /* Blacklist we're checking */
|
||||||
|
struct auth_client *auth; /* Client */
|
||||||
|
struct dns_query *query; /* DNS query pointer */
|
||||||
|
|
||||||
|
rb_dlink_node node;
|
||||||
|
};
|
||||||
|
|
||||||
|
/* A blacklist filter */
|
||||||
|
struct blacklist_filter
|
||||||
|
{
|
||||||
|
filter_t type; /* Type of filter */
|
||||||
|
char filter[HOSTIPLEN]; /* The filter itself */
|
||||||
|
|
||||||
|
rb_dlink_node node;
|
||||||
|
};
|
||||||
|
|
||||||
|
/* Blacklist user data attached to auth_client instance */
|
||||||
|
struct blacklist_user
|
||||||
|
{
|
||||||
|
rb_dlink_list queries; /* Blacklist queries in flight */
|
||||||
|
time_t timeout; /* When this times out */
|
||||||
|
};
|
||||||
|
|
||||||
|
/* public interfaces */
|
||||||
|
static bool blacklists_init(void);
|
||||||
|
static void blacklists_destroy(void);
|
||||||
|
|
||||||
|
static bool blacklists_start(struct auth_client *);
|
||||||
|
static void blacklists_cancel(struct auth_client *);
|
||||||
|
|
||||||
|
/* private interfaces */
|
||||||
|
static void unref_blacklist(struct blacklist *);
|
||||||
|
static struct blacklist *new_blacklist(const char *, const char *, unsigned char, rb_dlink_list *);
|
||||||
|
static struct blacklist *find_blacklist(const char *);
|
||||||
|
static bool blacklist_check_reply(struct blacklist_lookup *, const char *);
|
||||||
|
static void blacklist_dns_callback(const char *, bool, query_type, void *);
|
||||||
|
static void initiate_blacklist_dnsquery(struct blacklist *, struct auth_client *);
|
||||||
|
static void timeout_blacklist_queries_event(void *);
|
||||||
|
|
||||||
|
/* Variables */
|
||||||
|
static rb_dlink_list blacklist_list = { NULL, NULL, 0 };
|
||||||
|
static struct ev_entry *timeout_ev;
|
||||||
|
static int blacklist_timeout = 15;
|
||||||
|
|
||||||
|
/* private interfaces */
|
||||||
|
|
||||||
|
static void
|
||||||
|
unref_blacklist(struct blacklist *bl)
|
||||||
|
{
|
||||||
|
rb_dlink_node *ptr, *nptr;
|
||||||
|
|
||||||
|
bl->refcount--;
|
||||||
|
if (bl->delete && bl->refcount <= 0)
|
||||||
|
{
|
||||||
|
RB_DLINK_FOREACH_SAFE(ptr, nptr, bl->filters.head)
|
||||||
|
{
|
||||||
|
rb_dlinkDelete(ptr, &bl->filters);
|
||||||
|
rb_free(ptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
rb_dlinkFindDestroy(bl, &blacklist_list);
|
||||||
|
rb_free(bl);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct blacklist *
|
||||||
|
new_blacklist(const char *name, const char *reason, unsigned char iptype, rb_dlink_list *filters)
|
||||||
|
{
|
||||||
|
struct blacklist *bl;
|
||||||
|
|
||||||
|
if (name == NULL || reason == NULL || iptype == 0)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
if((bl = find_blacklist(name)) == NULL)
|
||||||
|
{
|
||||||
|
bl = rb_malloc(sizeof(struct blacklist));
|
||||||
|
rb_dlinkAddAlloc(bl, &blacklist_list);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
bl->delete = false;
|
||||||
|
|
||||||
|
rb_strlcpy(bl->host, name, IRCD_RES_HOSTLEN + 1);
|
||||||
|
rb_strlcpy(bl->reason, reason, BUFSIZE);
|
||||||
|
bl->iptype = iptype;
|
||||||
|
|
||||||
|
rb_dlinkMoveList(filters, &bl->filters);
|
||||||
|
|
||||||
|
bl->lastwarning = 0;
|
||||||
|
|
||||||
|
return bl;
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct blacklist *
|
||||||
|
find_blacklist(const char *name)
|
||||||
|
{
|
||||||
|
rb_dlink_node *ptr;
|
||||||
|
|
||||||
|
RB_DLINK_FOREACH(ptr, blacklist_list.head)
|
||||||
|
{
|
||||||
|
struct blacklist *bl = (struct blacklist *)ptr->data;
|
||||||
|
|
||||||
|
if (!strcasecmp(bl->host, name))
|
||||||
|
return bl;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline bool
|
||||||
|
blacklist_check_reply(struct blacklist_lookup *bllookup, const char *ipaddr)
|
||||||
|
{
|
||||||
|
struct blacklist *bl = bllookup->bl;
|
||||||
|
const char *lastoctet;
|
||||||
|
rb_dlink_node *ptr;
|
||||||
|
|
||||||
|
/* No filters and entry found - thus positive match */
|
||||||
|
if (!rb_dlink_list_length(&bl->filters))
|
||||||
|
return true;
|
||||||
|
|
||||||
|
/* Below will prolly have to change if IPv6 address replies are sent back */
|
||||||
|
if ((lastoctet = strrchr(ipaddr, '.')) == NULL || *(++lastoctet) == '\0')
|
||||||
|
goto blwarn;
|
||||||
|
|
||||||
|
RB_DLINK_FOREACH(ptr, bl->filters.head)
|
||||||
|
{
|
||||||
|
struct blacklist_filter *filter = ptr->data;
|
||||||
|
const char *cmpstr;
|
||||||
|
|
||||||
|
if (filter->type == FILTER_ALL)
|
||||||
|
cmpstr = ipaddr;
|
||||||
|
else if (filter->type == FILTER_LAST)
|
||||||
|
cmpstr = lastoctet;
|
||||||
|
else
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: Unknown blacklist filter type on blacklist %s: %d",
|
||||||
|
bl->host, filter->type);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (strcmp(cmpstr, filter->filter) == 0)
|
||||||
|
/* Match! */
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
blwarn:
|
||||||
|
if (bl->lastwarning + 3600 < rb_current_time())
|
||||||
|
{
|
||||||
|
warn_opers(L_WARN, "Garbage/undecipherable reply received from blacklist %s (reply %s)",
|
||||||
|
bl->host, ipaddr);
|
||||||
|
bl->lastwarning = rb_current_time();
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
blacklist_dns_callback(const char *result, bool status, query_type type, void *data)
|
||||||
|
{
|
||||||
|
struct blacklist_lookup *bllookup = (struct blacklist_lookup *)data;
|
||||||
|
struct blacklist_user *bluser;
|
||||||
|
struct blacklist *bl;
|
||||||
|
struct auth_client *auth;
|
||||||
|
|
||||||
|
if (bllookup == NULL || bllookup->auth == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
|
bl = bllookup->bl;
|
||||||
|
auth = bllookup->auth;
|
||||||
|
bluser = auth->data[PROVIDER_BLACKLIST];
|
||||||
|
if(bluser == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (result != NULL && status && blacklist_check_reply(bllookup, result))
|
||||||
|
{
|
||||||
|
/* Match found, so proceed no further */
|
||||||
|
blacklists_cancel(auth);
|
||||||
|
reject_client(auth, PROVIDER_BLACKLIST, bl->reason);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
unref_blacklist(bl);
|
||||||
|
cancel_query(bllookup->query); /* Ignore future responses */
|
||||||
|
rb_dlinkDelete(&bllookup->node, &bluser->queries);
|
||||||
|
rb_free(bllookup);
|
||||||
|
|
||||||
|
if(!rb_dlink_list_length(&bluser->queries))
|
||||||
|
{
|
||||||
|
/* Done here */
|
||||||
|
rb_free(bluser);
|
||||||
|
auth->data[PROVIDER_BLACKLIST] = NULL;
|
||||||
|
provider_done(auth, PROVIDER_BLACKLIST);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
initiate_blacklist_dnsquery(struct blacklist *bl, struct auth_client *auth)
|
||||||
|
{
|
||||||
|
struct blacklist_lookup *bllookup = rb_malloc(sizeof(struct blacklist_lookup));
|
||||||
|
struct blacklist_user *bluser = auth->data[PROVIDER_BLACKLIST];
|
||||||
|
char buf[IRCD_RES_HOSTLEN + 1];
|
||||||
|
int aftype;
|
||||||
|
|
||||||
|
bllookup->bl = bl;
|
||||||
|
bllookup->auth = auth;
|
||||||
|
|
||||||
|
aftype = GET_SS_FAMILY(&auth->c_addr);
|
||||||
|
if((aftype == AF_INET && (bl->iptype & IPTYPE_IPV4) == 0) ||
|
||||||
|
(aftype == AF_INET6 && (bl->iptype & IPTYPE_IPV6) == 0))
|
||||||
|
/* Incorrect blacklist type for this IP... */
|
||||||
|
return;
|
||||||
|
|
||||||
|
build_rdns(buf, sizeof(buf), &auth->c_addr, bl->host);
|
||||||
|
|
||||||
|
bllookup->query = lookup_ip(buf, AF_INET, blacklist_dns_callback, bllookup);
|
||||||
|
|
||||||
|
rb_dlinkAdd(bllookup, &bllookup->node, &bluser->queries);
|
||||||
|
bl->refcount++;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Timeout outstanding queries */
|
||||||
|
static void
|
||||||
|
timeout_blacklist_queries_event(void *notused)
|
||||||
|
{
|
||||||
|
struct auth_client *auth;
|
||||||
|
rb_dictionary_iter iter;
|
||||||
|
|
||||||
|
RB_DICTIONARY_FOREACH(auth, &iter, auth_clients)
|
||||||
|
{
|
||||||
|
struct blacklist_user *bluser = auth->data[PROVIDER_BLACKLIST];
|
||||||
|
|
||||||
|
if(bluser != NULL && bluser->timeout < rb_current_time())
|
||||||
|
{
|
||||||
|
blacklists_cancel(auth);
|
||||||
|
provider_done(auth, PROVIDER_BLACKLIST);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void
|
||||||
|
lookup_all_blacklists(struct auth_client *auth)
|
||||||
|
{
|
||||||
|
struct blacklist_user *bluser = auth->data[PROVIDER_BLACKLIST];
|
||||||
|
rb_dlink_node *ptr;
|
||||||
|
|
||||||
|
RB_DLINK_FOREACH(ptr, blacklist_list.head)
|
||||||
|
{
|
||||||
|
struct blacklist *bl = (struct blacklist *)ptr->data;
|
||||||
|
|
||||||
|
if (!bl->delete)
|
||||||
|
initiate_blacklist_dnsquery(bl, auth);
|
||||||
|
}
|
||||||
|
|
||||||
|
bluser->timeout = rb_current_time() + blacklist_timeout;
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void
|
||||||
|
delete_blacklist(struct blacklist *bl)
|
||||||
|
{
|
||||||
|
if (bl->refcount > 0)
|
||||||
|
bl->delete = true;
|
||||||
|
else
|
||||||
|
{
|
||||||
|
rb_dlinkFindDestroy(bl, &blacklist_list);
|
||||||
|
rb_free(bl);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
delete_all_blacklists(void)
|
||||||
|
{
|
||||||
|
rb_dlink_node *ptr, *nptr;
|
||||||
|
|
||||||
|
RB_DLINK_FOREACH_SAFE(ptr, nptr, blacklist_list.head)
|
||||||
|
{
|
||||||
|
delete_blacklist(ptr->data);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* public interfaces */
|
||||||
|
static bool
|
||||||
|
blacklists_start(struct auth_client *auth)
|
||||||
|
{
|
||||||
|
if(auth->data[PROVIDER_BLACKLIST] != NULL)
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if(!rb_dlink_list_length(&blacklist_list))
|
||||||
|
/* Nothing to do... */
|
||||||
|
return true;
|
||||||
|
|
||||||
|
auth->data[PROVIDER_BLACKLIST] = rb_malloc(sizeof(struct blacklist_user));
|
||||||
|
|
||||||
|
if(is_provider_done(auth, PROVIDER_RDNS) && is_provider_done(auth, PROVIDER_IDENT))
|
||||||
|
/* This probably can't happen but let's handle this case anyway */
|
||||||
|
lookup_all_blacklists(auth);
|
||||||
|
|
||||||
|
set_provider_on(auth, PROVIDER_BLACKLIST);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* This is called every time a provider is completed as long as we are marked not done */
|
||||||
|
static void
|
||||||
|
blacklists_initiate(struct auth_client *auth, provider_t provider)
|
||||||
|
{
|
||||||
|
struct blacklist_user *bluser = auth->data[PROVIDER_BLACKLIST];
|
||||||
|
|
||||||
|
lrb_assert(provider != PROVIDER_BLACKLIST);
|
||||||
|
lrb_assert(!is_provider_done(auth, PROVIDER_BLACKLIST));
|
||||||
|
lrb_assert(rb_dlink_list_length(&blacklist_list) > 0);
|
||||||
|
|
||||||
|
if(bluser == NULL || rb_dlink_list_length(&bluser->queries))
|
||||||
|
/* Nothing to do */
|
||||||
|
return;
|
||||||
|
else if(!(is_provider_done(auth, PROVIDER_RDNS) && is_provider_done(auth, PROVIDER_IDENT)))
|
||||||
|
/* Don't start until we've completed these */
|
||||||
|
return;
|
||||||
|
else
|
||||||
|
lookup_all_blacklists(auth);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
blacklists_cancel(struct auth_client *auth)
|
||||||
|
{
|
||||||
|
rb_dlink_node *ptr, *nptr;
|
||||||
|
struct blacklist_user *bluser = auth->data[PROVIDER_BLACKLIST];
|
||||||
|
|
||||||
|
if(bluser == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
|
RB_DLINK_FOREACH_SAFE(ptr, nptr, bluser->queries.head)
|
||||||
|
{
|
||||||
|
struct blacklist_lookup *bllookup = ptr->data;
|
||||||
|
|
||||||
|
cancel_query(bllookup->query);
|
||||||
|
unref_blacklist(bllookup->bl);
|
||||||
|
|
||||||
|
rb_dlinkDelete(&bllookup->node, &bluser->queries);
|
||||||
|
rb_free(bllookup);
|
||||||
|
}
|
||||||
|
|
||||||
|
rb_free(bluser);
|
||||||
|
auth->data[PROVIDER_BLACKLIST] = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool
|
||||||
|
blacklists_init(void)
|
||||||
|
{
|
||||||
|
timeout_ev = rb_event_addish("timeout_blacklist_queries_event", timeout_blacklist_queries_event, NULL, 1);
|
||||||
|
return (timeout_ev != NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
blacklists_destroy(void)
|
||||||
|
{
|
||||||
|
rb_dlink_node *ptr, *nptr;
|
||||||
|
rb_dictionary_iter iter;
|
||||||
|
struct blacklist *bl;
|
||||||
|
struct auth_client *auth;
|
||||||
|
|
||||||
|
RB_DICTIONARY_FOREACH(auth, &iter, auth_clients)
|
||||||
|
{
|
||||||
|
blacklists_cancel(auth);
|
||||||
|
}
|
||||||
|
|
||||||
|
delete_all_blacklists();
|
||||||
|
rb_event_delete(timeout_ev);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
add_conf_blacklist(const char *key, int parc, const char **parv)
|
||||||
|
{
|
||||||
|
rb_dlink_list filters = { NULL, NULL, 0 };
|
||||||
|
char *tmp, *elemlist = rb_strdup(parv[2]);
|
||||||
|
unsigned char iptype;
|
||||||
|
|
||||||
|
if(*elemlist == '*')
|
||||||
|
goto end;
|
||||||
|
|
||||||
|
for(char *elem = rb_strtok_r(elemlist, ",", &tmp); elem; elem = rb_strtok_r(NULL, ",", &tmp))
|
||||||
|
{
|
||||||
|
struct blacklist_filter *filter = rb_malloc(sizeof(struct blacklist_filter));
|
||||||
|
int dot_c = 0;
|
||||||
|
filter_t type = FILTER_LAST;
|
||||||
|
bool valid = true;
|
||||||
|
|
||||||
|
/* Check blacklist filter type and for validity */
|
||||||
|
for(char *c = elem; *c != '\0'; c++)
|
||||||
|
{
|
||||||
|
if(*c == '.')
|
||||||
|
{
|
||||||
|
if(++dot_c > 3)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "addr_conf_blacklist got a bad filter (too many octets)");
|
||||||
|
valid = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
type = FILTER_ALL;
|
||||||
|
}
|
||||||
|
else if(!isdigit(*c))
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "addr_conf_blacklist got a bad filter (invalid character in blacklist filter: %c)", *c);
|
||||||
|
valid = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if(valid && dot_c > 0 && dot_c < 3)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "addr_conf_blacklist got a bad filter (insufficient octets)");
|
||||||
|
valid = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(!valid)
|
||||||
|
{
|
||||||
|
rb_free(filter);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
filter->type = type;
|
||||||
|
rb_strlcpy(filter->filter, elem, sizeof(filter->filter));
|
||||||
|
rb_dlinkAdd(filter, &filter->node, &filters);
|
||||||
|
}
|
||||||
|
|
||||||
|
end:
|
||||||
|
rb_free(elemlist);
|
||||||
|
|
||||||
|
iptype = atoi(parv[1]) & 0x3;
|
||||||
|
if(new_blacklist(parv[0], parv[3], iptype, &filters) == NULL)
|
||||||
|
{
|
||||||
|
rb_dlink_node *ptr, *nptr;
|
||||||
|
|
||||||
|
warn_opers(L_CRIT, "addr_conf_blacklist got a malformed blacklist");
|
||||||
|
|
||||||
|
RB_DLINK_FOREACH_SAFE(ptr, nptr, filters.head)
|
||||||
|
{
|
||||||
|
rb_free(ptr->data);
|
||||||
|
rb_dlinkDelete(ptr, &filters);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
del_conf_blacklist(const char *key, int parc, const char **parv)
|
||||||
|
{
|
||||||
|
struct blacklist *bl = find_blacklist(parv[0]);
|
||||||
|
if(bl == NULL)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: tried to remove nonexistent blacklist %s", parv[0]);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
delete_blacklist(bl);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
del_conf_blacklist_all(const char *key, int parc, const char **parv)
|
||||||
|
{
|
||||||
|
delete_all_blacklists();
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
add_conf_blacklist_timeout(const char *key, int parc, const char **parv)
|
||||||
|
{
|
||||||
|
int timeout = atoi(parv[0]);
|
||||||
|
|
||||||
|
if(timeout < 0)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: blacklist timeout < 0 (value: %d)", timeout);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
blacklist_timeout = timeout;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct auth_opts_handler blacklist_options[] =
|
||||||
|
{
|
||||||
|
{ "rbl", 4, add_conf_blacklist },
|
||||||
|
{ "rbl_del", 1, del_conf_blacklist },
|
||||||
|
{ "rbl_del_all", 0, del_conf_blacklist_all },
|
||||||
|
{ "rbl_timeout", 1, add_conf_blacklist_timeout },
|
||||||
|
{ NULL, 0, NULL },
|
||||||
|
};
|
||||||
|
|
||||||
|
struct auth_provider blacklist_provider =
|
||||||
|
{
|
||||||
|
.id = PROVIDER_BLACKLIST,
|
||||||
|
.init = blacklists_init,
|
||||||
|
.destroy = blacklists_destroy,
|
||||||
|
.start = blacklists_start,
|
||||||
|
.cancel = blacklists_cancel,
|
||||||
|
.completed = blacklists_initiate,
|
||||||
|
.opt_handlers = blacklist_options,
|
||||||
|
};
|
|
@ -18,9 +18,16 @@
|
||||||
* POSSIBILITY OF SUCH DAMAGE.
|
* POSSIBILITY OF SUCH DAMAGE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/* Largely adapted from old s_auth.c, but reworked for authd. rDNS code
|
||||||
|
* moved to its own provider.
|
||||||
|
*
|
||||||
|
* --Elizafox 13 March 2016
|
||||||
|
*/
|
||||||
|
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "match.h"
|
#include "match.h"
|
||||||
#include "authd.h"
|
#include "authd.h"
|
||||||
|
#include "notice.h"
|
||||||
#include "provider.h"
|
#include "provider.h"
|
||||||
#include "res.h"
|
#include "res.h"
|
||||||
|
|
||||||
|
@ -28,9 +35,6 @@
|
||||||
|
|
||||||
struct ident_query
|
struct ident_query
|
||||||
{
|
{
|
||||||
rb_dlink_node node;
|
|
||||||
|
|
||||||
struct auth_client *auth; /* Our client */
|
|
||||||
time_t timeout; /* Timeout interval */
|
time_t timeout; /* Timeout interval */
|
||||||
rb_fde_t *F; /* Our FD */
|
rb_fde_t *F; /* Our FD */
|
||||||
};
|
};
|
||||||
|
@ -38,9 +42,10 @@ struct ident_query
|
||||||
/* Goinked from old s_auth.c --Elizafox */
|
/* Goinked from old s_auth.c --Elizafox */
|
||||||
static const char *messages[] =
|
static const char *messages[] =
|
||||||
{
|
{
|
||||||
":*** Checking Ident",
|
"*** Checking Ident",
|
||||||
":*** Got Ident response",
|
"*** Got Ident response",
|
||||||
":*** No Ident response",
|
"*** No Ident response",
|
||||||
|
"*** Cannot verify ident validity, ignoring ident",
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef enum
|
typedef enum
|
||||||
|
@ -48,134 +53,34 @@ typedef enum
|
||||||
REPORT_LOOKUP,
|
REPORT_LOOKUP,
|
||||||
REPORT_FOUND,
|
REPORT_FOUND,
|
||||||
REPORT_FAIL,
|
REPORT_FAIL,
|
||||||
|
REPORT_INVALID,
|
||||||
} ident_message;
|
} ident_message;
|
||||||
|
|
||||||
static EVH timeout_ident_queries_event;
|
static EVH timeout_ident_queries_event;
|
||||||
static CNCB ident_connected;
|
static CNCB ident_connected;
|
||||||
static PF read_ident_reply;
|
static PF read_ident_reply;
|
||||||
|
|
||||||
static void client_fail(struct ident_query *query, ident_message message);
|
static void client_fail(struct auth_client *auth, ident_message message);
|
||||||
static void client_success(struct ident_query *query);
|
static void client_success(struct auth_client *auth);
|
||||||
static void cleanup_query(struct ident_query *query);
|
|
||||||
static char * get_valid_ident(char *buf);
|
static char * get_valid_ident(char *buf);
|
||||||
|
|
||||||
static rb_dlink_list queries;
|
|
||||||
static struct ev_entry *timeout_ev;
|
static struct ev_entry *timeout_ev;
|
||||||
static int ident_timeout = 5;
|
static int ident_timeout = 5;
|
||||||
|
|
||||||
|
|
||||||
bool ident_init(void)
|
|
||||||
{
|
|
||||||
timeout_ev = rb_event_addish("timeout_ident_queries_event", timeout_ident_queries_event, NULL, 1);
|
|
||||||
return (timeout_ev != NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
void ident_destroy(void)
|
|
||||||
{
|
|
||||||
rb_dlink_node *ptr, *nptr;
|
|
||||||
|
|
||||||
/* Nuke all ident queries */
|
|
||||||
RB_DLINK_FOREACH_SAFE(ptr, nptr, queries.head)
|
|
||||||
{
|
|
||||||
struct ident_query *query = ptr->data;
|
|
||||||
|
|
||||||
notice_client(query->auth, messages[REPORT_FAIL]);
|
|
||||||
|
|
||||||
rb_close(query->F);
|
|
||||||
rb_free(query);
|
|
||||||
rb_dlinkDelete(ptr, &queries);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
bool ident_start(struct auth_client *auth)
|
|
||||||
{
|
|
||||||
struct ident_query *query = rb_malloc(sizeof(struct ident_query));
|
|
||||||
struct rb_sockaddr_storage localaddr, clientaddr;
|
|
||||||
int family;
|
|
||||||
rb_fde_t *F;
|
|
||||||
|
|
||||||
query->auth = auth;
|
|
||||||
query->timeout = rb_current_time() + ident_timeout;
|
|
||||||
|
|
||||||
if((F = rb_socket(family, SOCK_STREAM, 0, "ident")) == NULL)
|
|
||||||
{
|
|
||||||
client_fail(query, REPORT_FAIL);
|
|
||||||
return true; /* Not a fatal error */
|
|
||||||
}
|
|
||||||
|
|
||||||
query->F = F;
|
|
||||||
|
|
||||||
/* Build sockaddr_storages for rb_connect_tcp below */
|
|
||||||
memcpy(&localaddr, &auth->l_addr, sizeof(struct rb_sockaddr_storage));
|
|
||||||
memcpy(&clientaddr, &auth->c_addr, sizeof(struct rb_sockaddr_storage));
|
|
||||||
|
|
||||||
/* Set the ports correctly */
|
|
||||||
#ifdef RB_IPV6
|
|
||||||
if(GET_SS_FAMILY(&localaddr) == AF_INET6)
|
|
||||||
((struct sockaddr_in6 *)&localaddr)->sin6_port = 0;
|
|
||||||
else
|
|
||||||
#endif
|
|
||||||
((struct sockaddr_in *)&localaddr)->sin_port = 0;
|
|
||||||
|
|
||||||
#ifdef RB_IPV6
|
|
||||||
if(GET_SS_FAMILY(&clientaddr) == AF_INET6)
|
|
||||||
((struct sockaddr_in6 *)&clientaddr)->sin6_port = htons(113);
|
|
||||||
else
|
|
||||||
#endif
|
|
||||||
((struct sockaddr_in *)&clientaddr)->sin_port = htons(113);
|
|
||||||
|
|
||||||
rb_connect_tcp(F, (struct sockaddr *)&auth->c_addr,
|
|
||||||
(struct sockaddr *)&auth->l_addr,
|
|
||||||
GET_SS_LEN(&auth->l_addr), ident_connected,
|
|
||||||
query, ident_timeout);
|
|
||||||
|
|
||||||
set_provider(auth, PROVIDER_IDENT);
|
|
||||||
|
|
||||||
rb_dlinkAdd(query, &query->node, &queries);
|
|
||||||
|
|
||||||
notice_client(auth, messages[REPORT_LOOKUP]);
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void ident_cancel(struct auth_client *auth)
|
|
||||||
{
|
|
||||||
rb_dlink_node *ptr, *nptr;
|
|
||||||
|
|
||||||
RB_DLINK_FOREACH_SAFE(ptr, nptr, queries.head)
|
|
||||||
{
|
|
||||||
struct ident_query *query = ptr->data;
|
|
||||||
|
|
||||||
if(query->auth == auth)
|
|
||||||
{
|
|
||||||
client_fail(query, REPORT_FAIL);
|
|
||||||
|
|
||||||
rb_close(query->F);
|
|
||||||
rb_free(query);
|
|
||||||
rb_dlinkDelete(ptr, &queries);
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Timeout outstanding queries */
|
/* Timeout outstanding queries */
|
||||||
static void timeout_ident_queries_event(void *notused)
|
static void
|
||||||
|
timeout_ident_queries_event(void *notused __unused)
|
||||||
{
|
{
|
||||||
rb_dlink_node *ptr, *nptr;
|
struct auth_client *auth;
|
||||||
|
rb_dictionary_iter iter;
|
||||||
|
|
||||||
RB_DLINK_FOREACH_SAFE(ptr, nptr, queries.head)
|
RB_DICTIONARY_FOREACH(auth, &iter, auth_clients)
|
||||||
{
|
{
|
||||||
struct ident_query *query = ptr->data;
|
struct ident_query *query = auth->data[PROVIDER_IDENT];
|
||||||
|
|
||||||
if(query->timeout < rb_current_time())
|
if(query != NULL && query->timeout < rb_current_time())
|
||||||
{
|
client_fail(auth, REPORT_FAIL);
|
||||||
client_fail(query, REPORT_FAIL);
|
|
||||||
|
|
||||||
rb_close(query->F);
|
|
||||||
rb_free(query);
|
|
||||||
rb_dlinkDelete(ptr, &queries);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -190,74 +95,73 @@ static void timeout_ident_queries_event(void *notused)
|
||||||
* a write buffer far greater than this message to store it in should
|
* a write buffer far greater than this message to store it in should
|
||||||
* problems arise. -avalon
|
* problems arise. -avalon
|
||||||
*/
|
*/
|
||||||
static void ident_connected(rb_fde_t *F, int error, void *data)
|
static void
|
||||||
|
ident_connected(rb_fde_t *F __unused, int error, void *data)
|
||||||
{
|
{
|
||||||
struct ident_query *query = data;
|
struct auth_client *auth = data;
|
||||||
struct auth_client *auth = query->auth;
|
struct ident_query *query;
|
||||||
uint16_t c_port, l_port;
|
|
||||||
char authbuf[32];
|
char authbuf[32];
|
||||||
int authlen;
|
int authlen;
|
||||||
|
|
||||||
|
if(auth == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
|
query = auth->data[PROVIDER_IDENT];
|
||||||
|
|
||||||
|
if(query == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
/* Check the error */
|
/* Check the error */
|
||||||
if(error != RB_OK)
|
if(error != RB_OK)
|
||||||
{
|
{
|
||||||
/* We had an error during connection :( */
|
/* We had an error during connection :( */
|
||||||
client_fail(query, REPORT_FAIL);
|
client_fail(auth, REPORT_FAIL);
|
||||||
cleanup_query(query);
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef RB_IPV6
|
|
||||||
if(GET_SS_FAMILY(&auth->c_addr) == AF_INET6)
|
|
||||||
c_port = ntohs(((struct sockaddr_in6 *)&auth->c_addr)->sin6_port);
|
|
||||||
else
|
|
||||||
#endif
|
|
||||||
c_port = ntohs(((struct sockaddr_in *)&auth->c_addr)->sin_port);
|
|
||||||
|
|
||||||
#ifdef RB_IPV6
|
|
||||||
if(GET_SS_FAMILY(&auth->l_addr) == AF_INET6)
|
|
||||||
l_port = ntohs(((struct sockaddr_in6 *)&auth->l_addr)->sin6_port);
|
|
||||||
else
|
|
||||||
#endif
|
|
||||||
l_port = ntohs(((struct sockaddr_in *)&auth->l_addr)->sin_port);
|
|
||||||
|
|
||||||
|
|
||||||
snprintf(authbuf, sizeof(authbuf), "%u , %u\r\n",
|
snprintf(authbuf, sizeof(authbuf), "%u , %u\r\n",
|
||||||
c_port, l_port);
|
auth->c_port, auth->l_port);
|
||||||
authlen = strlen(authbuf);
|
authlen = strlen(authbuf);
|
||||||
|
|
||||||
if(rb_write(query->F, authbuf, authlen) != authlen)
|
if(rb_write(query->F, authbuf, authlen) != authlen)
|
||||||
{
|
{
|
||||||
client_fail(query, REPORT_FAIL);
|
client_fail(auth, REPORT_FAIL);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
read_ident_reply(query->F, query);
|
read_ident_reply(query->F, auth);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
read_ident_reply(rb_fde_t *F, void *data)
|
read_ident_reply(rb_fde_t *F, void *data)
|
||||||
{
|
{
|
||||||
struct ident_query *query = data;
|
struct auth_client *auth = data;
|
||||||
struct auth_client *auth = query->auth;
|
struct ident_query *query;
|
||||||
|
char buf[IDENT_BUFSIZE + 1]; /* buffer to read auth reply into */
|
||||||
|
ident_message message = REPORT_FAIL;
|
||||||
char *s = NULL;
|
char *s = NULL;
|
||||||
char *t = NULL;
|
char *t = NULL;
|
||||||
int len;
|
ssize_t len;
|
||||||
int count;
|
int count;
|
||||||
char buf[IDENT_BUFSIZE + 1]; /* buffer to read auth reply into */
|
|
||||||
|
if(auth == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
|
query = auth->data[PROVIDER_IDENT];
|
||||||
|
|
||||||
|
if(query == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
len = rb_read(F, buf, IDENT_BUFSIZE);
|
len = rb_read(F, buf, IDENT_BUFSIZE);
|
||||||
if(len < 0 && rb_ignore_errno(errno))
|
if(len < 0 && rb_ignore_errno(errno))
|
||||||
{
|
{
|
||||||
rb_setselect(F, RB_SELECT_READ, read_ident_reply, query);
|
rb_setselect(F, RB_SELECT_READ, read_ident_reply, auth);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(len > 0)
|
if(len > 0)
|
||||||
{
|
{
|
||||||
buf[len] = '\0';
|
if((s = get_valid_ident(buf)) != NULL)
|
||||||
|
|
||||||
if((s = get_valid_ident(buf)))
|
|
||||||
{
|
{
|
||||||
t = auth->username;
|
t = auth->username;
|
||||||
|
|
||||||
|
@ -266,10 +170,9 @@ read_ident_reply(rb_fde_t *F, void *data)
|
||||||
|
|
||||||
for (count = USERLEN; *s && count; s++)
|
for (count = USERLEN; *s && count; s++)
|
||||||
{
|
{
|
||||||
if(*s == '@')
|
if(*s == '@' || *s == '\r' || *s == '\n')
|
||||||
{
|
|
||||||
break;
|
break;
|
||||||
}
|
|
||||||
if(*s != ' ' && *s != ':' && *s != '[')
|
if(*s != ' ' && *s != ':' && *s != '[')
|
||||||
{
|
{
|
||||||
*t++ = *s;
|
*t++ = *s;
|
||||||
|
@ -278,61 +181,58 @@ read_ident_reply(rb_fde_t *F, void *data)
|
||||||
}
|
}
|
||||||
*t = '\0';
|
*t = '\0';
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
message = REPORT_INVALID;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(s == NULL)
|
if(s == NULL)
|
||||||
client_fail(query, REPORT_FAIL);
|
client_fail(auth, message);
|
||||||
else
|
else
|
||||||
client_success(query);
|
client_success(auth);
|
||||||
|
|
||||||
cleanup_query(query);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void client_fail(struct ident_query *query, ident_message report)
|
static void
|
||||||
|
client_fail(struct auth_client *auth, ident_message report)
|
||||||
{
|
{
|
||||||
struct auth_client *auth = query->auth;
|
struct ident_query *query = auth->data[PROVIDER_IDENT];
|
||||||
|
|
||||||
|
if(query == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
if(auth)
|
|
||||||
{
|
|
||||||
rb_strlcpy(auth->username, "*", sizeof(auth->username));
|
rb_strlcpy(auth->username, "*", sizeof(auth->username));
|
||||||
notice_client(auth, messages[report]);
|
|
||||||
provider_done(auth, PROVIDER_IDENT);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void client_success(struct ident_query *query)
|
if(query->F != NULL)
|
||||||
{
|
|
||||||
struct auth_client *auth = query->auth;
|
|
||||||
|
|
||||||
if(auth)
|
|
||||||
{
|
|
||||||
notice_client(auth, messages[REPORT_FOUND]);
|
|
||||||
provider_done(auth, PROVIDER_IDENT);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void cleanup_query(struct ident_query *query)
|
|
||||||
{
|
|
||||||
rb_dlink_node *ptr, *nptr;
|
|
||||||
|
|
||||||
RB_DLINK_FOREACH_SAFE(ptr, nptr, queries.head)
|
|
||||||
{
|
|
||||||
struct ident_query *query_l = ptr->data;
|
|
||||||
|
|
||||||
if(query_l == query)
|
|
||||||
{
|
|
||||||
rb_close(query->F);
|
rb_close(query->F);
|
||||||
|
|
||||||
rb_free(query);
|
rb_free(query);
|
||||||
rb_dlinkDelete(ptr, &queries);
|
auth->data[PROVIDER_IDENT] = NULL;
|
||||||
}
|
|
||||||
|
notice_client(auth->cid, messages[report]);
|
||||||
|
provider_done(auth, PROVIDER_IDENT);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
client_success(struct auth_client *auth)
|
||||||
|
{
|
||||||
|
struct ident_query *query = auth->data[PROVIDER_IDENT];
|
||||||
|
|
||||||
|
if(query == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if(query->F != NULL)
|
||||||
|
rb_close(query->F);
|
||||||
|
|
||||||
|
rb_free(query);
|
||||||
|
auth->data[PROVIDER_IDENT] = NULL;
|
||||||
|
|
||||||
|
notice_client(auth->cid, messages[REPORT_FOUND]);
|
||||||
|
provider_done(auth, PROVIDER_IDENT);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* get_valid_ident
|
/* get_valid_ident
|
||||||
* parse ident query reply from identd server
|
* parse ident query reply from identd server
|
||||||
*
|
*
|
||||||
* Torn out of old s_auth.c because there was nothing wrong with it
|
* Taken from old s_auth.c --Elizafox
|
||||||
* --Elizafox
|
|
||||||
*
|
*
|
||||||
* Inputs - pointer to ident buf
|
* Inputs - pointer to ident buf
|
||||||
* Outputs - NULL if no valid ident found, otherwise pointer to name
|
* Outputs - NULL if no valid ident found, otherwise pointer to name
|
||||||
|
@ -354,45 +254,145 @@ get_valid_ident(char *buf)
|
||||||
|
|
||||||
colon1Ptr = strchr(remotePortString, ':');
|
colon1Ptr = strchr(remotePortString, ':');
|
||||||
if(!colon1Ptr)
|
if(!colon1Ptr)
|
||||||
return 0;
|
return NULL;
|
||||||
|
|
||||||
*colon1Ptr = '\0';
|
*colon1Ptr = '\0';
|
||||||
colon1Ptr++;
|
colon1Ptr++;
|
||||||
colon2Ptr = strchr(colon1Ptr, ':');
|
colon2Ptr = strchr(colon1Ptr, ':');
|
||||||
if(!colon2Ptr)
|
if(!colon2Ptr)
|
||||||
return 0;
|
return NULL;
|
||||||
|
|
||||||
*colon2Ptr = '\0';
|
*colon2Ptr = '\0';
|
||||||
colon2Ptr++;
|
colon2Ptr++;
|
||||||
commaPtr = strchr(remotePortString, ',');
|
commaPtr = strchr(remotePortString, ',');
|
||||||
|
|
||||||
if(!commaPtr)
|
if(!commaPtr)
|
||||||
return 0;
|
return NULL;
|
||||||
|
|
||||||
*commaPtr = '\0';
|
*commaPtr = '\0';
|
||||||
commaPtr++;
|
commaPtr++;
|
||||||
|
|
||||||
remp = atoi(remotePortString);
|
remp = atoi(remotePortString);
|
||||||
if(!remp)
|
if(!remp)
|
||||||
return 0;
|
return NULL;
|
||||||
|
|
||||||
locp = atoi(commaPtr);
|
locp = atoi(commaPtr);
|
||||||
if(!locp)
|
if(!locp)
|
||||||
return 0;
|
return NULL;
|
||||||
|
|
||||||
/* look for USERID bordered by first pair of colons */
|
/* look for USERID bordered by first pair of colons */
|
||||||
if(!strstr(colon1Ptr, "USERID"))
|
if(!strstr(colon1Ptr, "USERID"))
|
||||||
return 0;
|
return NULL;
|
||||||
|
|
||||||
colon3Ptr = strchr(colon2Ptr, ':');
|
colon3Ptr = strchr(colon2Ptr, ':');
|
||||||
if(!colon3Ptr)
|
if(!colon3Ptr)
|
||||||
return 0;
|
return NULL;
|
||||||
|
|
||||||
*colon3Ptr = '\0';
|
*colon3Ptr = '\0';
|
||||||
colon3Ptr++;
|
colon3Ptr++;
|
||||||
return (colon3Ptr);
|
return (colon3Ptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static bool
|
||||||
|
ident_init(void)
|
||||||
|
{
|
||||||
|
timeout_ev = rb_event_addish("timeout_ident_queries_event", timeout_ident_queries_event, NULL, 1);
|
||||||
|
return (timeout_ev != NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
ident_destroy(void)
|
||||||
|
{
|
||||||
|
struct auth_client *auth;
|
||||||
|
rb_dictionary_iter iter;
|
||||||
|
|
||||||
|
/* Nuke all ident queries */
|
||||||
|
RB_DICTIONARY_FOREACH(auth, &iter, auth_clients)
|
||||||
|
{
|
||||||
|
if(auth->data[PROVIDER_IDENT] != NULL)
|
||||||
|
client_fail(auth, REPORT_FAIL);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool ident_start(struct auth_client *auth)
|
||||||
|
{
|
||||||
|
struct ident_query *query = rb_malloc(sizeof(struct ident_query));
|
||||||
|
struct rb_sockaddr_storage l_addr, c_addr;
|
||||||
|
int family = GET_SS_FAMILY(&auth->c_addr);
|
||||||
|
|
||||||
|
if(auth->data[PROVIDER_IDENT] != NULL)
|
||||||
|
return true;
|
||||||
|
|
||||||
|
notice_client(auth->cid, messages[REPORT_LOOKUP]);
|
||||||
|
|
||||||
|
auth->data[PROVIDER_IDENT] = query;
|
||||||
|
query->timeout = rb_current_time() + ident_timeout;
|
||||||
|
|
||||||
|
if((query->F = rb_socket(family, SOCK_STREAM, 0, "ident")) == NULL)
|
||||||
|
{
|
||||||
|
warn_opers(L_DEBUG, "Could not create ident socket: %s", strerror(errno));
|
||||||
|
client_fail(auth, REPORT_FAIL);
|
||||||
|
return true; /* Not a fatal error */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Build sockaddr_storages for rb_connect_tcp below */
|
||||||
|
memcpy(&l_addr, &auth->l_addr, sizeof(l_addr));
|
||||||
|
memcpy(&c_addr, &auth->c_addr, sizeof(c_addr));
|
||||||
|
|
||||||
|
/* Set the ports correctly */
|
||||||
|
#ifdef RB_IPV6
|
||||||
|
if(GET_SS_FAMILY(&l_addr) == AF_INET6)
|
||||||
|
((struct sockaddr_in6 *)&l_addr)->sin6_port = 0;
|
||||||
|
else
|
||||||
|
#endif
|
||||||
|
((struct sockaddr_in *)&l_addr)->sin_port = 0;
|
||||||
|
|
||||||
|
#ifdef RB_IPV6
|
||||||
|
if(GET_SS_FAMILY(&c_addr) == AF_INET6)
|
||||||
|
((struct sockaddr_in6 *)&c_addr)->sin6_port = htons(113);
|
||||||
|
else
|
||||||
|
#endif
|
||||||
|
((struct sockaddr_in *)&c_addr)->sin_port = htons(113);
|
||||||
|
|
||||||
|
rb_connect_tcp(query->F, (struct sockaddr *)&c_addr,
|
||||||
|
(struct sockaddr *)&l_addr,
|
||||||
|
GET_SS_LEN(&l_addr), ident_connected,
|
||||||
|
auth, ident_timeout);
|
||||||
|
|
||||||
|
set_provider_on(auth, PROVIDER_IDENT);
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
ident_cancel(struct auth_client *auth)
|
||||||
|
{
|
||||||
|
struct ident_query *query = auth->data[PROVIDER_IDENT];
|
||||||
|
|
||||||
|
if(query != NULL)
|
||||||
|
client_fail(auth, REPORT_FAIL);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
add_conf_ident_timeout(const char *key __unused, int parc __unused, const char **parv)
|
||||||
|
{
|
||||||
|
int timeout = atoi(parv[0]);
|
||||||
|
|
||||||
|
if(timeout < 0)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: ident timeout < 0 (value: %d)", timeout);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
ident_timeout = timeout;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct auth_opts_handler ident_options[] =
|
||||||
|
{
|
||||||
|
{ "ident_timeout", 1, add_conf_ident_timeout },
|
||||||
|
{ NULL, 0, NULL },
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
struct auth_provider ident_provider =
|
struct auth_provider ident_provider =
|
||||||
{
|
{
|
||||||
|
@ -402,4 +402,5 @@ struct auth_provider ident_provider =
|
||||||
.start = ident_start,
|
.start = ident_start,
|
||||||
.cancel = ident_cancel,
|
.cancel = ident_cancel,
|
||||||
.completed = NULL,
|
.completed = NULL,
|
||||||
|
.opt_handlers = ident_options,
|
||||||
};
|
};
|
||||||
|
|
|
@ -22,15 +22,13 @@
|
||||||
#include "rb_commio.h"
|
#include "rb_commio.h"
|
||||||
#include "authd.h"
|
#include "authd.h"
|
||||||
#include "provider.h"
|
#include "provider.h"
|
||||||
|
#include "notice.h"
|
||||||
#include "res.h"
|
#include "res.h"
|
||||||
#include "dns.h"
|
#include "dns.h"
|
||||||
|
|
||||||
struct dns_query
|
struct user_query
|
||||||
{
|
{
|
||||||
rb_dlink_node node;
|
struct dns_query *query; /* Pending DNS query */
|
||||||
|
|
||||||
struct auth_client *auth; /* Our client */
|
|
||||||
struct DNSQuery query; /* DNS query */
|
|
||||||
time_t timeout; /* When the request times out */
|
time_t timeout; /* When the request times out */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -51,176 +49,157 @@ typedef enum
|
||||||
REPORT_TOOLONG,
|
REPORT_TOOLONG,
|
||||||
} dns_message;
|
} dns_message;
|
||||||
|
|
||||||
static EVH timeout_dns_queries_event;
|
static void client_fail(struct auth_client *auth, dns_message message);
|
||||||
static void client_fail(struct dns_query *query, dns_message message);
|
static void client_success(struct auth_client *auth);
|
||||||
static void client_success(struct dns_query *query);
|
static void dns_answer_callback(const char *res, bool status, query_type type, void *data);
|
||||||
static void get_dns_answer(void *userdata, struct DNSReply *reply);
|
|
||||||
|
|
||||||
static rb_dlink_list queries;
|
|
||||||
static struct ev_entry *timeout_ev;
|
static struct ev_entry *timeout_ev;
|
||||||
static int rdns_timeout = 30;
|
static EVH timeout_dns_queries_event;
|
||||||
|
static int rdns_timeout = 15;
|
||||||
|
|
||||||
|
static void
|
||||||
bool client_dns_init(void)
|
dns_answer_callback(const char *res, bool status, query_type type, void *data)
|
||||||
{
|
{
|
||||||
timeout_ev = rb_event_addish("timeout_dns_queries_event", timeout_dns_queries_event, NULL, 5);
|
struct auth_client *auth = data;
|
||||||
return (timeout_ev != NULL);
|
struct user_query *query = auth->data[PROVIDER_RDNS];
|
||||||
|
|
||||||
|
if(query == NULL || res == NULL || status == false)
|
||||||
|
client_fail(auth, REPORT_FAIL);
|
||||||
|
else if(strlen(res) > HOSTLEN)
|
||||||
|
client_fail(auth, REPORT_TOOLONG);
|
||||||
|
else
|
||||||
|
{
|
||||||
|
rb_strlcpy(auth->hostname, res, HOSTLEN + 1);
|
||||||
|
client_success(auth);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void client_dns_destroy(void)
|
/* Timeout outstanding queries */
|
||||||
|
static void
|
||||||
|
timeout_dns_queries_event(void *notused)
|
||||||
{
|
{
|
||||||
rb_dlink_node *ptr, *nptr;
|
struct auth_client *auth;
|
||||||
struct dns_query *query;
|
rb_dictionary_iter iter;
|
||||||
|
|
||||||
RB_DLINK_FOREACH_SAFE(ptr, nptr, queries.head)
|
RB_DICTIONARY_FOREACH(auth, &iter, auth_clients)
|
||||||
{
|
{
|
||||||
client_fail(ptr->data, REPORT_FAIL);
|
struct user_query *query = auth->data[PROVIDER_RDNS];
|
||||||
rb_dlinkDelete(ptr, &queries);
|
|
||||||
rb_free(ptr);
|
|
||||||
}
|
|
||||||
|
|
||||||
rb_event_delete(timeout_ev);
|
if(query != NULL && query->timeout < rb_current_time())
|
||||||
}
|
|
||||||
|
|
||||||
bool client_dns_start(struct auth_client *auth)
|
|
||||||
{
|
{
|
||||||
struct dns_query *query = rb_malloc(sizeof(struct dns_query));
|
client_fail(auth, REPORT_FAIL);
|
||||||
|
|
||||||
query->auth = auth;
|
|
||||||
query->timeout = rb_current_time() + rdns_timeout;
|
|
||||||
|
|
||||||
query->query.ptr = query;
|
|
||||||
query->query.callback = get_dns_answer;
|
|
||||||
|
|
||||||
gethost_byaddr(&auth->c_addr, &query->query);
|
|
||||||
notice_client(auth, messages[REPORT_LOOKUP]);
|
|
||||||
set_provider(auth, PROVIDER_RDNS);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void client_dns_cancel(struct auth_client *auth)
|
|
||||||
{
|
|
||||||
rb_dlink_node *ptr;
|
|
||||||
|
|
||||||
/* Bah, the stupid DNS resolver code doesn't have a cancellation
|
|
||||||
* func... */
|
|
||||||
RB_DLINK_FOREACH(ptr, queries.head)
|
|
||||||
{
|
|
||||||
struct dns_query *query = ptr->data;
|
|
||||||
|
|
||||||
if(query->auth == auth)
|
|
||||||
{
|
|
||||||
/* This will get cleaned up later by the DNS stuff */
|
|
||||||
client_fail(query, REPORT_FAIL);
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
get_dns_answer(void *userdata, struct DNSReply *reply)
|
client_fail(struct auth_client *auth, dns_message report)
|
||||||
{
|
{
|
||||||
struct dns_query *query = userdata;
|
struct user_query *query = auth->data[PROVIDER_RDNS];
|
||||||
struct auth_client *auth = query->auth;
|
|
||||||
rb_dlink_node *ptr, *nptr;
|
|
||||||
bool fail = false;
|
|
||||||
dns_message response;
|
|
||||||
|
|
||||||
if(reply == NULL || auth == NULL)
|
if(query == NULL)
|
||||||
{
|
return;
|
||||||
response = REPORT_FAIL;
|
|
||||||
fail = true;
|
|
||||||
goto cleanup;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(!sockcmp(&auth->c_addr, &reply->addr, GET_SS_FAMILY(&auth->c_addr)))
|
rb_strlcpy(auth->hostname, "*", sizeof(auth->hostname));
|
||||||
{
|
|
||||||
response = REPORT_FAIL;
|
|
||||||
fail = true;
|
|
||||||
goto cleanup;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(strlen(reply->h_name) > HOSTLEN)
|
notice_client(auth->cid, messages[report]);
|
||||||
{
|
cancel_query(query->query);
|
||||||
/* Ah well. */
|
|
||||||
response = REPORT_TOOLONG;
|
|
||||||
fail = true;
|
|
||||||
goto cleanup;
|
|
||||||
}
|
|
||||||
|
|
||||||
rb_strlcpy(auth->hostname, reply->h_name, HOSTLEN + 1);
|
|
||||||
|
|
||||||
cleanup:
|
|
||||||
/* Clean us up off the pending queries list */
|
|
||||||
RB_DLINK_FOREACH_SAFE(ptr, nptr, queries.head)
|
|
||||||
{
|
|
||||||
struct dns_query *query_l = ptr->data;
|
|
||||||
|
|
||||||
if(query == query_l)
|
|
||||||
{
|
|
||||||
/* Found */
|
|
||||||
if(fail)
|
|
||||||
client_fail(query, response);
|
|
||||||
else
|
|
||||||
client_success(query);
|
|
||||||
|
|
||||||
rb_dlinkDelete(ptr, &queries);
|
|
||||||
rb_free(query);
|
rb_free(query);
|
||||||
|
auth->data[PROVIDER_RDNS] = NULL;
|
||||||
|
|
||||||
|
provider_done(auth, PROVIDER_RDNS);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
client_success(struct auth_client *auth)
|
||||||
|
{
|
||||||
|
struct user_query *query = auth->data[PROVIDER_RDNS];
|
||||||
|
|
||||||
|
notice_client(auth->cid, messages[REPORT_FOUND]);
|
||||||
|
cancel_query(query->query);
|
||||||
|
|
||||||
|
rb_free(query);
|
||||||
|
auth->data[PROVIDER_RDNS] = NULL;
|
||||||
|
|
||||||
|
provider_done(auth, PROVIDER_RDNS);
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool
|
||||||
|
rdns_init(void)
|
||||||
|
{
|
||||||
|
timeout_ev = rb_event_addish("timeout_dns_queries_event", timeout_dns_queries_event, NULL, 1);
|
||||||
|
return (timeout_ev != NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
rdns_destroy(void)
|
||||||
|
{
|
||||||
|
struct auth_client *auth;
|
||||||
|
rb_dictionary_iter iter;
|
||||||
|
|
||||||
|
RB_DICTIONARY_FOREACH(auth, &iter, auth_clients)
|
||||||
|
{
|
||||||
|
if(auth->data[PROVIDER_RDNS] != NULL)
|
||||||
|
client_fail(auth, REPORT_FAIL);
|
||||||
|
}
|
||||||
|
|
||||||
|
rb_event_delete(timeout_ev);
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool
|
||||||
|
rdns_start(struct auth_client *auth)
|
||||||
|
{
|
||||||
|
struct user_query *query = rb_malloc(sizeof(struct user_query));
|
||||||
|
|
||||||
|
query->timeout = rb_current_time() + rdns_timeout;
|
||||||
|
|
||||||
|
auth->data[PROVIDER_RDNS] = query;
|
||||||
|
|
||||||
|
query->query = lookup_hostname(auth->c_ip, dns_answer_callback, auth);
|
||||||
|
|
||||||
|
notice_client(auth->cid, messages[REPORT_LOOKUP]);
|
||||||
|
set_provider_on(auth, PROVIDER_RDNS);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
rdns_cancel(struct auth_client *auth)
|
||||||
|
{
|
||||||
|
struct user_query *query = auth->data[PROVIDER_RDNS];
|
||||||
|
|
||||||
|
if(query != NULL)
|
||||||
|
client_fail(auth, REPORT_FAIL);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
add_conf_dns_timeout(const char *key, int parc, const char **parv)
|
||||||
|
{
|
||||||
|
int timeout = atoi(parv[0]);
|
||||||
|
|
||||||
|
if(timeout < 0)
|
||||||
|
{
|
||||||
|
warn_opers(L_CRIT, "BUG: DNS timeout < 0 (value: %d)", timeout);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
rdns_timeout = timeout;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Timeout outstanding queries */
|
struct auth_opts_handler rdns_options[] =
|
||||||
static void timeout_dns_queries_event(void *notused)
|
|
||||||
{
|
{
|
||||||
rb_dlink_node *ptr;
|
{ "dns_timeout", 1, add_conf_dns_timeout },
|
||||||
|
{ NULL, 0, NULL },
|
||||||
/* NOTE - we do not delete queries from the list from a timeout, when
|
};
|
||||||
* the query times out later it will be deleted.
|
|
||||||
*/
|
|
||||||
RB_DLINK_FOREACH(ptr, queries.head)
|
|
||||||
{
|
|
||||||
struct dns_query *query = ptr->data;
|
|
||||||
|
|
||||||
if(query->auth && query->timeout < rb_current_time())
|
|
||||||
{
|
|
||||||
client_fail(query, REPORT_FAIL);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void client_fail(struct dns_query *query, dns_message report)
|
|
||||||
{
|
|
||||||
struct auth_client *auth = query->auth;
|
|
||||||
|
|
||||||
if(auth)
|
|
||||||
{
|
|
||||||
rb_strlcpy(auth->hostname, "*", sizeof(auth->hostname));
|
|
||||||
notice_client(auth, messages[report]);
|
|
||||||
provider_done(auth, PROVIDER_RDNS);
|
|
||||||
query->auth = NULL;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void client_success(struct dns_query *query)
|
|
||||||
{
|
|
||||||
struct auth_client *auth = query->auth;
|
|
||||||
|
|
||||||
if(auth)
|
|
||||||
{
|
|
||||||
notice_client(auth, messages[REPORT_FOUND]);
|
|
||||||
provider_done(auth, PROVIDER_RDNS);
|
|
||||||
query->auth = NULL;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
struct auth_provider rdns_provider =
|
struct auth_provider rdns_provider =
|
||||||
{
|
{
|
||||||
.id = PROVIDER_RDNS,
|
.id = PROVIDER_RDNS,
|
||||||
.init = client_dns_init,
|
.init = rdns_init,
|
||||||
.destroy = client_dns_destroy,
|
.destroy = rdns_destroy,
|
||||||
.start = client_dns_start,
|
.start = rdns_start,
|
||||||
.cancel = client_dns_cancel,
|
.cancel = rdns_cancel,
|
||||||
.completed = NULL,
|
.completed = NULL,
|
||||||
|
.opt_handlers = rdns_options,
|
||||||
};
|
};
|
||||||
|
|
142
authd/res.c
142
authd/res.c
|
@ -98,7 +98,6 @@ static int check_question(struct reslist *request, HEADER * header, char *buf, c
|
||||||
static int proc_answer(struct reslist *request, HEADER * header, char *, char *);
|
static int proc_answer(struct reslist *request, HEADER * header, char *, char *);
|
||||||
static struct reslist *find_id(int id);
|
static struct reslist *find_id(int id);
|
||||||
static struct DNSReply *make_dnsreply(struct reslist *request);
|
static struct DNSReply *make_dnsreply(struct reslist *request);
|
||||||
static int generate_random_port(void);
|
|
||||||
static uint16_t generate_random_id(void);
|
static uint16_t generate_random_id(void);
|
||||||
|
|
||||||
#ifdef RES_MIN
|
#ifdef RES_MIN
|
||||||
|
@ -107,55 +106,6 @@ static uint16_t generate_random_id(void);
|
||||||
|
|
||||||
#define RES_MIN(a, b) ((a) < (b) ? (a) : (b))
|
#define RES_MIN(a, b) ((a) < (b) ? (a) : (b))
|
||||||
|
|
||||||
static rb_fde_t *
|
|
||||||
random_socket(int family)
|
|
||||||
{
|
|
||||||
rb_fde_t *F;
|
|
||||||
int nport;
|
|
||||||
int i;
|
|
||||||
rb_socklen_t len;
|
|
||||||
struct rb_sockaddr_storage sockaddr;
|
|
||||||
F = rb_socket(family, SOCK_DGRAM, 0, "UDP resolver socket");
|
|
||||||
if(F == NULL)
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
memset(&sockaddr, 0, sizeof(sockaddr));
|
|
||||||
|
|
||||||
SET_SS_FAMILY(&sockaddr, family);
|
|
||||||
|
|
||||||
#ifdef RB_IPV6
|
|
||||||
if(family == AF_INET6)
|
|
||||||
{
|
|
||||||
struct sockaddr_in6 *in6 = (struct sockaddr_in6 *)&sockaddr;
|
|
||||||
memcpy(&in6->sin6_addr, &ipv6_addr, sizeof(struct in6_addr));
|
|
||||||
len = (rb_socklen_t) sizeof(struct sockaddr_in6);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
#endif
|
|
||||||
{
|
|
||||||
struct sockaddr_in *in = (struct sockaddr_in *)&sockaddr;
|
|
||||||
in->sin_addr.s_addr = ipv4_addr.s_addr;
|
|
||||||
len = (rb_socklen_t) sizeof(struct sockaddr_in);
|
|
||||||
}
|
|
||||||
|
|
||||||
for(i = 0; i < 10; i++)
|
|
||||||
{
|
|
||||||
nport = htons(generate_random_port());
|
|
||||||
|
|
||||||
if(family == AF_INET)
|
|
||||||
((struct sockaddr_in *)&sockaddr)->sin_port = nport;
|
|
||||||
#ifdef RB_IPV6
|
|
||||||
else
|
|
||||||
((struct sockaddr_in6 *)&sockaddr)->sin6_port = nport;
|
|
||||||
|
|
||||||
#endif
|
|
||||||
if(bind(rb_get_fd(F), (struct sockaddr *)&sockaddr, len) == 0)
|
|
||||||
return F;
|
|
||||||
}
|
|
||||||
rb_close(F);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* int
|
* int
|
||||||
* res_ourserver(inp)
|
* res_ourserver(inp)
|
||||||
|
@ -167,7 +117,8 @@ random_socket(int family)
|
||||||
* revised for ircd, cryogen(stu) may03
|
* revised for ircd, cryogen(stu) may03
|
||||||
* slightly modified for charybdis, mr_flea oct12
|
* slightly modified for charybdis, mr_flea oct12
|
||||||
*/
|
*/
|
||||||
static int res_ourserver(const struct rb_sockaddr_storage *inp)
|
static int
|
||||||
|
res_ourserver(const struct rb_sockaddr_storage *inp)
|
||||||
{
|
{
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
const struct sockaddr_in6 *v6;
|
const struct sockaddr_in6 *v6;
|
||||||
|
@ -180,46 +131,40 @@ static int res_ourserver(const struct rb_sockaddr_storage *inp)
|
||||||
for(ns = 0; ns < irc_nscount; ns++)
|
for(ns = 0; ns < irc_nscount; ns++)
|
||||||
{
|
{
|
||||||
const struct rb_sockaddr_storage *srv = &irc_nsaddr_list[ns];
|
const struct rb_sockaddr_storage *srv = &irc_nsaddr_list[ns];
|
||||||
|
|
||||||
if (srv->ss_family != inp->ss_family)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
v6 = (const struct sockaddr_in6 *)srv;
|
v6 = (const struct sockaddr_in6 *)srv;
|
||||||
#endif
|
#endif
|
||||||
v4 = (const struct sockaddr_in *)srv;
|
v4 = (const struct sockaddr_in *)srv;
|
||||||
|
|
||||||
/* could probably just memcmp(srv, inp, srv.ss_len) here
|
/* could probably just memcmp(srv, inp, srv.ss_len) here
|
||||||
* but we'll err on the side of caution - stu
|
* but we'll air on the side of caution - stu
|
||||||
*/
|
*/
|
||||||
switch (srv->ss_family)
|
switch (GET_SS_FAMILY(srv))
|
||||||
{
|
{
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
case AF_INET6:
|
case AF_INET6:
|
||||||
|
if(GET_SS_FAMILY(srv) == GET_SS_FAMILY(inp))
|
||||||
if(v6->sin6_port == v6in->sin6_port)
|
if(v6->sin6_port == v6in->sin6_port)
|
||||||
if((memcmp(&v6->sin6_addr.s6_addr, &v6in->sin6_addr.s6_addr,
|
if((memcmp(&v6->sin6_addr.s6_addr, &v6in->sin6_addr.s6_addr,
|
||||||
sizeof(struct in6_addr)) == 0) ||
|
sizeof(struct in6_addr)) == 0) ||
|
||||||
(memcmp(&v6->sin6_addr.s6_addr, &in6addr_any,
|
(memcmp(&v6->sin6_addr.s6_addr, &in6addr_any,
|
||||||
sizeof(struct in6_addr)) == 0))
|
sizeof(struct in6_addr)) == 0))
|
||||||
{
|
return 1;
|
||||||
return ns;
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
#endif
|
#endif
|
||||||
case AF_INET:
|
case AF_INET:
|
||||||
|
if(GET_SS_FAMILY(srv) == GET_SS_FAMILY(inp))
|
||||||
if(v4->sin_port == v4in->sin_port)
|
if(v4->sin_port == v4in->sin_port)
|
||||||
if((v4->sin_addr.s_addr == INADDR_ANY)
|
if((v4->sin_addr.s_addr == INADDR_ANY)
|
||||||
|| (v4->sin_addr.s_addr == v4in->sin_addr.s_addr))
|
|| (v4->sin_addr.s_addr == v4in->sin_addr.s_addr))
|
||||||
{
|
return 1;
|
||||||
return ns;
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return -1;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -280,7 +225,7 @@ static void start_resolver(void)
|
||||||
|
|
||||||
if (res_fd == NULL)
|
if (res_fd == NULL)
|
||||||
{
|
{
|
||||||
if ((res_fd = rb_socket(irc_nsaddr_list[0].ss_family, SOCK_DGRAM, 0,
|
if ((res_fd = rb_socket(GET_SS_FAMILY(&irc_nsaddr_list[0]), SOCK_DGRAM, 0,
|
||||||
"UDP resolver socket")) == NULL)
|
"UDP resolver socket")) == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
@ -472,20 +417,6 @@ generate_random_id(void)
|
||||||
return id;
|
return id;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int
|
|
||||||
generate_random_port(void)
|
|
||||||
{
|
|
||||||
uint16_t port;
|
|
||||||
|
|
||||||
while(1)
|
|
||||||
{
|
|
||||||
rb_get_random(&port, sizeof(port));
|
|
||||||
if(port > 1024)
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
return (int)port;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* gethost_byname_type - get host address from name, adding domain if needed
|
* gethost_byname_type - get host address from name, adding domain if needed
|
||||||
*/
|
*/
|
||||||
|
@ -534,37 +465,31 @@ static void do_query_name(struct DNSQuery *query, const char *name, struct resli
|
||||||
query_name(request);
|
query_name(request);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/* Build an rDNS style query - if suffix is NULL, use the appropriate .arpa zone */
|
||||||
* do_query_number - Use this to do reverse IP# lookups.
|
void build_rdns(char *buf, size_t size, const struct rb_sockaddr_storage *addr, const char *suffix)
|
||||||
*/
|
|
||||||
static void do_query_number(struct DNSQuery *query, const struct rb_sockaddr_storage *addr,
|
|
||||||
struct reslist *request)
|
|
||||||
{
|
{
|
||||||
const unsigned char *cp;
|
const unsigned char *cp;
|
||||||
|
|
||||||
if (request == NULL)
|
if (GET_SS_FAMILY(addr) == AF_INET)
|
||||||
{
|
|
||||||
request = make_request(query);
|
|
||||||
memcpy(&request->addr, addr, sizeof(struct rb_sockaddr_storage));
|
|
||||||
request->name = (char *)rb_malloc(IRCD_RES_HOSTLEN + 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (addr->ss_family == AF_INET)
|
|
||||||
{
|
{
|
||||||
const struct sockaddr_in *v4 = (const struct sockaddr_in *)addr;
|
const struct sockaddr_in *v4 = (const struct sockaddr_in *)addr;
|
||||||
cp = (const unsigned char *)&v4->sin_addr.s_addr;
|
cp = (const unsigned char *)&v4->sin_addr.s_addr;
|
||||||
|
|
||||||
sprintf(request->queryname, "%u.%u.%u.%u.in-addr.arpa", (unsigned int)(cp[3]),
|
(void) snprintf(buf, size, "%u.%u.%u.%u.%s",
|
||||||
(unsigned int)(cp[2]), (unsigned int)(cp[1]), (unsigned int)(cp[0]));
|
(unsigned int)(cp[3]),
|
||||||
|
(unsigned int)(cp[2]),
|
||||||
|
(unsigned int)(cp[1]),
|
||||||
|
(unsigned int)(cp[0]),
|
||||||
|
suffix == NULL ? "in-addr.arpa" : suffix);
|
||||||
}
|
}
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
else if (addr->ss_family == AF_INET6)
|
else if (GET_SS_FAMILY(addr) == AF_INET6)
|
||||||
{
|
{
|
||||||
const struct sockaddr_in6 *v6 = (const struct sockaddr_in6 *)addr;
|
const struct sockaddr_in6 *v6 = (const struct sockaddr_in6 *)addr;
|
||||||
cp = (const unsigned char *)&v6->sin6_addr.s6_addr;
|
cp = (const unsigned char *)&v6->sin6_addr.s6_addr;
|
||||||
|
|
||||||
(void)sprintf(request->queryname, "%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x."
|
(void) snprintf(buf, size,
|
||||||
"%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.%x.ip6.arpa",
|
"%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.%s",
|
||||||
(unsigned int)(cp[15] & 0xf), (unsigned int)(cp[15] >> 4),
|
(unsigned int)(cp[15] & 0xf), (unsigned int)(cp[15] >> 4),
|
||||||
(unsigned int)(cp[14] & 0xf), (unsigned int)(cp[14] >> 4),
|
(unsigned int)(cp[14] & 0xf), (unsigned int)(cp[14] >> 4),
|
||||||
(unsigned int)(cp[13] & 0xf), (unsigned int)(cp[13] >> 4),
|
(unsigned int)(cp[13] & 0xf), (unsigned int)(cp[13] >> 4),
|
||||||
|
@ -580,9 +505,28 @@ static void do_query_number(struct DNSQuery *query, const struct rb_sockaddr_sto
|
||||||
(unsigned int)(cp[3] & 0xf), (unsigned int)(cp[3] >> 4),
|
(unsigned int)(cp[3] & 0xf), (unsigned int)(cp[3] >> 4),
|
||||||
(unsigned int)(cp[2] & 0xf), (unsigned int)(cp[2] >> 4),
|
(unsigned int)(cp[2] & 0xf), (unsigned int)(cp[2] >> 4),
|
||||||
(unsigned int)(cp[1] & 0xf), (unsigned int)(cp[1] >> 4),
|
(unsigned int)(cp[1] & 0xf), (unsigned int)(cp[1] >> 4),
|
||||||
(unsigned int)(cp[0] & 0xf), (unsigned int)(cp[0] >> 4));
|
(unsigned int)(cp[0] & 0xf), (unsigned int)(cp[0] >> 4),
|
||||||
|
suffix == NULL ? "ip6.arpa" : suffix);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* do_query_number - Use this to do reverse IP# lookups.
|
||||||
|
*/
|
||||||
|
static void do_query_number(struct DNSQuery *query, const struct rb_sockaddr_storage *addr,
|
||||||
|
struct reslist *request)
|
||||||
|
{
|
||||||
|
const unsigned char *cp;
|
||||||
|
|
||||||
|
if (request == NULL)
|
||||||
|
{
|
||||||
|
request = make_request(query);
|
||||||
|
memcpy(&request->addr, addr, sizeof(struct rb_sockaddr_storage));
|
||||||
|
request->name = (char *)rb_malloc(IRCD_RES_HOSTLEN + 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
build_rdns(request->queryname, IRCD_RES_HOSTLEN + 1, addr, NULL);
|
||||||
|
|
||||||
request->type = T_PTR;
|
request->type = T_PTR;
|
||||||
query_name(request);
|
query_name(request);
|
||||||
|
@ -918,7 +862,7 @@ static int res_read_single_reply(rb_fde_t *F, void *data)
|
||||||
* ip#.
|
* ip#.
|
||||||
*/
|
*/
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
if (request->addr.ss_family == AF_INET6)
|
if (GET_SS_FAMILY(&request->addr) == AF_INET6)
|
||||||
gethost_byname_type_fqdn(request->name, request->query, T_AAAA);
|
gethost_byname_type_fqdn(request->name, request->query, T_AAAA);
|
||||||
else
|
else
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -32,5 +32,6 @@ extern void init_resolver(void);
|
||||||
extern void restart_resolver(void);
|
extern void restart_resolver(void);
|
||||||
extern void gethost_byname_type(const char *, struct DNSQuery *, int);
|
extern void gethost_byname_type(const char *, struct DNSQuery *, int);
|
||||||
extern void gethost_byaddr(const struct rb_sockaddr_storage *, struct DNSQuery *);
|
extern void gethost_byaddr(const struct rb_sockaddr_storage *, struct DNSQuery *);
|
||||||
|
extern void build_rdns(char *, size_t, const struct rb_sockaddr_storage *, const char *);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -76,9 +76,27 @@
|
||||||
* - Dianora
|
* - Dianora
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include <rb_lib.h>
|
||||||
|
|
||||||
|
#ifndef _WIN32
|
||||||
|
|
||||||
|
#include <netdb.h>
|
||||||
|
|
||||||
|
typedef struct addrinfo rb_addrinfo;
|
||||||
|
|
||||||
|
#else
|
||||||
|
#include "getaddrinfo.h"
|
||||||
|
#include "getnameinfo.h"
|
||||||
|
#define getaddrinfo rb_getaddrinfo
|
||||||
|
#define getnameinfo rb_getnameinfo
|
||||||
|
#define freeaddrinfo rb_freeaddrinfo
|
||||||
|
|
||||||
|
extern const char * get_windows_nameservers(void);
|
||||||
|
typedef struct rb_addrinfo rb_addrinfo;
|
||||||
|
#endif
|
||||||
|
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "ircd_defs.h"
|
#include "ircd_defs.h"
|
||||||
#include "common.h"
|
|
||||||
#include "ircd.h"
|
#include "ircd.h"
|
||||||
#include "res.h"
|
#include "res.h"
|
||||||
#include "reslib.h"
|
#include "reslib.h"
|
||||||
|
@ -112,7 +130,12 @@ static const char digitvalue[256] = {
|
||||||
-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, /*256*/
|
-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, /*256*/
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#ifndef _WIN32
|
||||||
static int parse_resvconf(void);
|
static int parse_resvconf(void);
|
||||||
|
#else
|
||||||
|
static void parse_windows_resolvers(void);
|
||||||
|
#endif
|
||||||
|
|
||||||
static void add_nameserver(const char *);
|
static void add_nameserver(const char *);
|
||||||
|
|
||||||
static const char digits[] = "0123456789";
|
static const char digits[] = "0123456789";
|
||||||
|
@ -139,12 +162,31 @@ int
|
||||||
irc_res_init(void)
|
irc_res_init(void)
|
||||||
{
|
{
|
||||||
irc_nscount = 0;
|
irc_nscount = 0;
|
||||||
|
#ifndef _WIN32
|
||||||
parse_resvconf();
|
parse_resvconf();
|
||||||
|
#else
|
||||||
|
parse_windows_resolvers();
|
||||||
|
#endif
|
||||||
if (irc_nscount == 0)
|
if (irc_nscount == 0)
|
||||||
add_nameserver("127.0.0.1");
|
add_nameserver("127.0.0.1");
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
static void
|
||||||
|
parse_windows_resolvers(void)
|
||||||
|
{
|
||||||
|
const char *ns = get_windows_nameservers();
|
||||||
|
char *server;
|
||||||
|
char *p;
|
||||||
|
char *buf = rb_strdup(ns);
|
||||||
|
for(server = rb_strtok_r(buf, " ", &p); server != NULL;server = rb_strtok_r(NULL, " ", &p))
|
||||||
|
{
|
||||||
|
add_nameserver(server);
|
||||||
|
}
|
||||||
|
rb_free(buf);
|
||||||
|
}
|
||||||
|
#else
|
||||||
/* parse_resvconf()
|
/* parse_resvconf()
|
||||||
*
|
*
|
||||||
* inputs - NONE
|
* inputs - NONE
|
||||||
|
@ -210,6 +252,7 @@ parse_resvconf(void)
|
||||||
fclose(file);
|
fclose(file);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
/* add_nameserver()
|
/* add_nameserver()
|
||||||
*
|
*
|
||||||
|
@ -221,7 +264,7 @@ parse_resvconf(void)
|
||||||
static void
|
static void
|
||||||
add_nameserver(const char *arg)
|
add_nameserver(const char *arg)
|
||||||
{
|
{
|
||||||
struct addrinfo hints, *res;
|
rb_addrinfo hints, *res;
|
||||||
|
|
||||||
/* Done max number of nameservers? */
|
/* Done max number of nameservers? */
|
||||||
if (irc_nscount >= IRCD_MAXNS)
|
if (irc_nscount >= IRCD_MAXNS)
|
||||||
|
|
|
@ -78,24 +78,24 @@ typedef struct
|
||||||
*/
|
*/
|
||||||
#define IRC_NS_GET16(s, cp) { \
|
#define IRC_NS_GET16(s, cp) { \
|
||||||
const unsigned char *t_cp = (const unsigned char *)(cp); \
|
const unsigned char *t_cp = (const unsigned char *)(cp); \
|
||||||
(s) = ((u_int16_t)t_cp[0] << 8) \
|
(s) = ((uint16_t)t_cp[0] << 8) \
|
||||||
| ((u_int16_t)t_cp[1]) \
|
| ((uint16_t)t_cp[1]) \
|
||||||
; \
|
; \
|
||||||
(cp) += NS_INT16SZ; \
|
(cp) += NS_INT16SZ; \
|
||||||
}
|
}
|
||||||
|
|
||||||
#define IRC_NS_GET32(l, cp) { \
|
#define IRC_NS_GET32(l, cp) { \
|
||||||
const unsigned char *t_cp = (const unsigned char *)(cp); \
|
const unsigned char *t_cp = (const unsigned char *)(cp); \
|
||||||
(l) = ((u_int32_t)t_cp[0] << 24) \
|
(l) = ((uint32_t)t_cp[0] << 24) \
|
||||||
| ((u_int32_t)t_cp[1] << 16) \
|
| ((uint32_t)t_cp[1] << 16) \
|
||||||
| ((u_int32_t)t_cp[2] << 8) \
|
| ((uint32_t)t_cp[2] << 8) \
|
||||||
| ((u_int32_t)t_cp[3]) \
|
| ((uint32_t)t_cp[3]) \
|
||||||
; \
|
; \
|
||||||
(cp) += NS_INT32SZ; \
|
(cp) += NS_INT32SZ; \
|
||||||
}
|
}
|
||||||
|
|
||||||
#define IRC_NS_PUT16(s, cp) { \
|
#define IRC_NS_PUT16(s, cp) { \
|
||||||
u_int16_t t_s = (u_int16_t)(s); \
|
uint16_t t_s = (uint16_t)(s); \
|
||||||
unsigned char *t_cp = (unsigned char *)(cp); \
|
unsigned char *t_cp = (unsigned char *)(cp); \
|
||||||
*t_cp++ = t_s >> 8; \
|
*t_cp++ = t_s >> 8; \
|
||||||
*t_cp = t_s; \
|
*t_cp = t_s; \
|
||||||
|
@ -103,7 +103,7 @@ typedef struct
|
||||||
}
|
}
|
||||||
|
|
||||||
#define IRC_NS_PUT32(l, cp) { \
|
#define IRC_NS_PUT32(l, cp) { \
|
||||||
u_int32_t t_l = (u_int32_t)(l); \
|
uint32_t t_l = (uint32_t)(l); \
|
||||||
unsigned char *t_cp = (unsigned char *)(cp); \
|
unsigned char *t_cp = (unsigned char *)(cp); \
|
||||||
*t_cp++ = t_l >> 24; \
|
*t_cp++ = t_l >> 24; \
|
||||||
*t_cp++ = t_l >> 16; \
|
*t_cp++ = t_l >> 16; \
|
||||||
|
|
276
authd/reslist.c
Normal file
276
authd/reslist.c
Normal file
|
@ -0,0 +1,276 @@
|
||||||
|
/*
|
||||||
|
* reslist.c - get nameservers from windows *
|
||||||
|
*
|
||||||
|
* ircd-ratbox related changes are as follows
|
||||||
|
*
|
||||||
|
* Copyright (C) 2008 Aaron Sethman <androsyn@ratbox.org>
|
||||||
|
* Copyright (C) 2008-2012 ircd-ratbox development team
|
||||||
|
*
|
||||||
|
* pretty much all of this was yanked from c-ares ares_init.c here is the original
|
||||||
|
* header from there --
|
||||||
|
*
|
||||||
|
* Id: ares_init.c,v 1.72 2008-05-15 00:00:19 yangtse Exp $
|
||||||
|
* Copyright 1998 by the Massachusetts Institute of Technology.
|
||||||
|
* Copyright (C) 2007-2008 by Daniel Stenberg
|
||||||
|
*
|
||||||
|
* Permission to use, copy, modify, and distribute this
|
||||||
|
* software and its documentation for any purpose and without
|
||||||
|
* fee is hereby granted, provided that the above copyright
|
||||||
|
* notice appear in all copies and that both that copyright
|
||||||
|
* notice and this permission notice appear in supporting
|
||||||
|
* documentation, and that the name of M.I.T. not be used in
|
||||||
|
* advertising or publicity pertaining to distribution of the
|
||||||
|
* software without specific, written prior permission.
|
||||||
|
* M.I.T. makes no representations about the suitability of
|
||||||
|
* this software for any purpose. It is provided "as is"
|
||||||
|
* without express or implied warranty.
|
||||||
|
*
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
#include <rb_lib.h>
|
||||||
|
|
||||||
|
#include <windows.h>
|
||||||
|
#include <iphlpapi.h>
|
||||||
|
|
||||||
|
const char *get_windows_nameservers(void);
|
||||||
|
|
||||||
|
|
||||||
|
#define IS_NT() ((int)GetVersion() > 0)
|
||||||
|
#define WIN_NS_9X "System\\CurrentControlSet\\Services\\VxD\\MSTCP"
|
||||||
|
#define WIN_NS_NT_KEY "System\\CurrentControlSet\\Services\\Tcpip\\Parameters"
|
||||||
|
#define NAMESERVER "NameServer"
|
||||||
|
#define DHCPNAMESERVER "DhcpNameServer"
|
||||||
|
#define DATABASEPATH "DatabasePath"
|
||||||
|
#define WIN_PATH_HOSTS "\\hosts"
|
||||||
|
|
||||||
|
static int
|
||||||
|
get_iphlpapi_dns_info(char *ret_buf, size_t ret_size)
|
||||||
|
{
|
||||||
|
FIXED_INFO *fi = alloca(sizeof(*fi));
|
||||||
|
DWORD size = sizeof(*fi);
|
||||||
|
typedef DWORD(WINAPI * get_net_param_func) (FIXED_INFO *, DWORD *);
|
||||||
|
get_net_param_func xxGetNetworkParams; /* available only on Win-98/2000+ */
|
||||||
|
HMODULE handle;
|
||||||
|
IP_ADDR_STRING *ipAddr;
|
||||||
|
int i, count = 0;
|
||||||
|
int debug = 0;
|
||||||
|
size_t ip_size = sizeof("255.255.255.255,") - 1;
|
||||||
|
size_t left = ret_size;
|
||||||
|
char *ret = ret_buf;
|
||||||
|
HRESULT res;
|
||||||
|
|
||||||
|
if(!fi)
|
||||||
|
return (0);
|
||||||
|
|
||||||
|
handle = LoadLibrary("iphlpapi.dll");
|
||||||
|
if(!handle)
|
||||||
|
return (0);
|
||||||
|
|
||||||
|
xxGetNetworkParams = (get_net_param_func) GetProcAddress(handle, "GetNetworkParams");
|
||||||
|
if(!xxGetNetworkParams)
|
||||||
|
goto quit;
|
||||||
|
|
||||||
|
res = (*xxGetNetworkParams) (fi, &size);
|
||||||
|
if((res != ERROR_BUFFER_OVERFLOW) && (res != ERROR_SUCCESS))
|
||||||
|
goto quit;
|
||||||
|
|
||||||
|
fi = alloca(size);
|
||||||
|
if(!fi || (*xxGetNetworkParams) (fi, &size) != ERROR_SUCCESS)
|
||||||
|
goto quit;
|
||||||
|
|
||||||
|
if(debug)
|
||||||
|
{
|
||||||
|
printf("Host Name: %s\n", fi->HostName);
|
||||||
|
printf("Domain Name: %s\n", fi->DomainName);
|
||||||
|
printf("DNS Servers:\n" " %s (primary)\n", fi->DnsServerList.IpAddress.String);
|
||||||
|
}
|
||||||
|
if(strlen(fi->DnsServerList.IpAddress.String) > 0 &&
|
||||||
|
inet_addr(fi->DnsServerList.IpAddress.String) != INADDR_NONE && left > ip_size)
|
||||||
|
{
|
||||||
|
ret += sprintf(ret, "%s,", fi->DnsServerList.IpAddress.String);
|
||||||
|
left -= ret - ret_buf;
|
||||||
|
count++;
|
||||||
|
}
|
||||||
|
|
||||||
|
for(i = 0, ipAddr = fi->DnsServerList.Next; ipAddr && left > ip_size;
|
||||||
|
ipAddr = ipAddr->Next, i++)
|
||||||
|
{
|
||||||
|
if(inet_addr(ipAddr->IpAddress.String) != INADDR_NONE)
|
||||||
|
{
|
||||||
|
ret += sprintf(ret, "%s,", ipAddr->IpAddress.String);
|
||||||
|
left -= ret - ret_buf;
|
||||||
|
count++;
|
||||||
|
}
|
||||||
|
if(debug)
|
||||||
|
printf(" %s (secondary %d)\n", ipAddr->IpAddress.String, i + 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
quit:
|
||||||
|
if(handle)
|
||||||
|
FreeLibrary(handle);
|
||||||
|
|
||||||
|
if(debug && left <= ip_size)
|
||||||
|
printf("Too many nameservers. Truncating to %d addressess", count);
|
||||||
|
if(ret > ret_buf)
|
||||||
|
ret[-1] = '\0';
|
||||||
|
return (count);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Warning: returns a dynamically allocated buffer, the user MUST
|
||||||
|
* use free() / rb_free() if the function returns 1
|
||||||
|
*/
|
||||||
|
static int
|
||||||
|
get_res_nt(HKEY hKey, const char *subkey, char **obuf)
|
||||||
|
{
|
||||||
|
/* Test for the size we need */
|
||||||
|
DWORD size = 0;
|
||||||
|
int result;
|
||||||
|
|
||||||
|
result = RegQueryValueEx(hKey, subkey, 0, NULL, NULL, &size);
|
||||||
|
if((result != ERROR_SUCCESS && result != ERROR_MORE_DATA) || !size)
|
||||||
|
return 0;
|
||||||
|
*obuf = rb_malloc(size + 1);
|
||||||
|
if(!*obuf)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
if(RegQueryValueEx(hKey, subkey, 0, NULL, (LPBYTE) * obuf, &size) != ERROR_SUCCESS)
|
||||||
|
{
|
||||||
|
rb_free(*obuf);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
if(size == 1)
|
||||||
|
{
|
||||||
|
rb_free(*obuf);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
get_res_interfaces_nt(HKEY hKey, const char *subkey, char **obuf)
|
||||||
|
{
|
||||||
|
char enumbuf[39]; /* GUIDs are 38 chars + 1 for NULL */
|
||||||
|
DWORD enum_size = 39;
|
||||||
|
int idx = 0;
|
||||||
|
HKEY hVal;
|
||||||
|
|
||||||
|
while(RegEnumKeyEx(hKey, idx++, enumbuf, &enum_size, 0,
|
||||||
|
NULL, NULL, NULL) != ERROR_NO_MORE_ITEMS)
|
||||||
|
{
|
||||||
|
int rc;
|
||||||
|
|
||||||
|
enum_size = 39;
|
||||||
|
if(RegOpenKeyEx(hKey, enumbuf, 0, KEY_QUERY_VALUE, &hVal) != ERROR_SUCCESS)
|
||||||
|
continue;
|
||||||
|
rc = get_res_nt(hVal, subkey, obuf);
|
||||||
|
RegCloseKey(hVal);
|
||||||
|
if(rc)
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
const char *
|
||||||
|
get_windows_nameservers(void)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
NameServer info via IPHLPAPI (IP helper API):
|
||||||
|
GetNetworkParams() should be the trusted source for this.
|
||||||
|
Available in Win-98/2000 and later. If that fail, fall-back to
|
||||||
|
registry information.
|
||||||
|
|
||||||
|
NameServer Registry:
|
||||||
|
|
||||||
|
On Windows 9X, the DNS server can be found in:
|
||||||
|
HKEY_LOCAL_MACHINE\System\CurrentControlSet\Services\VxD\MSTCP\NameServer
|
||||||
|
|
||||||
|
On Windows NT/2000/XP/2003:
|
||||||
|
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters\NameServer
|
||||||
|
or
|
||||||
|
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters\DhcpNameServer
|
||||||
|
or
|
||||||
|
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters\{AdapterID}\
|
||||||
|
NameServer
|
||||||
|
or
|
||||||
|
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters\{AdapterID}\
|
||||||
|
DhcpNameServer
|
||||||
|
*/
|
||||||
|
static char namelist[512];
|
||||||
|
HKEY mykey;
|
||||||
|
HKEY subkey;
|
||||||
|
DWORD data_type;
|
||||||
|
DWORD bytes;
|
||||||
|
DWORD result;
|
||||||
|
char *line = NULL;
|
||||||
|
memset(&namelist, 0, sizeof(namelist));
|
||||||
|
if(get_iphlpapi_dns_info(namelist, sizeof(namelist)) > 0)
|
||||||
|
{
|
||||||
|
return namelist;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(IS_NT())
|
||||||
|
{
|
||||||
|
if(RegOpenKeyEx(HKEY_LOCAL_MACHINE, WIN_NS_NT_KEY, 0,
|
||||||
|
KEY_READ, &mykey) == ERROR_SUCCESS)
|
||||||
|
{
|
||||||
|
RegOpenKeyEx(mykey, "Interfaces", 0,
|
||||||
|
KEY_QUERY_VALUE | KEY_ENUMERATE_SUB_KEYS, &subkey);
|
||||||
|
if(get_res_nt(mykey, NAMESERVER, &line))
|
||||||
|
{
|
||||||
|
rb_strlcpy(namelist, line, sizeof(namelist));
|
||||||
|
return namelist;
|
||||||
|
}
|
||||||
|
else if(get_res_nt(mykey, DHCPNAMESERVER, &line))
|
||||||
|
{
|
||||||
|
rb_strlcpy(namelist, line, sizeof(namelist));
|
||||||
|
rb_free(line);
|
||||||
|
}
|
||||||
|
/* Try the interfaces */
|
||||||
|
else if(get_res_interfaces_nt(subkey, NAMESERVER, &line))
|
||||||
|
{
|
||||||
|
rb_strlcpy(namelist, line, sizeof(namelist));
|
||||||
|
rb_free(line);
|
||||||
|
}
|
||||||
|
else if(get_res_interfaces_nt(subkey, DHCPNAMESERVER, &line))
|
||||||
|
{
|
||||||
|
rb_strlcpy(namelist, line, sizeof(namelist));
|
||||||
|
rb_free(line);
|
||||||
|
}
|
||||||
|
RegCloseKey(subkey);
|
||||||
|
RegCloseKey(mykey);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if(RegOpenKeyEx(HKEY_LOCAL_MACHINE, WIN_NS_9X, 0,
|
||||||
|
KEY_READ, &mykey) == ERROR_SUCCESS)
|
||||||
|
{
|
||||||
|
if((result = RegQueryValueEx(mykey, NAMESERVER, NULL, &data_type,
|
||||||
|
NULL, &bytes)) == ERROR_SUCCESS ||
|
||||||
|
result == ERROR_MORE_DATA)
|
||||||
|
{
|
||||||
|
if(bytes)
|
||||||
|
{
|
||||||
|
line = (char *)rb_malloc(bytes + 1);
|
||||||
|
if(RegQueryValueEx(mykey, NAMESERVER, NULL, &data_type,
|
||||||
|
(unsigned char *)line, &bytes) ==
|
||||||
|
ERROR_SUCCESS)
|
||||||
|
{
|
||||||
|
rb_strlcpy(namelist, line, sizeof(namelist));
|
||||||
|
}
|
||||||
|
free(line);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
RegCloseKey(mykey);
|
||||||
|
}
|
||||||
|
if(strlen(namelist) > 0)
|
||||||
|
return namelist;
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
|
@ -81,7 +81,7 @@ parse_options "$@"
|
||||||
echo "Building librb autotools files."
|
echo "Building librb autotools files."
|
||||||
|
|
||||||
cd "$TOP_DIR"/librb
|
cd "$TOP_DIR"/librb
|
||||||
bash autogen.sh
|
sh autogen.sh
|
||||||
|
|
||||||
echo "Building main autotools files."
|
echo "Building main autotools files."
|
||||||
|
|
||||||
|
|
|
@ -31,7 +31,7 @@
|
||||||
#include <rb_lib.h>
|
#include <rb_lib.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include "rsdb.h"
|
#include "rsdb.h"
|
||||||
#include "common.h"
|
#include "ircd_defs.h"
|
||||||
|
|
||||||
|
|
||||||
#define MAXPARA 10
|
#define MAXPARA 10
|
||||||
|
@ -255,7 +255,7 @@ dummy_handler(int sig)
|
||||||
static void
|
static void
|
||||||
setup_signals(void)
|
setup_signals(void)
|
||||||
{
|
{
|
||||||
#ifndef WINDOWS
|
#ifndef _WIN32
|
||||||
struct sigaction act;
|
struct sigaction act;
|
||||||
|
|
||||||
act.sa_flags = 0;
|
act.sa_flags = 0;
|
||||||
|
|
|
@ -40,7 +40,6 @@
|
||||||
#include <time.h>
|
#include <time.h>
|
||||||
|
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "common.h"
|
|
||||||
#include "rsdb.h"
|
#include "rsdb.h"
|
||||||
|
|
||||||
#define EmptyString(x) ((x == NULL) || (*(x) == '\0'))
|
#define EmptyString(x) ((x == NULL) || (*(x) == '\0'))
|
||||||
|
@ -93,16 +92,16 @@ struct counter
|
||||||
/* flags set by command line options */
|
/* flags set by command line options */
|
||||||
struct flags
|
struct flags
|
||||||
{
|
{
|
||||||
int none;
|
bool none;
|
||||||
int export;
|
bool export;
|
||||||
int import;
|
bool import;
|
||||||
int verify;
|
bool verify;
|
||||||
int vacuum;
|
bool vacuum;
|
||||||
int pretend;
|
bool pretend;
|
||||||
int verbose;
|
bool verbose;
|
||||||
int wipe;
|
bool wipe;
|
||||||
int dupes_ok;
|
bool dupes_ok;
|
||||||
} flag = {YES, NO, NO, NO, NO, NO, NO, NO, NO};
|
} flag = {true, false, false, false, false, false, false, false, false};
|
||||||
/* *INDENT-ON* */
|
/* *INDENT-ON* */
|
||||||
|
|
||||||
static int table_has_rows(const char *table);
|
static int table_has_rows(const char *table);
|
||||||
|
@ -145,32 +144,32 @@ main(int argc, char *argv[])
|
||||||
print_help(EXIT_SUCCESS);
|
print_help(EXIT_SUCCESS);
|
||||||
break;
|
break;
|
||||||
case 'i':
|
case 'i':
|
||||||
flag.none = NO;
|
flag.none = false;
|
||||||
flag.import = YES;
|
flag.import = true;
|
||||||
break;
|
break;
|
||||||
case 'e':
|
case 'e':
|
||||||
flag.none = NO;
|
flag.none = false;
|
||||||
flag.export = YES;
|
flag.export = true;
|
||||||
break;
|
break;
|
||||||
case 'u':
|
case 'u':
|
||||||
flag.none = NO;
|
flag.none = false;
|
||||||
flag.verify = YES;
|
flag.verify = true;
|
||||||
break;
|
break;
|
||||||
case 's':
|
case 's':
|
||||||
flag.none = NO;
|
flag.none = false;
|
||||||
flag.vacuum = YES;
|
flag.vacuum = true;
|
||||||
break;
|
break;
|
||||||
case 'p':
|
case 'p':
|
||||||
flag.pretend = YES;
|
flag.pretend = true;
|
||||||
break;
|
break;
|
||||||
case 'v':
|
case 'v':
|
||||||
flag.verbose = YES;
|
flag.verbose = true;
|
||||||
break;
|
break;
|
||||||
case 'w':
|
case 'w':
|
||||||
flag.wipe = YES;
|
flag.wipe = true;
|
||||||
break;
|
break;
|
||||||
case 'd':
|
case 'd':
|
||||||
flag.dupes_ok = YES;
|
flag.dupes_ok = true;
|
||||||
break;
|
break;
|
||||||
default: /* '?' */
|
default: /* '?' */
|
||||||
print_help(EXIT_FAILURE);
|
print_help(EXIT_FAILURE);
|
||||||
|
@ -200,7 +199,7 @@ main(int argc, char *argv[])
|
||||||
fprintf(stdout,
|
fprintf(stdout,
|
||||||
"* charybdis bantool v.%s\n", BT_VERSION);
|
"* charybdis bantool v.%s\n", BT_VERSION);
|
||||||
|
|
||||||
if(flag.pretend == NO)
|
if(flag.pretend == false)
|
||||||
{
|
{
|
||||||
if(rsdb_init(db_error_cb) == -1)
|
if(rsdb_init(db_error_cb) == -1)
|
||||||
{
|
{
|
||||||
|
@ -214,7 +213,7 @@ main(int argc, char *argv[])
|
||||||
|
|
||||||
if(flag.import && flag.wipe)
|
if(flag.import && flag.wipe)
|
||||||
{
|
{
|
||||||
flag.dupes_ok = YES; /* dont check for dupes if we are wiping the db clean */
|
flag.dupes_ok = true; /* dont check for dupes if we are wiping the db clean */
|
||||||
for(i = 0; i < 3; i++)
|
for(i = 0; i < 3; i++)
|
||||||
fprintf(stdout,
|
fprintf(stdout,
|
||||||
"* WARNING: YOU ARE ABOUT TO WIPE YOUR DATABASE!\n");
|
"* WARNING: YOU ARE ABOUT TO WIPE YOUR DATABASE!\n");
|
||||||
|
@ -226,7 +225,7 @@ main(int argc, char *argv[])
|
||||||
wipe_schema();
|
wipe_schema();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if(flag.verbose && flag.dupes_ok == YES)
|
if(flag.verbose && flag.dupes_ok == true)
|
||||||
fprintf(stdout, "* Allowing duplicate bans...\n");
|
fprintf(stdout, "* Allowing duplicate bans...\n");
|
||||||
|
|
||||||
/* checking for our files to import or export */
|
/* checking for our files to import or export */
|
||||||
|
@ -235,7 +234,7 @@ main(int argc, char *argv[])
|
||||||
snprintf(conf, sizeof(conf), "%s/%s.conf%s",
|
snprintf(conf, sizeof(conf), "%s/%s.conf%s",
|
||||||
etc, bandb_table[i], bandb_suffix[i]);
|
etc, bandb_table[i], bandb_suffix[i]);
|
||||||
|
|
||||||
if(flag.import && flag.pretend == NO)
|
if(flag.import && flag.pretend == false)
|
||||||
rsdb_transaction(RSDB_TRANS_START);
|
rsdb_transaction(RSDB_TRANS_START);
|
||||||
|
|
||||||
if(flag.import)
|
if(flag.import)
|
||||||
|
@ -244,7 +243,7 @@ main(int argc, char *argv[])
|
||||||
if(flag.export)
|
if(flag.export)
|
||||||
export_config(conf, i);
|
export_config(conf, i);
|
||||||
|
|
||||||
if(flag.import && flag.pretend == NO)
|
if(flag.import && flag.pretend == false)
|
||||||
rsdb_transaction(RSDB_TRANS_END);
|
rsdb_transaction(RSDB_TRANS_END);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -497,9 +496,9 @@ import_config(const char *conf, int id)
|
||||||
else
|
else
|
||||||
snprintf(newreason, sizeof(newreason), "%s", f_reason);
|
snprintf(newreason, sizeof(newreason), "%s", f_reason);
|
||||||
|
|
||||||
if(flag.pretend == NO)
|
if(flag.pretend == false)
|
||||||
{
|
{
|
||||||
if(flag.dupes_ok == NO)
|
if(flag.dupes_ok == false)
|
||||||
drop_dupes(f_mask1, f_mask2, bandb_table[id]);
|
drop_dupes(f_mask1, f_mask2, bandb_table[id]);
|
||||||
|
|
||||||
rsdb_exec(NULL,
|
rsdb_exec(NULL,
|
||||||
|
|
|
@ -25168,7 +25168,7 @@ winFullPathname(sqlite3_vfs * pVfs, /* Pointer to vfs object */
|
||||||
{
|
{
|
||||||
|
|
||||||
#if defined(__CYGWIN__)
|
#if defined(__CYGWIN__)
|
||||||
cygwin_conv_to_full_win32_path(zRelative, zFull);
|
cygwin_conv_path(CCP_POSIX_TO_WIN_A, zRelative, zFull, nFull);
|
||||||
return SQLITE_OK;
|
return SQLITE_OK;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
75
configure.ac
75
configure.ac
|
@ -19,6 +19,7 @@ fi
|
||||||
AC_PREFIX_DEFAULT($HOME/ircd)
|
AC_PREFIX_DEFAULT($HOME/ircd)
|
||||||
AC_CONFIG_MACRO_DIR([m4])
|
AC_CONFIG_MACRO_DIR([m4])
|
||||||
AC_CONFIG_HEADER(include/setup.h)
|
AC_CONFIG_HEADER(include/setup.h)
|
||||||
|
|
||||||
AC_CONFIG_SUBDIRS([librb])
|
AC_CONFIG_SUBDIRS([librb])
|
||||||
AC_CONFIG_AUX_DIR([libltdl/config])
|
AC_CONFIG_AUX_DIR([libltdl/config])
|
||||||
|
|
||||||
|
@ -33,6 +34,24 @@ LTDL_INIT
|
||||||
build_ltdl=$with_included_ltdl
|
build_ltdl=$with_included_ltdl
|
||||||
AM_CONDITIONAL([BUILD_LTDL], [test x"$build_ltdl" = x"yes"])
|
AM_CONDITIONAL([BUILD_LTDL], [test x"$build_ltdl" = x"yes"])
|
||||||
|
|
||||||
|
case "$host_os" in
|
||||||
|
*cygwin*)
|
||||||
|
AC_DEFINE_UNQUOTED(CYGWIN,1,[This is a Cygwin system])
|
||||||
|
AC_DEFINE_UNQUOTED(WINDOWS,1,[This is a Windows system])
|
||||||
|
;;
|
||||||
|
*mingw* | *msys*)
|
||||||
|
AC_DEFINE_UNQUOTED(MINGW,1,[This is a MinGW system])
|
||||||
|
AC_DEFINE_UNQUOTED(WINDOWS,1,[This is a Windows system])
|
||||||
|
AC_CHECK_HEADER(winsock2.h, , [AC_MSG_ERROR([** MinGW and no winsock2.h. I give up.])])
|
||||||
|
LIBS="$LIBS -lws2_32 -liphlpapi"
|
||||||
|
is_mingw="yes"
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
AM_CONDITIONAL([MINGW], [test "$is_mingw" = "yes"])
|
||||||
|
|
||||||
if test "$ac_cv_c_compiler_gnu" = yes; then
|
if test "$ac_cv_c_compiler_gnu" = yes; then
|
||||||
IRC_CFLAGS="$IRC_CFLAGS -O0 -Wall"
|
IRC_CFLAGS="$IRC_CFLAGS -O0 -Wall"
|
||||||
fi
|
fi
|
||||||
|
@ -102,7 +121,8 @@ AS_IF([test "x$enable_fhs_paths" = "xyes"],
|
||||||
pkglibexecdir='${libexecdir}/${PACKAGE_TARNAME}'
|
pkglibexecdir='${libexecdir}/${PACKAGE_TARNAME}'
|
||||||
rundir=${rundir-'${prefix}/run'}
|
rundir=${rundir-'${prefix}/run'}
|
||||||
pkgrundir='${rundir}/${PACKAGE_TARNAME}'
|
pkgrundir='${rundir}/${PACKAGE_TARNAME}'
|
||||||
pkglocalstatedir='${localstatedir}/${PACKAGE_TARNAME}'],
|
pkglocalstatedir='${localstatedir}/${PACKAGE_TARNAME}'
|
||||||
|
AC_DEFINE([ENABLE_FHS_PATHS], [1], [Uncomment if FHS pathnames are enabled])],
|
||||||
[libexecdir='${bindir}'
|
[libexecdir='${bindir}'
|
||||||
pkglibexecdir='${libexecdir}'
|
pkglibexecdir='${libexecdir}'
|
||||||
rundir='${sysconfdir}'
|
rundir='${sysconfdir}'
|
||||||
|
@ -141,19 +161,13 @@ AC_CHECK_SIZEOF(long long)
|
||||||
dnl Networking Functions
|
dnl Networking Functions
|
||||||
dnl ====================
|
dnl ====================
|
||||||
|
|
||||||
AC_SEARCH_LIBS(socket, socket, , [AC_MSG_ERROR([You have no socket()! Aborting.])])
|
AC_SEARCH_LIBS(socket, [socket ws2_32], , [AC_MSG_ERROR([You have no socket()! Aborting.])])
|
||||||
|
|
||||||
dnl SunOS/Solaris required libnsl for inet_ntoa()
|
dnl SunOS/Solaris required libnsl for inet_ntoa()
|
||||||
if test x"$SUN" = xyes; then
|
if test x"$SUN" = xyes; then
|
||||||
AC_SEARCH_LIBS(inet_ntoa, nsl,, [AC_MSG_ERROR([libnsl not found! Aborting.])])
|
AC_SEARCH_LIBS(inet_ntoa, nsl,, [AC_MSG_ERROR([libnsl not found! Aborting.])])
|
||||||
fi
|
fi
|
||||||
|
|
||||||
AC_CHECK_TYPE(socklen_t, ,
|
|
||||||
[AC_DEFINE([socklen_t], [unsigned int],
|
|
||||||
[If we don't have a real socklen_t, unsigned int is good enough.])],
|
|
||||||
[#include <sys/types.h>
|
|
||||||
#include <sys/socket.h>])
|
|
||||||
|
|
||||||
AC_ARG_ENABLE(ipv6,
|
AC_ARG_ENABLE(ipv6,
|
||||||
AC_HELP_STRING([--enable-ipv6],[Enable IPv6 support]),[ipv6=$enableval],[ipv6=no])
|
AC_HELP_STRING([--enable-ipv6],[Enable IPv6 support]),[ipv6=$enableval],[ipv6=no])
|
||||||
|
|
||||||
|
@ -175,34 +189,8 @@ dnl Check for stdarg.h - if we can't find it, halt configure
|
||||||
AC_CHECK_HEADER(stdarg.h, , [AC_MSG_ERROR([** stdarg.h could not be found - charybdis will not compile without it **])])
|
AC_CHECK_HEADER(stdarg.h, , [AC_MSG_ERROR([** stdarg.h could not be found - charybdis will not compile without it **])])
|
||||||
AC_CHECK_FUNCS([strlcat strlcpy])
|
AC_CHECK_FUNCS([strlcat strlcpy])
|
||||||
|
|
||||||
AC_CHECK_TYPE([u_int32_t], [],
|
AC_TYPE_INT16_T
|
||||||
[
|
AC_TYPE_INT32_T
|
||||||
AC_CHECK_TYPE([uint32_t],
|
|
||||||
[
|
|
||||||
AC_DEFINE(u_int32_t, [uint32_t], [If system does not define u_int32_t, define a reasonable substitute.])
|
|
||||||
],
|
|
||||||
[
|
|
||||||
AC_MSG_WARN([system has no u_int32_t or uint32_t, default to unsigned long int])
|
|
||||||
AC_DEFINE(u_int32_t, [unsigned long int], [If system does not define u_int32_t, define to unsigned long int here.])
|
|
||||||
])
|
|
||||||
])
|
|
||||||
|
|
||||||
AC_CHECK_TYPE([u_int16_t], [],
|
|
||||||
[
|
|
||||||
AC_CHECK_TYPE([uint16_t],
|
|
||||||
[
|
|
||||||
AC_DEFINE(u_int16_t, [uint16_t], [If system does not define u_int16_t, define a usable substitute])
|
|
||||||
],
|
|
||||||
[
|
|
||||||
AC_MSG_WARN([system has no u_int16_t or uint16_t, default to unsigned short int])
|
|
||||||
AC_DEFINE(u_int16_t, [unsigned short int], [If system does not define u_int16_t, define a usable substitute.])
|
|
||||||
])
|
|
||||||
])
|
|
||||||
|
|
||||||
AC_CHECK_TYPE([in_port_t], [],
|
|
||||||
[AC_DEFINE(in_port_t, [u_int16_t], [If system does not define in_port_t, define it to what it should be.])],
|
|
||||||
[[#include <sys/types.h>
|
|
||||||
#include <netinet/in.h>]])
|
|
||||||
|
|
||||||
AC_CHECK_TYPE([sa_family_t], [],
|
AC_CHECK_TYPE([sa_family_t], [],
|
||||||
[AC_DEFINE(sa_family_t, [u_int16_t], [If system does not define sa_family_t, define it here.])],
|
[AC_DEFINE(sa_family_t, [u_int16_t], [If system does not define sa_family_t, define it here.])],
|
||||||
|
@ -497,6 +485,18 @@ if test "x$BRANDING_NAME" != "x$PACKAGE_NAME"; then
|
||||||
AC_DEFINE(CUSTOM_BRANDING, 1, [Define if custom branding is enabled.])
|
AC_DEFINE(CUSTOM_BRANDING, 1, [Define if custom branding is enabled.])
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
dnl **********************************************************************
|
||||||
|
dnl Enable oper chghost
|
||||||
|
dnl **********************************************************************
|
||||||
|
|
||||||
|
AC_ARG_ENABLE(oper-chghost,
|
||||||
|
AC_HELP_STRING([--enable-oper-chghost],[Enable opers to use the CHGHOST command]),
|
||||||
|
[operchghost=$enableval],[operchghost=no])
|
||||||
|
|
||||||
|
if test "$operchghost" = yes; then
|
||||||
|
AC_DEFINE(ENABLE_OPER_CHGHOST, 1, [Define this to enable opers to use the CHGHOST command.])
|
||||||
|
fi
|
||||||
|
|
||||||
dnl Debug-related options
|
dnl Debug-related options
|
||||||
dnl =====================
|
dnl =====================
|
||||||
|
|
||||||
|
@ -607,7 +607,7 @@ CHARYBDIS_C_GCC_TRY_FLAGS([-Wcast-qual], charybdis_cv_c_gcc_w_cast_qual)
|
||||||
CHARYBDIS_C_GCC_TRY_FLAGS([-Wwrite-strings], charybdis_cv_c_gcc_w_write_strings)
|
CHARYBDIS_C_GCC_TRY_FLAGS([-Wwrite-strings], charybdis_cv_c_gcc_w_write_strings)
|
||||||
CHARYBDIS_C_GCC_TRY_FLAGS([-Werror-implicit-function-declaration], charybdis_cv_c_gcc_w_error_implicit_function_declaration)
|
CHARYBDIS_C_GCC_TRY_FLAGS([-Werror-implicit-function-declaration], charybdis_cv_c_gcc_w_error_implicit_function_declaration)
|
||||||
CHARYBDIS_C_GCC_TRY_FLAGS([-Wstrict-prototypes -Wmissing-prototypes -Wmissing-declarations], charybdis_cv_c_gcc_prototypes)
|
CHARYBDIS_C_GCC_TRY_FLAGS([-Wstrict-prototypes -Wmissing-prototypes -Wmissing-declarations], charybdis_cv_c_gcc_prototypes)
|
||||||
CHARYBDIS_C_GCC_TRY_FLAGS([-Wparenthesis], charybdis_cv_c_gcc_parenthesis)
|
CHARYBDIS_C_GCC_TRY_FLAGS([-Wparentheses], charybdis_cv_c_gcc_parentheses)
|
||||||
CHARYBDIS_C_GCC_TRY_FLAGS([-W -Wno-unused], charybdis_cv_c_gcc_w)
|
CHARYBDIS_C_GCC_TRY_FLAGS([-W -Wno-unused], charybdis_cv_c_gcc_w)
|
||||||
CHARYBDIS_C_GCC_TRY_FLAGS([-Wextra], charybdis_cv_c_gcc_w_extra)
|
CHARYBDIS_C_GCC_TRY_FLAGS([-Wextra], charybdis_cv_c_gcc_w_extra)
|
||||||
CHARYBDIS_C_GCC_TRY_FLAGS([-Wshadow], charybdis_cv_c_gcc_w_shadow)
|
CHARYBDIS_C_GCC_TRY_FLAGS([-Wshadow], charybdis_cv_c_gcc_w_shadow)
|
||||||
|
@ -656,6 +656,7 @@ AC_CONFIG_FILES( \
|
||||||
authd/Makefile \
|
authd/Makefile \
|
||||||
bandb/Makefile \
|
bandb/Makefile \
|
||||||
ssld/Makefile \
|
ssld/Makefile \
|
||||||
|
wsockd/Makefile \
|
||||||
extensions/Makefile \
|
extensions/Makefile \
|
||||||
ircd/Makefile \
|
ircd/Makefile \
|
||||||
modules/Makefile \
|
modules/Makefile \
|
||||||
|
|
|
@ -8,33 +8,33 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* Extensions */
|
/* Extensions */
|
||||||
#loadmodule "extensions/chm_operonly_compat.la";
|
#loadmodule "extensions/chm_operonly_compat";
|
||||||
#loadmodule "extensions/chm_quietunreg_compat.la";
|
#loadmodule "extensions/chm_quietunreg_compat";
|
||||||
#loadmodule "extensions/chm_sslonly_compat.la";
|
#loadmodule "extensions/chm_sslonly_compat";
|
||||||
#loadmodule "extensions/chm_operpeace.la";
|
#loadmodule "extensions/chm_operpeace";
|
||||||
#loadmodule "extensions/createauthonly.la";
|
#loadmodule "extensions/createauthonly";
|
||||||
#loadmodule "extensions/extb_account.la";
|
#loadmodule "extensions/extb_account";
|
||||||
#loadmodule "extensions/extb_canjoin.la";
|
#loadmodule "extensions/extb_canjoin";
|
||||||
#loadmodule "extensions/extb_channel.la";
|
#loadmodule "extensions/extb_channel";
|
||||||
#loadmodule "extensions/extb_combi.la";
|
#loadmodule "extensions/extb_combi";
|
||||||
#loadmodule "extensions/extb_extgecos.la";
|
#loadmodule "extensions/extb_extgecos";
|
||||||
#loadmodule "extensions/extb_hostmask.la";
|
#loadmodule "extensions/extb_hostmask";
|
||||||
#loadmodule "extensions/extb_oper.la";
|
#loadmodule "extensions/extb_oper";
|
||||||
#loadmodule "extensions/extb_realname.la";
|
#loadmodule "extensions/extb_realname";
|
||||||
#loadmodule "extensions/extb_server.la";
|
#loadmodule "extensions/extb_server";
|
||||||
#loadmodule "extensions/extb_ssl.la";
|
#loadmodule "extensions/extb_ssl";
|
||||||
#loadmodule "extensions/hurt.la";
|
#loadmodule "extensions/hurt";
|
||||||
#loadmodule "extensions/m_extendchans.la";
|
#loadmodule "extensions/m_extendchans";
|
||||||
#loadmodule "extensions/m_findforwards.la";
|
#loadmodule "extensions/m_findforwards";
|
||||||
#loadmodule "extensions/m_identify.la";
|
#loadmodule "extensions/m_identify";
|
||||||
#loadmodule "extensions/no_oper_invis.la";
|
#loadmodule "extensions/no_oper_invis";
|
||||||
#loadmodule "extensions/sno_farconnect.la";
|
#loadmodule "extensions/sno_farconnect";
|
||||||
#loadmodule "extensions/sno_globalkline.la";
|
#loadmodule "extensions/sno_globalkline";
|
||||||
#loadmodule "extensions/sno_globalnickchange.la";
|
#loadmodule "extensions/sno_globalnickchange";
|
||||||
#loadmodule "extensions/sno_globaloper.la";
|
#loadmodule "extensions/sno_globaloper";
|
||||||
#loadmodule "extensions/sno_whois.la";
|
#loadmodule "extensions/sno_whois";
|
||||||
#loadmodule "extensions/override.la";
|
#loadmodule "extensions/override";
|
||||||
#loadmodule "extensions/no_kill_services.la";
|
#loadmodule "extensions/no_kill_services";
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* IP cloaking extensions: use ip_cloaking_4.0
|
* IP cloaking extensions: use ip_cloaking_4.0
|
||||||
|
@ -43,15 +43,14 @@
|
||||||
* releases.
|
* releases.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#loadmodule "extensions/ip_cloaking_4.0.la";
|
#loadmodule "extensions/ip_cloaking_4.0";
|
||||||
#loadmodule "extensions/ip_cloaking.la";
|
#loadmodule "extensions/ip_cloaking";
|
||||||
|
|
||||||
serverinfo {
|
serverinfo {
|
||||||
name = "hades.arpa";
|
name = "hades.arpa";
|
||||||
sid = "42X";
|
sid = "42X";
|
||||||
description = "charybdis test server";
|
description = "charybdis test server";
|
||||||
network_name = "StaticBox";
|
network_name = "StaticBox";
|
||||||
hub = yes;
|
|
||||||
|
|
||||||
/* On multi-homed hosts you may need the following. These define
|
/* On multi-homed hosts you may need the following. These define
|
||||||
* the addresses we connect from to other servers. */
|
* the addresses we connect from to other servers. */
|
||||||
|
|
|
@ -43,73 +43,73 @@
|
||||||
* Charybdis contains several extensions that are not enabled by default.
|
* Charybdis contains several extensions that are not enabled by default.
|
||||||
* To use them, uncomment the lines below.
|
* To use them, uncomment the lines below.
|
||||||
*
|
*
|
||||||
* Channel mode +-A (admin only) -- chm_adminonly.la
|
* Channel mode +-A (admin only) -- chm_adminonly
|
||||||
* Channel mode +-O (oper only) -- chm_operonly.la
|
* Channel mode +-O (oper only) -- chm_operonly
|
||||||
* Channel mode +-S (ssl only) -- chm_sslonly.la
|
* Channel mode +-S (ssl only) -- chm_sslonly
|
||||||
* Emulates channel mode +-O (oper only) (+-iI $o) -- chm_operonly_compat.la
|
* Emulates channel mode +-O (oper only) (+-iI $o) -- chm_operonly_compat
|
||||||
* Emulates channel mode +-R (quiet unreg) (+-q $~a) -- chm_quietunreg_compat.la
|
* Emulates channel mode +-R (quiet unreg) (+-q $~a) -- chm_quietunreg_compat
|
||||||
* Emulates channel mode +-S (ssl only) (+-b $~z) -- chm_sslonly_compat.la
|
* Emulates channel mode +-S (ssl only) (+-b $~z) -- chm_sslonly_compat
|
||||||
* Channel mode +-M (disallow KICK on IRC ops) -- chm_operpeace.la
|
* Channel mode +-M (disallow KICK on IRC ops) -- chm_operpeace
|
||||||
* Restrict channel creation to logged in users -- createauthonly.la
|
* Restrict channel creation to logged in users -- createauthonly
|
||||||
* Account bans (+b $a[:mask]) -- extb_account.la
|
* Account bans (+b $a[:mask]) -- extb_account
|
||||||
* Banned from another channel (+b $j:mask) -- extb_canjoin.la
|
* Banned from another channel (+b $j:mask) -- extb_canjoin
|
||||||
* Other-channel bans (+b $c:mask) -- extb_channel.la
|
* Other-channel bans (+b $c:mask) -- extb_channel
|
||||||
* Combination extbans -- extb_combi.la
|
* Combination extbans -- extb_combi
|
||||||
* Extended ban (+b $x:mask) -- extb_extgecos.la
|
* Extended ban (+b $x:mask) -- extb_extgecos
|
||||||
* Hostmask bans (for combination extbans) -- extb_hostmask.la
|
* Hostmask bans (for combination extbans) -- extb_hostmask
|
||||||
* Oper bans (+b $o) -- extb_oper.la
|
* Oper bans (+b $o) -- extb_oper
|
||||||
* Realname (gecos) bans (+b $r:mask) -- extb_realname.la
|
* Realname (gecos) bans (+b $r:mask) -- extb_realname
|
||||||
* Server bans (+b $s:mask) -- extb_server.la
|
* Server bans (+b $s:mask) -- extb_server
|
||||||
* SSL bans (+b $z) -- extb_ssl.la
|
* SSL bans (+b $z) -- extb_ssl
|
||||||
* Helpops system (umode +H) -- helpops.la
|
* Helpops system (umode +H) -- helpops
|
||||||
* HURT system -- hurt.la
|
* HURT system -- hurt
|
||||||
* New host mangling (umode +x) -- ip_cloaking_4.0.la
|
* New host mangling (umode +x) -- ip_cloaking_4.0
|
||||||
* Old host mangling (umode +h) -- ip_cloaking.la
|
* Old host mangling (umode +h) -- ip_cloaking
|
||||||
* Dynamically extend channel limits -- m_extendchans.la
|
* Dynamically extend channel limits -- m_extendchans
|
||||||
* Find channel forwards -- m_findforwards.la
|
* Find channel forwards -- m_findforwards
|
||||||
* /identify support -- m_identify.la
|
* /identify support -- m_identify
|
||||||
* Opers cannot be invisible (umode +i) -- no_oper_invis.la
|
* Opers cannot be invisible (umode +i) -- no_oper_invis
|
||||||
* Far connection notices (snomask +F) -- sno_farconnect.la
|
* Far connection notices (snomask +F) -- sno_farconnect
|
||||||
* Remote k/d/x line active notices -- sno_globalkline.la
|
* Remote k/d/x line active notices -- sno_globalkline
|
||||||
* Remote oper up notices -- sno_globaloper.la
|
* Remote oper up notices -- sno_globaloper
|
||||||
* Global nick-change notices -- sno_globalnickchange.la
|
* Global nick-change notices -- sno_globalnickchange
|
||||||
* /whois notifications (snomask +W) -- sno_whois.la
|
* /whois notifications (snomask +W) -- sno_whois
|
||||||
* Oper-override (modehacking only) -- override.la
|
* Oper-override (modehacking only) -- override
|
||||||
* Stop services kills -- no_kill_services.la
|
* Stop services kills -- no_kill_services
|
||||||
*/
|
*/
|
||||||
#loadmodule "extensions/chm_adminonly.la";
|
#loadmodule "extensions/chm_adminonly";
|
||||||
#loadmodule "extensions/chm_operonly.la";
|
#loadmodule "extensions/chm_operonly";
|
||||||
#loadmodule "extensions/chm_sslonly.la";
|
#loadmodule "extensions/chm_sslonly";
|
||||||
#loadmodule "extensions/chm_operonly_compat.la";
|
#loadmodule "extensions/chm_operonly_compat";
|
||||||
#loadmodule "extensions/chm_quietunreg_compat.la";
|
#loadmodule "extensions/chm_quietunreg_compat";
|
||||||
#loadmodule "extensions/chm_sslonly_compat.la";
|
#loadmodule "extensions/chm_sslonly_compat";
|
||||||
#loadmodule "extensions/chm_operpeace.la";
|
#loadmodule "extensions/chm_operpeace";
|
||||||
#loadmodule "extensions/createauthonly.la";
|
#loadmodule "extensions/createauthonly";
|
||||||
#loadmodule "extensions/extb_account.la";
|
#loadmodule "extensions/extb_account";
|
||||||
#loadmodule "extensions/extb_canjoin.la";
|
#loadmodule "extensions/extb_canjoin";
|
||||||
#loadmodule "extensions/extb_channel.la";
|
#loadmodule "extensions/extb_channel";
|
||||||
#loadmodule "extensions/extb_combi.la";
|
#loadmodule "extensions/extb_combi";
|
||||||
#loadmodule "extensions/extb_extgecos.la";
|
#loadmodule "extensions/extb_extgecos";
|
||||||
#loadmodule "extensions/extb_hostmask.la";
|
#loadmodule "extensions/extb_hostmask";
|
||||||
#loadmodule "extensions/extb_oper.la";
|
#loadmodule "extensions/extb_oper";
|
||||||
#loadmodule "extensions/extb_realname.la";
|
#loadmodule "extensions/extb_realname";
|
||||||
#loadmodule "extensions/extb_server.la";
|
#loadmodule "extensions/extb_server";
|
||||||
#loadmodule "extensions/extb_ssl.la";
|
#loadmodule "extensions/extb_ssl";
|
||||||
#loadmodule "extensions/helpops.la";
|
#loadmodule "extensions/helpops";
|
||||||
#loadmodule "extensions/hurt.la";
|
#loadmodule "extensions/hurt";
|
||||||
#loadmodule "extensions/ip_cloaking_4.0.la";
|
#loadmodule "extensions/ip_cloaking_4.0";
|
||||||
#loadmodule "extensions/ip_cloaking.la";
|
#loadmodule "extensions/ip_cloaking";
|
||||||
#loadmodule "extensions/m_extendchans.la";
|
#loadmodule "extensions/m_extendchans";
|
||||||
#loadmodule "extensions/m_findforwards.la";
|
#loadmodule "extensions/m_findforwards";
|
||||||
#loadmodule "extensions/m_identify.la";
|
#loadmodule "extensions/m_identify";
|
||||||
#loadmodule "extensions/no_oper_invis.la";
|
#loadmodule "extensions/no_oper_invis";
|
||||||
#loadmodule "extensions/sno_farconnect.la";
|
#loadmodule "extensions/sno_farconnect";
|
||||||
#loadmodule "extensions/sno_globalkline.la";
|
#loadmodule "extensions/sno_globalkline";
|
||||||
#loadmodule "extensions/sno_globalnickchange.la";
|
#loadmodule "extensions/sno_globalnickchange";
|
||||||
#loadmodule "extensions/sno_globaloper.la";
|
#loadmodule "extensions/sno_globaloper";
|
||||||
#loadmodule "extensions/sno_whois.la";
|
#loadmodule "extensions/sno_whois";
|
||||||
#loadmodule "extensions/override.la";
|
#loadmodule "extensions/override";
|
||||||
#loadmodule "extensions/no_kill_services.la";
|
#loadmodule "extensions/no_kill_services";
|
||||||
|
|
||||||
/* serverinfo {}: Contains information about the server. (OLD M:) */
|
/* serverinfo {}: Contains information about the server. (OLD M:) */
|
||||||
serverinfo {
|
serverinfo {
|
||||||
|
@ -134,11 +134,6 @@ serverinfo {
|
||||||
*/
|
*/
|
||||||
network_name = "MyNet";
|
network_name = "MyNet";
|
||||||
|
|
||||||
/* hub: allow this server to act as a hub and have multiple servers
|
|
||||||
* connected to it.
|
|
||||||
*/
|
|
||||||
hub = no;
|
|
||||||
|
|
||||||
/* vhost: the IP to bind to when we connect outward to ipv4 servers.
|
/* vhost: the IP to bind to when we connect outward to ipv4 servers.
|
||||||
* This should be an ipv4 IP only.
|
* This should be an ipv4 IP only.
|
||||||
*/
|
*/
|
||||||
|
@ -1349,5 +1344,5 @@ modules {
|
||||||
path = "/usr/local/ircd/modules/autoload";
|
path = "/usr/local/ircd/modules/autoload";
|
||||||
|
|
||||||
/* module: the name of a module to load on startup/rehash */
|
/* module: the name of a module to load on startup/rehash */
|
||||||
#module = "some_module.la";
|
#module = "some_module";
|
||||||
};
|
};
|
||||||
|
|
|
@ -17,8 +17,6 @@
|
||||||
+----------------------------+
|
+----------------------------+
|
||||||
| 'e' | USE_EXCEPT |
|
| 'e' | USE_EXCEPT |
|
||||||
|------+---------------------|
|
|------+---------------------|
|
||||||
| 'H' | HUB |
|
|
||||||
|------+---------------------|
|
|
||||||
| 'I' | USE_INVEX |
|
| 'I' | USE_INVEX |
|
||||||
|------+---------------------|
|
|------+---------------------|
|
||||||
| 'K' | USE_KNOCK |
|
| 'K' | USE_KNOCK |
|
||||||
|
@ -29,8 +27,6 @@
|
||||||
|------+---------------------|
|
|------+---------------------|
|
||||||
| 'S' | OPERS_SEE_ALL_USERS |
|
| 'S' | OPERS_SEE_ALL_USERS |
|
||||||
|------+---------------------|
|
|------+---------------------|
|
||||||
| 'T' | IGNORE_BOGUS_TS |
|
|
||||||
|------+---------------------|
|
|
||||||
| 'Z' | ZIPLINKS |
|
| 'Z' | ZIPLINKS |
|
||||||
|------+---------------------|
|
|------+---------------------|
|
||||||
| '6' | IPv6 |
|
| '6' | IPv6 |
|
||||||
|
|
|
@ -1198,8 +1198,6 @@ CAP
|
||||||
CHALLENGE
|
CHALLENGE
|
||||||
CHANTRACE
|
CHANTRACE
|
||||||
CLOSE
|
CLOSE
|
||||||
CNOTICE
|
|
||||||
CPRIVMSG
|
|
||||||
DIE
|
DIE
|
||||||
GET
|
GET
|
||||||
HELP
|
HELP
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
AM_CPPFLAGS = -I$(top_srcdir)/include -I$(top_srcdir)/librb/include $(LTDLINCL)
|
AM_CPPFLAGS = -I$(top_srcdir)/include -I$(top_srcdir)/librb/include $(LTDLINCL)
|
||||||
AM_LDFLAGS = -module -export-dynamic -avoid-version -no-undefined -shared
|
AM_LDFLAGS = -module -export-dynamic -avoid-version -no-undefined -shared
|
||||||
AM_LDFLAGS += -export-symbols-regex _mheader
|
AM_LDFLAGS += -export-symbols-regex _mheader
|
||||||
LIBS += $(top_srcdir)/librb/src/librb.la $(top_srcdir)/ircd/libircd.la
|
LIBS += $(top_srcdir)/ircd/libircd.la
|
||||||
|
|
||||||
extensiondir=@moduledir@/extensions
|
extensiondir=@moduledir@/extensions
|
||||||
|
|
||||||
|
|
|
@ -52,7 +52,7 @@ static int _modinit(void);
|
||||||
static void _moddeinit(void);
|
static void _moddeinit(void);
|
||||||
static int eb_or(const char *data, struct Client *client_p, struct Channel *chptr, long mode_type);
|
static int eb_or(const char *data, struct Client *client_p, struct Channel *chptr, long mode_type);
|
||||||
static int eb_and(const char *data, struct Client *client_p, struct Channel *chptr, long mode_type);
|
static int eb_and(const char *data, struct Client *client_p, struct Channel *chptr, long mode_type);
|
||||||
static int eb_combi(const char *data, struct Client *client_p, struct Channel *chptr, long mode_type, int is_and);
|
static int eb_combi(const char *data, struct Client *client_p, struct Channel *chptr, long mode_type, bool is_and);
|
||||||
static int recursion_depth = 0;
|
static int recursion_depth = 0;
|
||||||
|
|
||||||
DECLARE_MODULE_AV2(extb_extended, _modinit, _moddeinit, NULL, NULL, NULL, NULL, NULL, extb_desc);
|
DECLARE_MODULE_AV2(extb_extended, _modinit, _moddeinit, NULL, NULL, NULL, NULL, NULL, extb_desc);
|
||||||
|
@ -76,20 +76,20 @@ _moddeinit(void)
|
||||||
static int eb_or(const char *data, struct Client *client_p,
|
static int eb_or(const char *data, struct Client *client_p,
|
||||||
struct Channel *chptr, long mode_type)
|
struct Channel *chptr, long mode_type)
|
||||||
{
|
{
|
||||||
return eb_combi(data, client_p, chptr, mode_type, FALSE);
|
return eb_combi(data, client_p, chptr, mode_type, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int eb_and(const char *data, struct Client *client_p,
|
static int eb_and(const char *data, struct Client *client_p,
|
||||||
struct Channel *chptr, long mode_type)
|
struct Channel *chptr, long mode_type)
|
||||||
{
|
{
|
||||||
return eb_combi(data, client_p, chptr, mode_type, TRUE);
|
return eb_combi(data, client_p, chptr, mode_type, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int eb_combi(const char *data, struct Client *client_p,
|
static int eb_combi(const char *data, struct Client *client_p,
|
||||||
struct Channel *chptr, long mode_type, int is_and)
|
struct Channel *chptr, long mode_type, bool is_and)
|
||||||
{
|
{
|
||||||
const char *p, *banend;
|
const char *p, *banend;
|
||||||
int have_result = FALSE;
|
bool have_result = false;
|
||||||
int allowed_nodes = 11;
|
int allowed_nodes = 11;
|
||||||
size_t datalen;
|
size_t datalen;
|
||||||
|
|
||||||
|
@ -143,12 +143,12 @@ static int eb_combi(const char *data, struct Client *client_p,
|
||||||
recursion_depth++;
|
recursion_depth++;
|
||||||
|
|
||||||
while (--allowed_nodes) {
|
while (--allowed_nodes) {
|
||||||
int invert = FALSE;
|
bool invert = false;
|
||||||
char *child_data, child_data_buf[BANLEN];
|
char *child_data, child_data_buf[BANLEN];
|
||||||
ExtbanFunc f;
|
ExtbanFunc f;
|
||||||
|
|
||||||
if (*p == '~') {
|
if (*p == '~') {
|
||||||
invert = TRUE;
|
invert = true;
|
||||||
p++;
|
p++;
|
||||||
if (p == banend) {
|
if (p == banend) {
|
||||||
MOD_DEBUG("combo invalid: no data after ~");
|
MOD_DEBUG("combo invalid: no data after ~");
|
||||||
|
@ -164,7 +164,7 @@ static int eb_combi(const char *data, struct Client *client_p,
|
||||||
|
|
||||||
if (*p == ':') {
|
if (*p == ':') {
|
||||||
unsigned int parencount = 0;
|
unsigned int parencount = 0;
|
||||||
int escaped = FALSE, done = FALSE;
|
bool escaped = false, done = false;
|
||||||
char *o;
|
char *o;
|
||||||
|
|
||||||
p++;
|
p++;
|
||||||
|
@ -173,7 +173,7 @@ static int eb_combi(const char *data, struct Client *client_p,
|
||||||
* we already have_result.
|
* we already have_result.
|
||||||
*/
|
*/
|
||||||
o = child_data = child_data_buf;
|
o = child_data = child_data_buf;
|
||||||
while (TRUE) {
|
while (true) {
|
||||||
if (p == banend) {
|
if (p == banend) {
|
||||||
if (parencount) {
|
if (parencount) {
|
||||||
MOD_DEBUG("combo invalid: EOD while in parens");
|
MOD_DEBUG("combo invalid: EOD while in parens");
|
||||||
|
@ -186,11 +186,11 @@ static int eb_combi(const char *data, struct Client *client_p,
|
||||||
if (*p != '(' && *p != ')' && *p != '\\' && *p != ',')
|
if (*p != '(' && *p != ')' && *p != '\\' && *p != ',')
|
||||||
*o++ = '\\';
|
*o++ = '\\';
|
||||||
*o++ = *p++;
|
*o++ = *p++;
|
||||||
escaped = FALSE;
|
escaped = false;
|
||||||
} else {
|
} else {
|
||||||
switch (*p) {
|
switch (*p) {
|
||||||
case '\\':
|
case '\\':
|
||||||
escaped = TRUE;
|
escaped = true;
|
||||||
break;
|
break;
|
||||||
case '(':
|
case '(':
|
||||||
parencount++;
|
parencount++;
|
||||||
|
@ -208,7 +208,7 @@ static int eb_combi(const char *data, struct Client *client_p,
|
||||||
if (parencount)
|
if (parencount)
|
||||||
*o++ = *p;
|
*o++ = *p;
|
||||||
else
|
else
|
||||||
done = TRUE;
|
done = true;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
*o++ = *p;
|
*o++ = *p;
|
||||||
|
@ -239,7 +239,7 @@ static int eb_combi(const char *data, struct Client *client_p,
|
||||||
child_result = child_result == EXTBAN_MATCH;
|
child_result = child_result == EXTBAN_MATCH;
|
||||||
|
|
||||||
if (is_and ? !child_result : child_result)
|
if (is_and ? !child_result : child_result)
|
||||||
have_result = TRUE;
|
have_result = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (p == banend)
|
if (p == banend)
|
||||||
|
|
|
@ -56,7 +56,7 @@ eb_hostmask(const char *banstr, struct Client *client_p, struct Channel *chptr,
|
||||||
|
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
/* handle Teredo if necessary */
|
/* handle Teredo if necessary */
|
||||||
if (client_p->localClient->ip.ss_family == AF_INET6 && ipv4_from_ipv6((const struct sockaddr_in6 *) &client_p->localClient->ip, &ip4))
|
if (GET_SS_FAMILY(&client_p->localClient->ip) == AF_INET6 && ipv4_from_ipv6((const struct sockaddr_in6 *) &client_p->localClient->ip, &ip4))
|
||||||
{
|
{
|
||||||
sprintf(src_ip4host, "%s!%s@", client_p->name, client_p->username);
|
sprintf(src_ip4host, "%s!%s@", client_p->name, client_p->username);
|
||||||
s4 = src_ip4host + strlen(src_ip4host);
|
s4 = src_ip4host + strlen(src_ip4host);
|
||||||
|
|
|
@ -20,18 +20,16 @@ DECLARE_MODULE_AV2(echotags, NULL, NULL, echotags_clist, NULL, NULL, NULL, NULL,
|
||||||
static void
|
static void
|
||||||
m_echotags(struct MsgBuf *msgbuf_p, struct Client *client_p, struct Client *source_p, int parc, const char *parv[])
|
m_echotags(struct MsgBuf *msgbuf_p, struct Client *client_p, struct Client *source_p, int parc, const char *parv[])
|
||||||
{
|
{
|
||||||
int i;
|
|
||||||
|
|
||||||
sendto_one_notice(source_p, ":*** You sent %zu tags.", msgbuf_p->n_tags);
|
sendto_one_notice(source_p, ":*** You sent %zu tags.", msgbuf_p->n_tags);
|
||||||
|
|
||||||
for (i = 0; i < msgbuf_p->n_tags; i++)
|
for (size_t i = 0; i < msgbuf_p->n_tags; i++)
|
||||||
{
|
{
|
||||||
struct MsgTag *tag = &msgbuf_p->tags[i];
|
struct MsgTag *tag = &msgbuf_p->tags[i];
|
||||||
|
|
||||||
if (tag->value)
|
if (tag->value)
|
||||||
sendto_one_notice(source_p, ":*** %d: %s => %s", i, tag->key, tag->value);
|
sendto_one_notice(source_p, ":*** %zu: %s => %s", i, tag->key, tag->value);
|
||||||
else
|
else
|
||||||
sendto_one_notice(source_p, ":*** %d: %s", i, tag->key);
|
sendto_one_notice(source_p, ":*** %zu: %s", i, tag->key);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -31,7 +31,6 @@
|
||||||
|
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "client.h"
|
#include "client.h"
|
||||||
#include "common.h"
|
|
||||||
#include "ircd.h"
|
#include "ircd.h"
|
||||||
#include "match.h"
|
#include "match.h"
|
||||||
#include "numeric.h"
|
#include "numeric.h"
|
||||||
|
|
|
@ -31,7 +31,6 @@
|
||||||
|
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "client.h"
|
#include "client.h"
|
||||||
#include "common.h"
|
|
||||||
#include "ircd.h"
|
#include "ircd.h"
|
||||||
#include "match.h"
|
#include "match.h"
|
||||||
#include "numeric.h"
|
#include "numeric.h"
|
||||||
|
@ -91,7 +90,7 @@ mo_sendbans(struct MsgBuf *msgbuf_p, struct Client *client_p, struct Client *sou
|
||||||
{
|
{
|
||||||
struct ConfItem *aconf;
|
struct ConfItem *aconf;
|
||||||
rb_dlink_node *ptr;
|
rb_dlink_node *ptr;
|
||||||
int i, count;
|
int count;
|
||||||
const char *target, *mask2;
|
const char *target, *mask2;
|
||||||
struct Client *server_p;
|
struct Client *server_p;
|
||||||
struct rb_radixtree_iteration_state state;
|
struct rb_radixtree_iteration_state state;
|
||||||
|
|
|
@ -92,7 +92,7 @@ mr_webirc(struct MsgBuf *msgbuf_p, struct Client *client_p, struct Client *sourc
|
||||||
IsGotId(client_p) ? client_p->username : "webirc",
|
IsGotId(client_p) ? client_p->username : "webirc",
|
||||||
IsGotId(client_p) ? client_p->username : "webirc",
|
IsGotId(client_p) ? client_p->username : "webirc",
|
||||||
(struct sockaddr *) &client_p->localClient->ip,
|
(struct sockaddr *) &client_p->localClient->ip,
|
||||||
client_p->localClient->ip.ss_family, NULL);
|
GET_SS_FAMILY(&client_p->localClient->ip), NULL);
|
||||||
if (aconf == NULL || !(aconf->status & CONF_CLIENT))
|
if (aconf == NULL || !(aconf->status & CONF_CLIENT))
|
||||||
return;
|
return;
|
||||||
if (!IsConfDoSpoofIp(aconf) || irccmp(aconf->info.name, "webirc."))
|
if (!IsConfDoSpoofIp(aconf) || irccmp(aconf->info.name, "webirc."))
|
||||||
|
@ -145,7 +145,7 @@ mr_webirc(struct MsgBuf *msgbuf_p, struct Client *client_p, struct Client *sourc
|
||||||
|
|
||||||
/* Check dlines now, klines will be checked on registration */
|
/* Check dlines now, klines will be checked on registration */
|
||||||
if((aconf = find_dline((struct sockaddr *)&source_p->localClient->ip,
|
if((aconf = find_dline((struct sockaddr *)&source_p->localClient->ip,
|
||||||
source_p->localClient->ip.ss_family)))
|
GET_SS_FAMILY(&source_p->localClient->ip))))
|
||||||
{
|
{
|
||||||
if(!(aconf->status & CONF_EXEMPTDLINE))
|
if(!(aconf->status & CONF_EXEMPTDLINE))
|
||||||
{
|
{
|
||||||
|
|
|
@ -13,7 +13,7 @@ SYMLINKS= topic accept cmode admin names links away whowas \
|
||||||
version kick who invite quit join list nick oper part \
|
version kick who invite quit join list nick oper part \
|
||||||
time credits motd userhost users whois ison lusers \
|
time credits motd userhost users whois ison lusers \
|
||||||
user help pass error challenge knock ping pong \
|
user help pass error challenge knock ping pong \
|
||||||
cprivmsg cnotice map trace chantrace extban monitor
|
map trace chantrace extban monitor
|
||||||
|
|
||||||
all:
|
all:
|
||||||
build:
|
build:
|
||||||
|
|
|
@ -1,5 +0,0 @@
|
||||||
CNOTICE <nick> <channel> :<text>
|
|
||||||
|
|
||||||
Providing you are opped (+o) or voiced (+v) in <channel>, and <nick>
|
|
||||||
is a member of <channel>, CNOTICE generates a NOTICE towards
|
|
||||||
<nick>. CNOTICE bypasses any anti-spam measures in place.
|
|
|
@ -1,5 +0,0 @@
|
||||||
CPRIVMSG <nick> <channel> :<text>
|
|
||||||
|
|
||||||
Providing you are opped (+o) or voiced (+v) in <channel>, and <nick>
|
|
||||||
is a member of <channel>, CPRIVMSG generates a PRIVMSG towards
|
|
||||||
<nick>. CPRIVMSG bypasses any anti-spam measures in place.
|
|
|
@ -2,23 +2,23 @@ Help topics available to opers:
|
||||||
|
|
||||||
ACCEPT ADMIN AWAY CAPAB
|
ACCEPT ADMIN AWAY CAPAB
|
||||||
CHALLENGE CHANTRACE CLOSE CMODE
|
CHALLENGE CHANTRACE CLOSE CMODE
|
||||||
CNOTICE CONNECT CPRIVMSG CREDITS
|
CONNECT CREDITS DIE DLINE
|
||||||
DIE DLINE ERROR ETRACE
|
ERROR ETRACE EXTBAN HELP
|
||||||
EXTBAN HELP INDEX INFO
|
INDEX INFO INVITE ISON
|
||||||
INVITE ISON JOIN KICK
|
JOIN KICK KILL KLINE
|
||||||
KILL KLINE KNOCK LINKS
|
KNOCK LINKS LIST LOCOPS
|
||||||
LIST LOCOPS LUSERS MAP
|
LUSERS MAP MASKTRACE MODLIST
|
||||||
MASKTRACE MODLIST MODLOAD MODRELOAD
|
MODLOAD MODRELOAD MODRESTART MODUNLOAD
|
||||||
MODRESTART MODUNLOAD MONITOR MOTD
|
MONITOR MOTD NAMES NICK
|
||||||
NAMES NICK NOTICE OPER
|
NOTICE OPER OPERSPY OPERWALL
|
||||||
OPERSPY OPERWALL PART PASS
|
PART PASS PING PONG
|
||||||
PING PONG POST PRIVMSG
|
POST PRIVMSG PRIVS QUIT
|
||||||
PRIVS QUIT REHASH RESTART
|
REHASH RESTART RESV SCAN
|
||||||
RESV SCAN SERVER SET
|
SERVER SET SJOIN SNOMASK
|
||||||
SJOIN SNOMASK SQUIT STATS
|
SQUIT STATS SVINFO TESTGECOS
|
||||||
SVINFO TESTGECOS TESTLINE TESTMASK
|
TESTLINE TESTMASK TIME TOPIC
|
||||||
TIME TOPIC TRACE UHELP
|
TRACE UHELP UMODE UNDLINE
|
||||||
UMODE UNDLINE UNKLINE UNREJECT
|
UNKLINE UNREJECT UNRESV UNXLINE
|
||||||
UNRESV UNXLINE USER USERHOST
|
USER USERHOST USERS VERSION
|
||||||
USERS VERSION WALLOPS WHO
|
WALLOPS WHO WHOIS WHOWAS
|
||||||
WHOIS WHOWAS XLINE
|
XLINE
|
||||||
|
|
|
@ -1,14 +1,14 @@
|
||||||
Help topics available to users:
|
Help topics available to users:
|
||||||
|
|
||||||
ACCEPT ADMIN AWAY CHALLENGE
|
ACCEPT ADMIN AWAY CHALLENGE
|
||||||
CHANTRACE CMODE CNOTICE CPRIVMSG
|
CHANTRACE CMODE CREDITS ERROR
|
||||||
CREDITS ERROR EXTBAN HELP
|
EXTBAN HELP INDEX INFO
|
||||||
INDEX INFO INVITE ISON
|
INVITE ISON JOIN KICK
|
||||||
JOIN KICK KNOCK LINKS
|
KNOCK LINKS LIST LUSERS
|
||||||
LIST LUSERS MAP MONITOR
|
MAP MONITOR MOTD NAMES
|
||||||
MOTD NAMES NICK NOTICE
|
NICK NOTICE OPER PART
|
||||||
OPER PART PASS PING
|
PASS PING PONG PRIVMSG
|
||||||
PONG PRIVMSG QUIT STATS
|
QUIT STATS TIME TOPIC
|
||||||
TIME TOPIC TRACE UMODE
|
TRACE UMODE USER USERHOST
|
||||||
USER USERHOST USERS VERSION
|
USERS VERSION WHO WHOIS
|
||||||
WHO WHOIS WHOWAS
|
WHOWAS
|
||||||
|
|
|
@ -36,7 +36,7 @@ struct Blacklist {
|
||||||
int ipv6; /* Does this blacklist support IPv6 lookups? */
|
int ipv6; /* Does this blacklist support IPv6 lookups? */
|
||||||
char host[IRCD_RES_HOSTLEN + 1];
|
char host[IRCD_RES_HOSTLEN + 1];
|
||||||
rb_dlink_list filters; /* Filters for queries */
|
rb_dlink_list filters; /* Filters for queries */
|
||||||
char reject_reason[IRCD_BUFSIZE];
|
char reject_reason[BUFSIZE];
|
||||||
unsigned int hits;
|
unsigned int hits;
|
||||||
time_t lastwarning;
|
time_t lastwarning;
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,6 +1,8 @@
|
||||||
#ifndef INCLUDED_CACHE_H
|
#ifndef INCLUDED_CACHE_H
|
||||||
#define INCLUDED_CACHE_H
|
#define INCLUDED_CACHE_H
|
||||||
|
|
||||||
|
#include "rb_dictionary.h"
|
||||||
|
|
||||||
#define HELP_MAX 100
|
#define HELP_MAX 100
|
||||||
|
|
||||||
#define CACHEFILELEN 30
|
#define CACHEFILELEN 30
|
||||||
|
@ -43,8 +45,7 @@ void send_user_motd(struct Client *);
|
||||||
void send_oper_motd(struct Client *);
|
void send_oper_motd(struct Client *);
|
||||||
void cache_user_motd(void);
|
void cache_user_motd(void);
|
||||||
|
|
||||||
struct Dictionary;
|
extern rb_dictionary *help_dict_oper;
|
||||||
extern struct Dictionary *help_dict_oper;
|
extern rb_dictionary *help_dict_user;
|
||||||
extern struct Dictionary *help_dict_user;
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
|
@ -21,9 +21,12 @@
|
||||||
#ifndef __CAPABILITY_H__
|
#ifndef __CAPABILITY_H__
|
||||||
#define __CAPABILITY_H__
|
#define __CAPABILITY_H__
|
||||||
|
|
||||||
|
#include "stdinc.h"
|
||||||
|
#include "rb_dictionary.h"
|
||||||
|
|
||||||
struct CapabilityIndex {
|
struct CapabilityIndex {
|
||||||
const char *name;
|
const char *name;
|
||||||
struct Dictionary *cap_dict;
|
rb_dictionary *cap_dict;
|
||||||
unsigned int highest_bit;
|
unsigned int highest_bit;
|
||||||
rb_dlink_node node;
|
rb_dlink_node node;
|
||||||
};
|
};
|
||||||
|
|
|
@ -73,7 +73,7 @@ struct Channel
|
||||||
unsigned int join_count; /* joins within delta */
|
unsigned int join_count; /* joins within delta */
|
||||||
unsigned int join_delta; /* last ts of join */
|
unsigned int join_delta; /* last ts of join */
|
||||||
|
|
||||||
unsigned long bants;
|
time_t bants;
|
||||||
time_t channelts;
|
time_t channelts;
|
||||||
char *chname;
|
char *chname;
|
||||||
|
|
||||||
|
@ -93,7 +93,7 @@ struct membership
|
||||||
struct Client *client_p;
|
struct Client *client_p;
|
||||||
unsigned int flags;
|
unsigned int flags;
|
||||||
|
|
||||||
unsigned long bants;
|
time_t bants;
|
||||||
};
|
};
|
||||||
|
|
||||||
#define BANLEN 195
|
#define BANLEN 195
|
||||||
|
@ -213,7 +213,7 @@ extern void destroy_channel(struct Channel *);
|
||||||
|
|
||||||
extern int can_send(struct Channel *chptr, struct Client *who,
|
extern int can_send(struct Channel *chptr, struct Client *who,
|
||||||
struct membership *);
|
struct membership *);
|
||||||
extern int flood_attack_channel(int p_or_n, struct Client *source_p,
|
extern bool flood_attack_channel(int p_or_n, struct Client *source_p,
|
||||||
struct Channel *chptr, char *chname);
|
struct Channel *chptr, char *chname);
|
||||||
extern int is_banned(struct Channel *chptr, struct Client *who,
|
extern int is_banned(struct Channel *chptr, struct Client *who,
|
||||||
struct membership *msptr, const char *, const char *, const char **);
|
struct membership *msptr, const char *, const char *, const char **);
|
||||||
|
@ -231,7 +231,7 @@ extern void invalidate_bancache_user(struct Client *);
|
||||||
|
|
||||||
extern void free_channel_list(rb_dlink_list *);
|
extern void free_channel_list(rb_dlink_list *);
|
||||||
|
|
||||||
extern int check_channel_name(const char *name);
|
extern bool check_channel_name(const char *name);
|
||||||
|
|
||||||
extern void channel_member_names(struct Channel *chptr, struct Client *,
|
extern void channel_member_names(struct Channel *chptr, struct Client *,
|
||||||
int show_eon);
|
int show_eon);
|
||||||
|
@ -264,7 +264,7 @@ extern void set_channel_mlock(struct Client *client_p, struct Client *source_p,
|
||||||
|
|
||||||
extern struct ChannelMode chmode_table[256];
|
extern struct ChannelMode chmode_table[256];
|
||||||
|
|
||||||
extern int add_id(struct Client *source_p, struct Channel *chptr, const char *banid,
|
extern bool add_id(struct Client *source_p, struct Channel *chptr, const char *banid,
|
||||||
const char *forward, rb_dlink_list * list, long mode_type);
|
const char *forward, rb_dlink_list * list, long mode_type);
|
||||||
|
|
||||||
extern struct Ban * del_id(struct Channel *chptr, const char *banid, rb_dlink_list * list,
|
extern struct Ban * del_id(struct Channel *chptr, const char *banid, rb_dlink_list * list,
|
||||||
|
|
|
@ -26,11 +26,7 @@
|
||||||
#ifndef INCLUDED_client_h
|
#ifndef INCLUDED_client_h
|
||||||
#define INCLUDED_client_h
|
#define INCLUDED_client_h
|
||||||
|
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
|
|
||||||
#if !defined(CONFIG_CHARYBDIS_LEVEL_1)
|
|
||||||
#error Incorrect config.h for this revision of ircd.
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#include "ircd_defs.h"
|
#include "ircd_defs.h"
|
||||||
#include "channel.h"
|
#include "channel.h"
|
||||||
|
@ -171,6 +167,8 @@ struct Client
|
||||||
struct LocalUser
|
struct LocalUser
|
||||||
{
|
{
|
||||||
rb_dlink_node tnode; /* This is the node for the local list type the client is on */
|
rb_dlink_node tnode; /* This is the node for the local list type the client is on */
|
||||||
|
rb_dlink_list connids; /* This is the list of connids to free */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The following fields are allocated only for local clients
|
* The following fields are allocated only for local clients
|
||||||
* (directly connected to *this* server with a socket.
|
* (directly connected to *this* server with a socket.
|
||||||
|
@ -237,7 +235,6 @@ struct LocalUser
|
||||||
|
|
||||||
time_t next_away; /* Don't allow next away before... */
|
time_t next_away; /* Don't allow next away before... */
|
||||||
time_t last;
|
time_t last;
|
||||||
uint32_t connid;
|
|
||||||
|
|
||||||
/* clients allowed to talk through +g */
|
/* clients allowed to talk through +g */
|
||||||
rb_dlink_list allow_list;
|
rb_dlink_list allow_list;
|
||||||
|
@ -276,7 +273,6 @@ struct LocalUser
|
||||||
|
|
||||||
struct _ssl_ctl *ssl_ctl; /* which ssl daemon we're associate with */
|
struct _ssl_ctl *ssl_ctl; /* which ssl daemon we're associate with */
|
||||||
struct _ssl_ctl *z_ctl; /* second ctl for ssl+zlib */
|
struct _ssl_ctl *z_ctl; /* second ctl for ssl+zlib */
|
||||||
uint32_t zconnid;
|
|
||||||
uint32_t localflags;
|
uint32_t localflags;
|
||||||
struct ZipStats *zipstats; /* zipstats */
|
struct ZipStats *zipstats; /* zipstats */
|
||||||
uint16_t cork_count; /* used for corking/uncorking connections */
|
uint16_t cork_count; /* used for corking/uncorking connections */
|
||||||
|
@ -609,4 +605,8 @@ extern char *generate_uid(void);
|
||||||
void allocate_away(struct Client *);
|
void allocate_away(struct Client *);
|
||||||
void free_away(struct Client *);
|
void free_away(struct Client *);
|
||||||
|
|
||||||
|
uint32_t connid_get(struct Client *client_p);
|
||||||
|
void connid_put(uint32_t id);
|
||||||
|
void client_release_connids(struct Client *client_p);
|
||||||
|
|
||||||
#endif /* INCLUDED_client_h */
|
#endif /* INCLUDED_client_h */
|
||||||
|
|
|
@ -1,58 +0,0 @@
|
||||||
/*
|
|
||||||
* ircd-ratbox: A slightly useful ircd.
|
|
||||||
* common.h: An ircd header common to most code.
|
|
||||||
*
|
|
||||||
* Copyright (C) 1990 Jarkko Oikarinen and University of Oulu, Co Center
|
|
||||||
* Copyright (C) 1996-2002 Hybrid Development Team
|
|
||||||
* Copyright (C) 2002-2004 ircd-ratbox development team
|
|
||||||
*
|
|
||||||
* 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 2 of the License, 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., 59 Temple Place, Suite 330, Boston, MA 02111-1307
|
|
||||||
* USA
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef INCLUDED_common_h
|
|
||||||
#define INCLUDED_common_h
|
|
||||||
|
|
||||||
|
|
||||||
#ifndef NULL
|
|
||||||
#define NULL 0
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
/* Blah. I use these a lot. -Dianora */
|
|
||||||
#ifdef YES
|
|
||||||
#undef YES
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define YES 1
|
|
||||||
|
|
||||||
#ifdef NO
|
|
||||||
#undef NO
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define NO 0
|
|
||||||
|
|
||||||
/* Just blindly define our own MIN/MAX macro */
|
|
||||||
|
|
||||||
#define IRCD_MAX(a, b) ((a) > (b) ? (a) : (b))
|
|
||||||
#define IRCD_MIN(a, b) ((a) < (b) ? (a) : (b))
|
|
||||||
|
|
||||||
/* Right out of the RFC */
|
|
||||||
#define IRCD_BUFSIZE 512
|
|
||||||
|
|
||||||
/* readbuf size */
|
|
||||||
#define READBUF_SIZE 16384
|
|
||||||
|
|
||||||
#endif /* INCLUDED_common_h */
|
|
116
include/config.h
116
include/config.h
|
@ -1,116 +0,0 @@
|
||||||
/*
|
|
||||||
* ircd-ratbox: A slightly useful ircd.
|
|
||||||
* config.h: The ircd compile-time-configurable header.
|
|
||||||
*
|
|
||||||
* Copyright (C) 1990 Jarkko Oikarinen and University of Oulu, Co Center
|
|
||||||
* Copyright (C) 1996-2002 Hybrid Development Team
|
|
||||||
* Copyright (C) 2002-2004 ircd-ratbox development team
|
|
||||||
*
|
|
||||||
* 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 2 of the License, 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., 59 Temple Place, Suite 330, Boston, MA 02111-1307
|
|
||||||
* USA
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef INCLUDED_config_h
|
|
||||||
#define INCLUDED_config_h
|
|
||||||
|
|
||||||
#include "setup.h"
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Directory paths and filenames for UNIX systems.
|
|
||||||
* IRCD_PREFIX is set using ./configure --prefix, see INSTALL.
|
|
||||||
* The other defaults should be fine.
|
|
||||||
*
|
|
||||||
* NOTE: CHANGING THESE WILL NOT ALTER THE DIRECTORY THAT FILES WILL
|
|
||||||
* BE INSTALLED TO. IF YOU CHANGE THESE, DO NOT USE MAKE INSTALL,
|
|
||||||
* BUT COPY THE FILES MANUALLY TO WHERE YOU WANT THEM.
|
|
||||||
*
|
|
||||||
* IRCD_PREFIX = prefix for all directories,
|
|
||||||
* DPATH = root directory of installation,
|
|
||||||
* BINPATH = directory for binary files,
|
|
||||||
* ETCPATH = directory for configuration files,
|
|
||||||
* LOGPATH = directory for logfiles,
|
|
||||||
* MODPATH = directory for modules,
|
|
||||||
* AUTOMODPATH = directory for autoloaded modules
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* dirs */
|
|
||||||
#define DPATH IRCD_PREFIX
|
|
||||||
#define BINPATH IRCD_PREFIX "/bin/"
|
|
||||||
#define MODPATH MODULE_DIR
|
|
||||||
#define AUTOMODPATH MODULE_DIR "/autoload/"
|
|
||||||
#define ETCPATH ETC_DIR
|
|
||||||
#define LOGPATH LOG_DIR
|
|
||||||
#define UHPATH HELP_DIR "/users"
|
|
||||||
#define HPATH HELP_DIR "/opers"
|
|
||||||
|
|
||||||
/* files */
|
|
||||||
#define SPATH BINPATH "/" PROGRAM_PREFIX "charybdis" /* ircd executable */
|
|
||||||
#define CPATH ETCPATH "/ircd.conf" /* ircd.conf file */
|
|
||||||
#define MPATH ETCPATH "/ircd.motd" /* MOTD file */
|
|
||||||
#define LPATH LOGPATH "/ircd.log" /* ircd logfile */
|
|
||||||
#define PPATH PKGRUNDIR "/ircd.pid" /* pid file */
|
|
||||||
#define OPATH ETCPATH "/opers.motd" /* oper MOTD file */
|
|
||||||
#define DBPATH PKGLOCALSTATEDIR "/ban.db" /* bandb file */
|
|
||||||
|
|
||||||
/* IGNORE_BOGUS_TS
|
|
||||||
* Ignore bogus timestamps from other servers. Yes this will desync
|
|
||||||
* the network, but it will allow chanops to resync with a valid non TS 0
|
|
||||||
*
|
|
||||||
* This should be enabled network wide, or not at all.
|
|
||||||
*/
|
|
||||||
#undef IGNORE_BOGUS_TS
|
|
||||||
|
|
||||||
/* HANGONGOODLINK and HANGONRETRYDELAY
|
|
||||||
* Often net breaks for a short time and it's useful to try to
|
|
||||||
* establishing the same connection again faster than CONNECTFREQUENCY
|
|
||||||
* would allow. But, to keep trying on bad connection, we require
|
|
||||||
* that connection has been open for certain minimum time
|
|
||||||
* (HANGONGOODLINK) and we give the net few seconds to steady
|
|
||||||
* (HANGONRETRYDELAY). This latter has to be long enough that the
|
|
||||||
* other end of the connection has time to notice it broke too.
|
|
||||||
* 1997/09/18 recommended values by ThemBones for modern EFnet
|
|
||||||
*/
|
|
||||||
#define HANGONRETRYDELAY 60 /* Recommended value: 30-60 seconds */
|
|
||||||
#define HANGONGOODLINK 3600 /* Recommended value: 30-60 minutes */
|
|
||||||
|
|
||||||
/* KILLCHASETIMELIMIT -
|
|
||||||
* Max time from the nickname change that still causes KILL
|
|
||||||
* automatically to switch for the current nick of that user. (seconds)
|
|
||||||
*/
|
|
||||||
#define KILLCHASETIMELIMIT 90 /* Recommended value: 90 */
|
|
||||||
|
|
||||||
/* CHARYBDIS_SOMAXCONN
|
|
||||||
* Use SOMAXCONN if OS has it, otherwise use this value for the
|
|
||||||
* listen(); backlog. 5 for AIX/SUNOS, 25 for other OSs.
|
|
||||||
*/
|
|
||||||
#define CHARYBDIS_SOMAXCONN 25
|
|
||||||
|
|
||||||
/* MAX_BUFFER
|
|
||||||
* The amount of fds to reserve for clients exempt from limits
|
|
||||||
* and dns lookups.
|
|
||||||
*/
|
|
||||||
#define MAX_BUFFER 60
|
|
||||||
|
|
||||||
/* ----------------------------------------------------------------
|
|
||||||
* STOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOP
|
|
||||||
* ----------------------------------------------------------------
|
|
||||||
* The options below this line should NOT be modified.
|
|
||||||
* ----------------------------------------------------------------
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define CONFIG_CHARYBDIS_LEVEL_2
|
|
||||||
|
|
||||||
#include "defaults.h"
|
|
||||||
#endif /* INCLUDED_config_h */
|
|
|
@ -1,116 +0,0 @@
|
||||||
/*
|
|
||||||
* ircd-ratbox: A slightly useful ircd.
|
|
||||||
* config.h: The ircd compile-time-configurable header.
|
|
||||||
*
|
|
||||||
* Copyright (C) 1990 Jarkko Oikarinen and University of Oulu, Co Center
|
|
||||||
* Copyright (C) 1996-2002 Hybrid Development Team
|
|
||||||
* Copyright (C) 2002-2004 ircd-ratbox development team
|
|
||||||
*
|
|
||||||
* 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 2 of the License, 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., 59 Temple Place, Suite 330, Boston, MA 02111-1307
|
|
||||||
* USA
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef INCLUDED_config_h
|
|
||||||
#define INCLUDED_config_h
|
|
||||||
|
|
||||||
#include "setup.h"
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Directory paths and filenames for UNIX systems.
|
|
||||||
* IRCD_PREFIX is set using ./configure --prefix, see INSTALL.
|
|
||||||
* The other defaults should be fine.
|
|
||||||
*
|
|
||||||
* NOTE: CHANGING THESE WILL NOT ALTER THE DIRECTORY THAT FILES WILL
|
|
||||||
* BE INSTALLED TO. IF YOU CHANGE THESE, DO NOT USE MAKE INSTALL,
|
|
||||||
* BUT COPY THE FILES MANUALLY TO WHERE YOU WANT THEM.
|
|
||||||
*
|
|
||||||
* IRCD_PREFIX = prefix for all directories,
|
|
||||||
* DPATH = root directory of installation,
|
|
||||||
* BINPATH = directory for binary files,
|
|
||||||
* ETCPATH = directory for configuration files,
|
|
||||||
* LOGPATH = directory for logfiles,
|
|
||||||
* MODPATH = directory for modules,
|
|
||||||
* AUTOMODPATH = directory for autoloaded modules
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* dirs */
|
|
||||||
#define DPATH IRCD_PREFIX
|
|
||||||
#define BINPATH IRCD_PREFIX "/bin/"
|
|
||||||
#define MODPATH MODULE_DIR
|
|
||||||
#define AUTOMODPATH MODULE_DIR "/autoload/"
|
|
||||||
#define ETCPATH ETC_DIR
|
|
||||||
#define LOGPATH LOG_DIR
|
|
||||||
#define UHPATH HELP_DIR "/users"
|
|
||||||
#define HPATH HELP_DIR "/opers"
|
|
||||||
|
|
||||||
/* files */
|
|
||||||
#define SPATH BINPATH "/" PROGRAM_PREFIX "charybdis" /* ircd executable */
|
|
||||||
#define CPATH ETCPATH "/ircd.conf" /* ircd.conf file */
|
|
||||||
#define MPATH ETCPATH "/ircd.motd" /* MOTD file */
|
|
||||||
#define LPATH LOGPATH "/ircd.log" /* ircd logfile */
|
|
||||||
#define PPATH PKGRUNDIR "/ircd.pid" /* pid file */
|
|
||||||
#define OPATH ETCPATH "/opers.motd" /* oper MOTD file */
|
|
||||||
#define DBPATH PKGLOCALSTATEDIR "/ban.db" /* bandb file */
|
|
||||||
|
|
||||||
/* IGNORE_BOGUS_TS
|
|
||||||
* Ignore bogus timestamps from other servers. Yes this will desync
|
|
||||||
* the network, but it will allow chanops to resync with a valid non TS 0
|
|
||||||
*
|
|
||||||
* This should be enabled network wide, or not at all.
|
|
||||||
*/
|
|
||||||
#undef IGNORE_BOGUS_TS
|
|
||||||
|
|
||||||
/* HANGONGOODLINK and HANGONRETRYDELAY
|
|
||||||
* Often net breaks for a short time and it's useful to try to
|
|
||||||
* establishing the same connection again faster than CONNECTFREQUENCY
|
|
||||||
* would allow. But, to keep trying on bad connection, we require
|
|
||||||
* that connection has been open for certain minimum time
|
|
||||||
* (HANGONGOODLINK) and we give the net few seconds to steady
|
|
||||||
* (HANGONRETRYDELAY). This latter has to be long enough that the
|
|
||||||
* other end of the connection has time to notice it broke too.
|
|
||||||
* 1997/09/18 recommended values by ThemBones for modern EFnet
|
|
||||||
*/
|
|
||||||
#define HANGONRETRYDELAY 60 /* Recommended value: 30-60 seconds */
|
|
||||||
#define HANGONGOODLINK 3600 /* Recommended value: 30-60 minutes */
|
|
||||||
|
|
||||||
/* KILLCHASETIMELIMIT -
|
|
||||||
* Max time from the nickname change that still causes KILL
|
|
||||||
* automatically to switch for the current nick of that user. (seconds)
|
|
||||||
*/
|
|
||||||
#define KILLCHASETIMELIMIT 90 /* Recommended value: 90 */
|
|
||||||
|
|
||||||
/* CHARYBDIS_SOMAXCONN
|
|
||||||
* Use SOMAXCONN if OS has it, otherwise use this value for the
|
|
||||||
* listen(); backlog. 5 for AIX/SUNOS, 25 for other OSs.
|
|
||||||
*/
|
|
||||||
#define CHARYBDIS_SOMAXCONN 25
|
|
||||||
|
|
||||||
/* MAX_BUFFER
|
|
||||||
* The amount of fds to reserve for clients exempt from limits
|
|
||||||
* and dns lookups.
|
|
||||||
*/
|
|
||||||
#define MAX_BUFFER 60
|
|
||||||
|
|
||||||
/* ----------------------------------------------------------------
|
|
||||||
* STOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOPSTOP
|
|
||||||
* ----------------------------------------------------------------
|
|
||||||
* The options below this line should NOT be modified.
|
|
||||||
* ----------------------------------------------------------------
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define CONFIG_CHARYBDIS_LEVEL_2
|
|
||||||
|
|
||||||
#include "defaults.h"
|
|
||||||
#endif /* INCLUDED_config_h */
|
|
|
@ -25,14 +25,38 @@
|
||||||
#ifndef INCLUDED_defaults_h
|
#ifndef INCLUDED_defaults_h
|
||||||
#define INCLUDED_defaults_h
|
#define INCLUDED_defaults_h
|
||||||
|
|
||||||
/* this file is included (only) at the end of config.h, to supply default
|
/* /!\ DANGER WILL ROBINSON! DANGER! /!\
|
||||||
* values for things which are now configurable at runtime.
|
*
|
||||||
|
* Do not mess with these values unless you know what you are doing!
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "setup.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* First, set other fd limits based on values from user
|
* First, set other fd limits based on values from user
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
typedef enum {
|
||||||
|
IRCD_PATH_PREFIX,
|
||||||
|
IRCD_PATH_MODULES,
|
||||||
|
IRCD_PATH_AUTOLOAD_MODULES,
|
||||||
|
IRCD_PATH_ETC,
|
||||||
|
IRCD_PATH_LOG,
|
||||||
|
IRCD_PATH_USERHELP,
|
||||||
|
IRCD_PATH_OPERHELP,
|
||||||
|
IRCD_PATH_IRCD_EXEC,
|
||||||
|
IRCD_PATH_IRCD_CONF,
|
||||||
|
IRCD_PATH_IRCD_MOTD,
|
||||||
|
IRCD_PATH_IRCD_LOG,
|
||||||
|
IRCD_PATH_IRCD_PID,
|
||||||
|
IRCD_PATH_IRCD_OMOTD,
|
||||||
|
IRCD_PATH_BANDB,
|
||||||
|
IRCD_PATH_BIN,
|
||||||
|
IRCD_PATH_LIBEXEC,
|
||||||
|
IRCD_PATH_COUNT
|
||||||
|
} ircd_path_t;
|
||||||
|
|
||||||
|
extern const char *ircd_paths[IRCD_PATH_COUNT];
|
||||||
|
|
||||||
#define MAXCONNECTIONS 65535 /* default max connections if getrlimit doesn't work */
|
#define MAXCONNECTIONS 65535 /* default max connections if getrlimit doesn't work */
|
||||||
/* class {} default values */
|
/* class {} default values */
|
||||||
|
@ -59,5 +83,64 @@
|
||||||
#define JOIN_LEAVE_COUNT_EXPIRE_TIME 120
|
#define JOIN_LEAVE_COUNT_EXPIRE_TIME 120
|
||||||
#define MIN_SPAM_NUM 5
|
#define MIN_SPAM_NUM 5
|
||||||
#define MIN_SPAM_TIME 60
|
#define MIN_SPAM_TIME 60
|
||||||
#define CONFIG_CHARYBDIS_LEVEL_1
|
|
||||||
|
/*
|
||||||
|
* Directory paths and filenames for UNIX systems.
|
||||||
|
* IRCD_PREFIX is set using ./configure --prefix, see INSTALL.
|
||||||
|
*
|
||||||
|
* IRCD_PREFIX = prefix for all directories,
|
||||||
|
* DPATH = root directory of installation,
|
||||||
|
* BINPATH = directory for binary files,
|
||||||
|
* ETCPATH = directory for configuration files,
|
||||||
|
* LOGPATH = directory for logfiles,
|
||||||
|
* MODPATH = directory for modules,
|
||||||
|
* AUTOMODPATH = directory for autoloaded modules
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define DPATH IRCD_PREFIX
|
||||||
|
#define BINPATH IRCD_PREFIX "/bin/"
|
||||||
|
#define MODPATH MODULE_DIR
|
||||||
|
#define AUTOMODPATH MODULE_DIR "/autoload/"
|
||||||
|
#define ETCPATH ETC_DIR
|
||||||
|
#define LOGPATH LOG_DIR
|
||||||
|
#define UHPATH HELP_DIR "/users"
|
||||||
|
#define HPATH HELP_DIR "/opers"
|
||||||
|
#define SPATH BINPATH "/" PROGRAM_PREFIX "charybdis" /* ircd executable */
|
||||||
|
#define CPATH ETCPATH "/ircd.conf" /* ircd.conf file */
|
||||||
|
#define MPATH ETCPATH "/ircd.motd" /* MOTD file */
|
||||||
|
#define LPATH LOGPATH "/ircd.log" /* ircd logfile */
|
||||||
|
#define PPATH PKGRUNDIR "/ircd.pid" /* pid file */
|
||||||
|
#define OPATH ETCPATH "/opers.motd" /* oper MOTD file */
|
||||||
|
#define DBPATH PKGLOCALSTATEDIR "/ban.db" /* bandb file */
|
||||||
|
|
||||||
|
/* HANGONGOODLINK and HANGONRETRYDELAY
|
||||||
|
* Often net breaks for a short time and it's useful to try to
|
||||||
|
* establishing the same connection again faster than CONNECTFREQUENCY
|
||||||
|
* would allow. But, to keep trying on bad connection, we require
|
||||||
|
* that connection has been open for certain minimum time
|
||||||
|
* (HANGONGOODLINK) and we give the net few seconds to steady
|
||||||
|
* (HANGONRETRYDELAY). This latter has to be long enough that the
|
||||||
|
* other end of the connection has time to notice it broke too.
|
||||||
|
*/
|
||||||
|
#define HANGONRETRYDELAY 60 /* Recommended value: 30-60 seconds */
|
||||||
|
#define HANGONGOODLINK 3600 /* Recommended value: 30-60 minutes */
|
||||||
|
|
||||||
|
/* KILLCHASETIMELIMIT -
|
||||||
|
* Max time from the nickname change that still causes KILL
|
||||||
|
* automatically to switch for the current nick of that user. (seconds)
|
||||||
|
*/
|
||||||
|
#define KILLCHASETIMELIMIT 90 /* Recommended value: 90 */
|
||||||
|
|
||||||
|
/* MAX_BUFFER
|
||||||
|
* The amount of fds to reserve for clients exempt from limits
|
||||||
|
* and dns lookups.
|
||||||
|
*/
|
||||||
|
#define MAX_BUFFER 60
|
||||||
|
|
||||||
|
/* CHARYBDIS_SOMAXCONN
|
||||||
|
* Use SOMAXCONN if OS has it, otherwise use this value for the
|
||||||
|
* listen(); backlog. 5 for AIX/SUNOS, 25 for other OSs.
|
||||||
|
*/
|
||||||
|
#define CHARYBDIS_SOMAXCONN 25
|
||||||
|
|
||||||
#endif /* INCLUDED_defaults_h */
|
#endif /* INCLUDED_defaults_h */
|
||||||
|
|
|
@ -34,12 +34,15 @@ extern rb_dlink_list nameservers;
|
||||||
typedef void (*DNSCB)(const char *res, int status, int aftype, void *data);
|
typedef void (*DNSCB)(const char *res, int status, int aftype, void *data);
|
||||||
typedef void (*DNSLISTCB)(int resc, const char *resv[], int status, void *data);
|
typedef void (*DNSLISTCB)(int resc, const char *resv[], int status, void *data);
|
||||||
|
|
||||||
uint16_t lookup_hostname(const char *hostname, int aftype, DNSCB callback, void *data);
|
uint32_t lookup_hostname(const char *hostname, int aftype, DNSCB callback, void *data);
|
||||||
uint16_t lookup_ip(const char *hostname, int aftype, DNSCB callback, void *data);
|
uint32_t lookup_ip(const char *hostname, int aftype, DNSCB callback, void *data);
|
||||||
void cancel_lookup(uint16_t xid);
|
void cancel_lookup(uint32_t xid);
|
||||||
|
void cancel_dns_stats(uint32_t xid);
|
||||||
|
|
||||||
void dns_results_callback(const char *callid, const char *status, const char *aftype, const char *results);
|
void dns_results_callback(const char *callid, const char *status, const char *aftype, const char *results);
|
||||||
void dns_stats_results_callback(const char *callid, const char *status, int resc, const char *resv[]);
|
void dns_stats_results_callback(const char *callid, const char *status, int resc, const char *resv[]);
|
||||||
void init_nameserver_cache(void);
|
|
||||||
bool reload_nameservers(void);
|
void init_dns(void);
|
||||||
|
void reload_nameservers(void);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -25,12 +25,12 @@
|
||||||
#ifndef INCLUDED_hash_h
|
#ifndef INCLUDED_hash_h
|
||||||
#define INCLUDED_hash_h
|
#define INCLUDED_hash_h
|
||||||
|
|
||||||
struct Dictionary;
|
#include "rb_dictionary.h"
|
||||||
struct rb_radixtree;
|
#include "rb_radixtree.h"
|
||||||
|
|
||||||
extern struct Dictionary *nd_dict;
|
extern rb_dictionary *nd_dict;
|
||||||
extern struct rb_radixtree *resv_tree;
|
extern rb_radixtree *resv_tree;
|
||||||
extern struct rb_radixtree *channel_tree;
|
extern rb_radixtree *channel_tree;
|
||||||
|
|
||||||
/* Magic value for FNV hash functions */
|
/* Magic value for FNV hash functions */
|
||||||
#define FNV1_32_INIT 0x811c9dc5UL
|
#define FNV1_32_INIT 0x811c9dc5UL
|
||||||
|
@ -65,10 +65,10 @@ struct ConfItem;
|
||||||
struct cachefile;
|
struct cachefile;
|
||||||
struct nd_entry;
|
struct nd_entry;
|
||||||
|
|
||||||
extern u_int32_t fnv_hash_upper(const unsigned char *s, int bits);
|
extern uint32_t fnv_hash_upper(const unsigned char *s, int bits);
|
||||||
extern u_int32_t fnv_hash(const unsigned char *s, int bits);
|
extern uint32_t fnv_hash(const unsigned char *s, int bits);
|
||||||
extern u_int32_t fnv_hash_len(const unsigned char *s, int bits, int len);
|
extern uint32_t fnv_hash_len(const unsigned char *s, int bits, int len);
|
||||||
extern u_int32_t fnv_hash_upper_len(const unsigned char *s, int bits, int len);
|
extern uint32_t fnv_hash_upper_len(const unsigned char *s, int bits, int len);
|
||||||
|
|
||||||
extern void init_hash(void);
|
extern void init_hash(void);
|
||||||
|
|
||||||
|
@ -95,11 +95,8 @@ extern void del_from_resv_hash(const char *name, struct ConfItem *aconf);
|
||||||
extern struct ConfItem *hash_find_resv(const char *name);
|
extern struct ConfItem *hash_find_resv(const char *name);
|
||||||
extern void clear_resv_hash(void);
|
extern void clear_resv_hash(void);
|
||||||
|
|
||||||
void add_to_cli_connid_hash(struct Client *client_p);
|
void add_to_cli_connid_hash(struct Client *client_p, uint32_t id);
|
||||||
void del_from_cli_connid_hash(struct Client *client_p);
|
void del_from_cli_connid_hash(uint32_t id);
|
||||||
struct Client *find_cli_connid_hash(uint32_t connid);
|
struct Client *find_cli_connid_hash(uint32_t connid);
|
||||||
|
|
||||||
void add_to_zconnid_hash(struct Client *client_p);
|
|
||||||
void del_from_zconnid_hash(struct Client *client_p);
|
|
||||||
|
|
||||||
#endif /* INCLUDED_hash_h */
|
#endif /* INCLUDED_hash_h */
|
||||||
|
|
|
@ -54,7 +54,7 @@ struct ConfItem *find_dline(struct sockaddr *, int);
|
||||||
#define find_kline(x) (find_conf_by_address((x)->host, (x)->sockhost, \
|
#define find_kline(x) (find_conf_by_address((x)->host, (x)->sockhost, \
|
||||||
(x)->orighost, \
|
(x)->orighost, \
|
||||||
(struct sockaddr *)&(x)->localClient->ip, CONF_KILL,\
|
(struct sockaddr *)&(x)->localClient->ip, CONF_KILL,\
|
||||||
(x)->localClient->ip.ss_family, (x)->username, NULL))
|
GET_SS_FAMILY(&(x)->localClient->ip), (x)->username, NULL))
|
||||||
|
|
||||||
void report_auth(struct Client *);
|
void report_auth(struct Client *);
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
|
|
|
@ -25,7 +25,7 @@
|
||||||
#ifndef INCLUDED_ircd_h
|
#ifndef INCLUDED_ircd_h
|
||||||
#define INCLUDED_ircd_h
|
#define INCLUDED_ircd_h
|
||||||
|
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
|
|
||||||
struct Client;
|
struct Client;
|
||||||
struct rb_dlink_list;
|
struct rb_dlink_list;
|
||||||
|
@ -99,8 +99,8 @@ extern int testing_conf;
|
||||||
|
|
||||||
extern struct ev_entry *check_splitmode_ev;
|
extern struct ev_entry *check_splitmode_ev;
|
||||||
|
|
||||||
extern bool ssl_ok;
|
extern bool ircd_ssl_ok;
|
||||||
extern bool zlib_ok;
|
extern bool ircd_zlib_ok;
|
||||||
extern int maxconnections;
|
extern int maxconnections;
|
||||||
|
|
||||||
void ircd_shutdown(const char *reason);
|
void ircd_shutdown(const char *reason);
|
||||||
|
|
|
@ -35,7 +35,7 @@
|
||||||
#ifndef INCLUDED_ircd_defs_h
|
#ifndef INCLUDED_ircd_defs_h
|
||||||
#define INCLUDED_ircd_defs_h
|
#define INCLUDED_ircd_defs_h
|
||||||
|
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
|
|
||||||
/* For those unfamiliar with GNU format attributes, a is the 1 based
|
/* For those unfamiliar with GNU format attributes, a is the 1 based
|
||||||
* argument number of the format string, and b is the 1 based argument
|
* argument number of the format string, and b is the 1 based argument
|
||||||
|
@ -56,8 +56,12 @@
|
||||||
#define IRC_DEPRECATED
|
#define IRC_DEPRECATED
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if !defined(CONFIG_CHARYBDIS_LEVEL_1)
|
#ifndef MAX
|
||||||
# error Incorrect config.h for this revision of ircd.
|
#define MAX(a, b) ((a) > (b) ? (a) : (b))
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef MIN
|
||||||
|
#define MIN(a, b) ((a) < (b) ? (a) : (b))
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define HOSTLEN 63 /* Length of hostname. Updated to */
|
#define HOSTLEN 63 /* Length of hostname. Updated to */
|
||||||
|
@ -119,4 +123,7 @@
|
||||||
#define PATRICIA_BITS 32
|
#define PATRICIA_BITS 32
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* Read buffer size */
|
||||||
|
#define READBUF_SIZE 16384
|
||||||
|
|
||||||
#endif /* INCLUDED_ircd_defs_h */
|
#endif /* INCLUDED_ircd_defs_h */
|
||||||
|
|
|
@ -25,7 +25,7 @@
|
||||||
#ifndef INCLUDED_m_info_h
|
#ifndef INCLUDED_m_info_h
|
||||||
#define INCLUDED_m_info_h
|
#define INCLUDED_m_info_h
|
||||||
|
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
|
|
||||||
typedef struct Information
|
typedef struct Information
|
||||||
{
|
{
|
||||||
|
|
|
@ -46,8 +46,8 @@ extern int match_ips(const char *mask, const char *name);
|
||||||
/*
|
/*
|
||||||
* comp_with_mask - compares to IP address
|
* comp_with_mask - compares to IP address
|
||||||
*/
|
*/
|
||||||
int comp_with_mask(void *addr, void *dest, u_int mask);
|
int comp_with_mask(void *addr, void *dest, unsigned int mask);
|
||||||
int comp_with_mask_sock(struct sockaddr *addr, struct sockaddr *dest, u_int mask);
|
int comp_with_mask_sock(struct sockaddr *addr, struct sockaddr *dest, unsigned int mask);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* collapse - collapse a string in place, converts multiple adjacent *'s
|
* collapse - collapse a string in place, converts multiple adjacent *'s
|
||||||
|
|
|
@ -25,7 +25,7 @@
|
||||||
#ifndef INCLUDED_modules_h
|
#ifndef INCLUDED_modules_h
|
||||||
#define INCLUDED_modules_h
|
#define INCLUDED_modules_h
|
||||||
#include "serno.h"
|
#include "serno.h"
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
#include "setup.h"
|
#include "setup.h"
|
||||||
#include "parse.h"
|
#include "parse.h"
|
||||||
|
|
||||||
|
|
|
@ -25,7 +25,7 @@
|
||||||
#ifndef INCLUDED_msg_h
|
#ifndef INCLUDED_msg_h
|
||||||
#define INCLUDED_msg_h
|
#define INCLUDED_msg_h
|
||||||
|
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
#include "msgbuf.h"
|
#include "msgbuf.h"
|
||||||
|
|
||||||
struct Client;
|
struct Client;
|
||||||
|
@ -54,7 +54,7 @@ typedef void (*MessageHandler) (struct MsgBuf *, struct Client *, struct Client
|
||||||
struct MessageEntry
|
struct MessageEntry
|
||||||
{
|
{
|
||||||
MessageHandler handler;
|
MessageHandler handler;
|
||||||
int min_para;
|
size_t min_para;
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Message table structure */
|
/* Message table structure */
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
/* This code is in the public domain.
|
/* This code is in the public domain.
|
||||||
* $Nightmare: nightmare/include/config.h,v 1.32.2.2.2.2 2002/07/02 03:41:28 ejb Exp $
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NEWCONF_H_INCLUDED
|
#ifndef _NEWCONF_H_INCLUDED
|
||||||
|
|
|
@ -25,7 +25,7 @@
|
||||||
#ifndef INCLUDED_numeric_h
|
#ifndef INCLUDED_numeric_h
|
||||||
#define INCLUDED_numeric_h
|
#define INCLUDED_numeric_h
|
||||||
|
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
#include "messages.h"
|
#include "messages.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
|
@ -39,7 +39,7 @@ extern void mod_add_cmd(struct Message *msg);
|
||||||
extern void mod_del_cmd(struct Message *msg);
|
extern void mod_del_cmd(struct Message *msg);
|
||||||
extern char *reconstruct_parv(int parc, const char *parv[]);
|
extern char *reconstruct_parv(int parc, const char *parv[]);
|
||||||
|
|
||||||
extern struct Dictionary *alias_dict;
|
extern rb_dictionary *alias_dict;
|
||||||
extern struct Dictionary *cmd_dict;
|
extern rb_dictionary *cmd_dict;
|
||||||
|
|
||||||
#endif /* INCLUDED_parse_h_h */
|
#endif /* INCLUDED_parse_h_h */
|
||||||
|
|
|
@ -26,7 +26,7 @@
|
||||||
#ifndef INCLUDED_s_assert_h
|
#ifndef INCLUDED_s_assert_h
|
||||||
#define INCLUDED_s_assert_h
|
#define INCLUDED_s_assert_h
|
||||||
|
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
|
|
||||||
#ifdef SOFT_ASSERT
|
#ifdef SOFT_ASSERT
|
||||||
|
|
||||||
|
|
|
@ -33,7 +33,6 @@
|
||||||
#include "ircd_defs.h"
|
#include "ircd_defs.h"
|
||||||
#include "class.h"
|
#include "class.h"
|
||||||
#include "client.h"
|
#include "client.h"
|
||||||
#include "common.h"
|
|
||||||
|
|
||||||
struct Client;
|
struct Client;
|
||||||
struct DNSReply;
|
struct DNSReply;
|
||||||
|
@ -373,8 +372,8 @@ extern void add_temp_dline(struct ConfItem *);
|
||||||
extern void report_temp_klines(struct Client *);
|
extern void report_temp_klines(struct Client *);
|
||||||
extern void show_temp_klines(struct Client *, rb_dlink_list *);
|
extern void show_temp_klines(struct Client *, rb_dlink_list *);
|
||||||
|
|
||||||
extern int rehash(int);
|
extern bool rehash(bool);
|
||||||
extern void rehash_bans(int);
|
extern void rehash_bans(void);
|
||||||
|
|
||||||
extern int conf_add_server(struct ConfItem *, int);
|
extern int conf_add_server(struct ConfItem *, int);
|
||||||
extern void conf_add_class_to_conf(struct ConfItem *);
|
extern void conf_add_class_to_conf(struct ConfItem *);
|
||||||
|
@ -389,11 +388,11 @@ extern int yylex(void);
|
||||||
|
|
||||||
extern unsigned long cidr_to_bitmask[];
|
extern unsigned long cidr_to_bitmask[];
|
||||||
|
|
||||||
extern char conffilebuf[IRCD_BUFSIZE + 1];
|
extern char conffilebuf[BUFSIZE + 1];
|
||||||
extern int lineno;
|
extern int lineno;
|
||||||
|
|
||||||
#define NOT_AUTHORISED (-1)
|
#define NOT_AUTHORISED (-1)
|
||||||
#define SOCKET_ERROR (-2)
|
#define I_SOCKET_ERROR (-2)
|
||||||
#define I_LINE_FULL (-3)
|
#define I_LINE_FULL (-3)
|
||||||
#define BANNED_CLIENT (-4)
|
#define BANNED_CLIENT (-4)
|
||||||
#define TOO_MANY_LOCAL (-6)
|
#define TOO_MANY_LOCAL (-6)
|
||||||
|
|
|
@ -131,7 +131,7 @@ struct oper_conf
|
||||||
extern struct remote_conf *make_remote_conf(void);
|
extern struct remote_conf *make_remote_conf(void);
|
||||||
extern void free_remote_conf(struct remote_conf *);
|
extern void free_remote_conf(struct remote_conf *);
|
||||||
|
|
||||||
extern int find_shared_conf(const char *username, const char *host,
|
extern bool find_shared_conf(const char *username, const char *host,
|
||||||
const char *server, int flags);
|
const char *server, int flags);
|
||||||
extern void propagate_generic(struct Client *source_p, const char *command,
|
extern void propagate_generic(struct Client *source_p, const char *command,
|
||||||
const char *target, int cap, const char *format, ...);
|
const char *target, int cap, const char *format, ...);
|
||||||
|
|
|
@ -25,7 +25,7 @@
|
||||||
#ifndef INCLUDED_serv_h
|
#ifndef INCLUDED_serv_h
|
||||||
#define INCLUDED_serv_h
|
#define INCLUDED_serv_h
|
||||||
|
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
#include "capability.h"
|
#include "capability.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
|
@ -25,7 +25,7 @@
|
||||||
#ifndef INCLUDED_s_user_h
|
#ifndef INCLUDED_s_user_h
|
||||||
#define INCLUDED_s_user_h
|
#define INCLUDED_s_user_h
|
||||||
|
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
|
|
||||||
struct Client;
|
struct Client;
|
||||||
struct User;
|
struct User;
|
||||||
|
|
|
@ -27,7 +27,6 @@
|
||||||
|
|
||||||
#include "rb_lib.h"
|
#include "rb_lib.h"
|
||||||
#include "ircd_defs.h"
|
#include "ircd_defs.h"
|
||||||
#include "config.h" /* HAVE_STDARG_H */
|
|
||||||
|
|
||||||
struct Client;
|
struct Client;
|
||||||
struct Channel;
|
struct Channel;
|
||||||
|
|
|
@ -1,473 +0,0 @@
|
||||||
/* include/setup.h.in. Generated from configure.ac by autoheader. */
|
|
||||||
|
|
||||||
/* Define if building universal (internal helper macro) */
|
|
||||||
#undef AC_APPLE_UNIVERSAL_BUILD
|
|
||||||
|
|
||||||
/* Size of away heap. */
|
|
||||||
#undef AWAY_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Size of the ban heap. */
|
|
||||||
#undef BAN_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Custom branding name. */
|
|
||||||
#undef BRANDING_NAME
|
|
||||||
|
|
||||||
/* Custom branding name. */
|
|
||||||
#undef BRANDING_VERSION
|
|
||||||
|
|
||||||
/* Size of the channel heap. */
|
|
||||||
#undef CHANNEL_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Define this if you are profiling. */
|
|
||||||
#undef CHARYBDIS_PROFILE
|
|
||||||
|
|
||||||
/* Size of the client heap. */
|
|
||||||
#undef CLIENT_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Size of the confitem heap. */
|
|
||||||
#undef CONFITEM_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Define to one of `_getb67', `GETB67', `getb67' for Cray-2 and Cray-YMP
|
|
||||||
systems. This function is required for `alloca.c' support on those systems.
|
|
||||||
*/
|
|
||||||
#undef CRAY_STACKSEG_END
|
|
||||||
|
|
||||||
/* Define if custom branding is enabled. */
|
|
||||||
#undef CUSTOM_BRANDING
|
|
||||||
|
|
||||||
/* Define to 1 if using `alloca.c'. */
|
|
||||||
#undef C_ALLOCA
|
|
||||||
|
|
||||||
/* Size of the dlink_node heap. */
|
|
||||||
#undef DNODE_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Prefix where config files are installed. */
|
|
||||||
#undef ETC_DIR
|
|
||||||
|
|
||||||
/* Size of fd heap. */
|
|
||||||
#undef FD_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Define to 1 if you have `alloca', as a function or macro. */
|
|
||||||
#undef HAVE_ALLOCA
|
|
||||||
|
|
||||||
/* Define to 1 if you have <alloca.h> and it should be used (not on Ultrix).
|
|
||||||
*/
|
|
||||||
#undef HAVE_ALLOCA_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `argz_add' function. */
|
|
||||||
#undef HAVE_ARGZ_ADD
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `argz_append' function. */
|
|
||||||
#undef HAVE_ARGZ_APPEND
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `argz_count' function. */
|
|
||||||
#undef HAVE_ARGZ_COUNT
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `argz_create_sep' function. */
|
|
||||||
#undef HAVE_ARGZ_CREATE_SEP
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <argz.h> header file. */
|
|
||||||
#undef HAVE_ARGZ_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `argz_insert' function. */
|
|
||||||
#undef HAVE_ARGZ_INSERT
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `argz_next' function. */
|
|
||||||
#undef HAVE_ARGZ_NEXT
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `argz_stringify' function. */
|
|
||||||
#undef HAVE_ARGZ_STRINGIFY
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `closedir' function. */
|
|
||||||
#undef HAVE_CLOSEDIR
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <crypt.h> header file. */
|
|
||||||
#undef HAVE_CRYPT_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the declaration of `cygwin_conv_path', and to 0 if
|
|
||||||
you don't. */
|
|
||||||
#undef HAVE_DECL_CYGWIN_CONV_PATH
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <dirent.h> header file. */
|
|
||||||
#undef HAVE_DIRENT_H
|
|
||||||
|
|
||||||
/* Define if you have the GNU dld library. */
|
|
||||||
#undef HAVE_DLD
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <dld.h> header file. */
|
|
||||||
#undef HAVE_DLD_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `dlerror' function. */
|
|
||||||
#undef HAVE_DLERROR
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <dlfcn.h> header file. */
|
|
||||||
#undef HAVE_DLFCN_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <dl.h> header file. */
|
|
||||||
#undef HAVE_DL_H
|
|
||||||
|
|
||||||
/* Define if you have the _dyld_func_lookup function. */
|
|
||||||
#undef HAVE_DYLD
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <errno.h> header file. */
|
|
||||||
#undef HAVE_ERRNO_H
|
|
||||||
|
|
||||||
/* Define to 1 if the system has the type `error_t'. */
|
|
||||||
#undef HAVE_ERROR_T
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `gettimeofday' function. */
|
|
||||||
#undef HAVE_GETTIMEOFDAY
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <inttypes.h> header file. */
|
|
||||||
#undef HAVE_INTTYPES_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `crypto' library (-lcrypto). */
|
|
||||||
#undef HAVE_LIBCRYPTO
|
|
||||||
|
|
||||||
/* Define if you have the libdl library or equivalent. */
|
|
||||||
#undef HAVE_LIBDL
|
|
||||||
|
|
||||||
/* Define if libdlloader will be built on this platform */
|
|
||||||
#undef HAVE_LIBDLLOADER
|
|
||||||
|
|
||||||
/* Define to 1 if zlib (-lz) is available. */
|
|
||||||
#undef HAVE_LIBZ
|
|
||||||
|
|
||||||
/* Define this if a modern libltdl is already installed */
|
|
||||||
#undef HAVE_LTDL
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <machine/endian.h> header file. */
|
|
||||||
#undef HAVE_MACHINE_ENDIAN_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <mach-o/dyld.h> header file. */
|
|
||||||
#undef HAVE_MACH_O_DYLD_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <memory.h> header file. */
|
|
||||||
#undef HAVE_MEMORY_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `mmap' function. */
|
|
||||||
#undef HAVE_MMAP
|
|
||||||
|
|
||||||
/* Define if nanosleep exists */
|
|
||||||
#undef HAVE_NANOSLEEP
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `opendir' function. */
|
|
||||||
#undef HAVE_OPENDIR
|
|
||||||
|
|
||||||
/* Define if libtool can extract symbol lists from object files. */
|
|
||||||
#undef HAVE_PRELOADED_SYMBOLS
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `readdir' function. */
|
|
||||||
#undef HAVE_READDIR
|
|
||||||
|
|
||||||
/* Define if you have the shl_load function. */
|
|
||||||
#undef HAVE_SHL_LOAD
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `snprintf' function. */
|
|
||||||
#undef HAVE_SNPRINTF
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `socketpair' function. */
|
|
||||||
#undef HAVE_SOCKETPAIR
|
|
||||||
|
|
||||||
/* Define to 1 if stdbool.h conforms to C99. */
|
|
||||||
#undef HAVE_STDBOOL_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <stddef.h> header file. */
|
|
||||||
#undef HAVE_STDDEF_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <stdint.h> header file. */
|
|
||||||
#undef HAVE_STDINT_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <stdlib.h> header file. */
|
|
||||||
#undef HAVE_STDLIB_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `strdup' function. */
|
|
||||||
#undef HAVE_STRDUP
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <strings.h> header file. */
|
|
||||||
#undef HAVE_STRINGS_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <string.h> header file. */
|
|
||||||
#undef HAVE_STRING_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `strlcat' function. */
|
|
||||||
#undef HAVE_STRLCAT
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `strlcpy' function. */
|
|
||||||
#undef HAVE_STRLCPY
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `strndup' function. */
|
|
||||||
#undef HAVE_STRNDUP
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <sys/dl.h> header file. */
|
|
||||||
#undef HAVE_SYS_DL_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <sys/epoll.h> header file. */
|
|
||||||
#undef HAVE_SYS_EPOLL_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <sys/param.h> header file. */
|
|
||||||
#undef HAVE_SYS_PARAM_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <sys/resource.h> header file. */
|
|
||||||
#undef HAVE_SYS_RESOURCE_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <sys/stat.h> header file. */
|
|
||||||
#undef HAVE_SYS_STAT_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <sys/syslog.h> header file. */
|
|
||||||
#undef HAVE_SYS_SYSLOG_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <sys/types.h> header file. */
|
|
||||||
#undef HAVE_SYS_TYPES_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <sys/uio.h> header file. */
|
|
||||||
#undef HAVE_SYS_UIO_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <sys/wait.h> header file. */
|
|
||||||
#undef HAVE_SYS_WAIT_H
|
|
||||||
|
|
||||||
/* Define to 1 if the system has the type `uintptr_t'. */
|
|
||||||
#undef HAVE_UINTPTR_T
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <unistd.h> header file. */
|
|
||||||
#undef HAVE_UNISTD_H
|
|
||||||
|
|
||||||
/* Define to 1 if you have the `vsnprintf' function. */
|
|
||||||
#undef HAVE_VSNPRINTF
|
|
||||||
|
|
||||||
/* Define to 1 if you have the <wait.h> header file. */
|
|
||||||
#undef HAVE_WAIT_H
|
|
||||||
|
|
||||||
/* This value is set to 1 to indicate that the system argz facility works */
|
|
||||||
#undef HAVE_WORKING_ARGZ
|
|
||||||
|
|
||||||
/* Define to 1 if the system has the type `_Bool'. */
|
|
||||||
#undef HAVE__BOOL
|
|
||||||
|
|
||||||
/* Prefix where help files are installed. */
|
|
||||||
#undef HELP_DIR
|
|
||||||
|
|
||||||
/* Prefix where the ircd is installed. */
|
|
||||||
#undef IRCD_PREFIX
|
|
||||||
|
|
||||||
/* Size of the local client heap. */
|
|
||||||
#undef LCLIENT_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Size of the linebuf heap. */
|
|
||||||
#undef LINEBUF_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Prefix where to write logfiles. */
|
|
||||||
#undef LOG_DIR
|
|
||||||
|
|
||||||
/* Define if the OS needs help to load dependent libraries for dlopen(). */
|
|
||||||
#undef LTDL_DLOPEN_DEPLIBS
|
|
||||||
|
|
||||||
/* Define to the system default library search path. */
|
|
||||||
#undef LT_DLSEARCH_PATH
|
|
||||||
|
|
||||||
/* The archive extension */
|
|
||||||
#undef LT_LIBEXT
|
|
||||||
|
|
||||||
/* The archive prefix */
|
|
||||||
#undef LT_LIBPREFIX
|
|
||||||
|
|
||||||
/* Define to the extension used for runtime loadable modules, say, ".so". */
|
|
||||||
#undef LT_MODULE_EXT
|
|
||||||
|
|
||||||
/* Define to the name of the environment variable that determines the run-time
|
|
||||||
module search path. */
|
|
||||||
#undef LT_MODULE_PATH_VAR
|
|
||||||
|
|
||||||
/* Define to the sub-directory where libtool stores uninstalled libraries. */
|
|
||||||
#undef LT_OBJDIR
|
|
||||||
|
|
||||||
/* Define to the shared library suffix, say, ".dylib". */
|
|
||||||
#undef LT_SHARED_EXT
|
|
||||||
|
|
||||||
/* Define to the shared archive member specification, say "(shr.o)". */
|
|
||||||
#undef LT_SHARED_LIB_MEMBER
|
|
||||||
|
|
||||||
/* Sizeof member heap. */
|
|
||||||
#undef MEMBER_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Prefix where modules are installed. */
|
|
||||||
#undef MODULE_DIR
|
|
||||||
|
|
||||||
/* Size of the monitor heap. */
|
|
||||||
#undef MONITOR_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Define this to disable debugging support. */
|
|
||||||
#undef NDEBUG
|
|
||||||
|
|
||||||
/* Size of the nick delay heap. */
|
|
||||||
#undef ND_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Define if dlsym() requires a leading underscore in symbol names. */
|
|
||||||
#undef NEED_USCORE
|
|
||||||
|
|
||||||
/* Nickname length */
|
|
||||||
#undef NICKLEN
|
|
||||||
|
|
||||||
/* Size of the WHOWAS array. */
|
|
||||||
#undef NICKNAMEHISTORYLENGTH
|
|
||||||
|
|
||||||
/* Name of package */
|
|
||||||
#undef PACKAGE
|
|
||||||
|
|
||||||
/* Define to the address where bug reports for this package should be sent. */
|
|
||||||
#undef PACKAGE_BUGREPORT
|
|
||||||
|
|
||||||
/* Define to the full name of this package. */
|
|
||||||
#undef PACKAGE_NAME
|
|
||||||
|
|
||||||
/* Define to the full name and version of this package. */
|
|
||||||
#undef PACKAGE_STRING
|
|
||||||
|
|
||||||
/* Define to the one symbol short name of this package. */
|
|
||||||
#undef PACKAGE_TARNAME
|
|
||||||
|
|
||||||
/* Define to the home page for this package. */
|
|
||||||
#undef PACKAGE_URL
|
|
||||||
|
|
||||||
/* Define to the version of this package. */
|
|
||||||
#undef PACKAGE_VERSION
|
|
||||||
|
|
||||||
/* Path to /dev/null */
|
|
||||||
#undef PATH_DEVNULL
|
|
||||||
|
|
||||||
/* Size of the pre-client heap. */
|
|
||||||
#undef PCLIENT_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Directory where binaries the IRCd itself spawns live */
|
|
||||||
#undef PKGLIBEXECDIR
|
|
||||||
|
|
||||||
/* Directory in which to store state, such as ban database */
|
|
||||||
#undef PKGLOCALSTATEDIR
|
|
||||||
|
|
||||||
/* Directory to store pidfile in. */
|
|
||||||
#undef PKGRUNDIR
|
|
||||||
|
|
||||||
/* String with which all programs intended to be in PATH are prefixed. */
|
|
||||||
#undef PROGRAM_PREFIX
|
|
||||||
|
|
||||||
/* The size of `int', as computed by sizeof. */
|
|
||||||
#undef SIZEOF_INT
|
|
||||||
|
|
||||||
/* The size of `long', as computed by sizeof. */
|
|
||||||
#undef SIZEOF_LONG
|
|
||||||
|
|
||||||
/* The size of `long long', as computed by sizeof. */
|
|
||||||
#undef SIZEOF_LONG_LONG
|
|
||||||
|
|
||||||
/* The size of `short', as computed by sizeof. */
|
|
||||||
#undef SIZEOF_SHORT
|
|
||||||
|
|
||||||
/* Define this to enable soft asserts. */
|
|
||||||
#undef SOFT_ASSERT
|
|
||||||
|
|
||||||
/* If using the C implementation of alloca, define if you know the
|
|
||||||
direction of stack growth for your system; otherwise it will be
|
|
||||||
automatically deduced at runtime.
|
|
||||||
STACK_DIRECTION > 0 => grows toward higher addresses
|
|
||||||
STACK_DIRECTION < 0 => grows toward lower addresses
|
|
||||||
STACK_DIRECTION = 0 => direction of growth unknown */
|
|
||||||
#undef STACK_DIRECTION
|
|
||||||
|
|
||||||
/* Define to 1 if you have the ANSI C header files. */
|
|
||||||
#undef STDC_HEADERS
|
|
||||||
|
|
||||||
/* Maximum topic length (<=390) */
|
|
||||||
#undef TOPICLEN
|
|
||||||
|
|
||||||
/* Size of the topic heap. */
|
|
||||||
#undef TOPIC_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Size of the user heap. */
|
|
||||||
#undef USER_HEAP_SIZE
|
|
||||||
|
|
||||||
/* Enable extensions on AIX 3, Interix. */
|
|
||||||
#ifndef _ALL_SOURCE
|
|
||||||
# undef _ALL_SOURCE
|
|
||||||
#endif
|
|
||||||
/* Enable GNU extensions on systems that have them. */
|
|
||||||
#ifndef _GNU_SOURCE
|
|
||||||
# undef _GNU_SOURCE
|
|
||||||
#endif
|
|
||||||
/* Enable threading extensions on Solaris. */
|
|
||||||
#ifndef _POSIX_PTHREAD_SEMANTICS
|
|
||||||
# undef _POSIX_PTHREAD_SEMANTICS
|
|
||||||
#endif
|
|
||||||
/* Enable extensions on HP NonStop. */
|
|
||||||
#ifndef _TANDEM_SOURCE
|
|
||||||
# undef _TANDEM_SOURCE
|
|
||||||
#endif
|
|
||||||
/* Enable general extensions on Solaris. */
|
|
||||||
#ifndef __EXTENSIONS__
|
|
||||||
# undef __EXTENSIONS__
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
/* Version number of package */
|
|
||||||
#undef VERSION
|
|
||||||
|
|
||||||
/* Define WORDS_BIGENDIAN to 1 if your processor stores words with the most
|
|
||||||
significant byte first (like Motorola and SPARC, unlike Intel). */
|
|
||||||
#if defined AC_APPLE_UNIVERSAL_BUILD
|
|
||||||
# if defined __BIG_ENDIAN__
|
|
||||||
# define WORDS_BIGENDIAN 1
|
|
||||||
# endif
|
|
||||||
#else
|
|
||||||
# ifndef WORDS_BIGENDIAN
|
|
||||||
# undef WORDS_BIGENDIAN
|
|
||||||
# endif
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/* Define to 1 if `lex' declares `yytext' as a `char *' by default, not a
|
|
||||||
`char[]'. */
|
|
||||||
#undef YYTEXT_POINTER
|
|
||||||
|
|
||||||
/* Define to 1 if on MINIX. */
|
|
||||||
#undef _MINIX
|
|
||||||
|
|
||||||
/* Define to 2 if the system does not provide POSIX.1 features except with
|
|
||||||
this defined. */
|
|
||||||
#undef _POSIX_1_SOURCE
|
|
||||||
|
|
||||||
/* Define to 1 if you need to in order for `stat' and other things to work. */
|
|
||||||
#undef _POSIX_SOURCE
|
|
||||||
|
|
||||||
/* Define so that glibc/gnulib argp.h does not typedef error_t. */
|
|
||||||
#undef __error_t_defined
|
|
||||||
|
|
||||||
/* Define to empty if `const' does not conform to ANSI C. */
|
|
||||||
#undef const
|
|
||||||
|
|
||||||
/* Define to a type to use for 'error_t' if it is not otherwise available. */
|
|
||||||
#undef error_t
|
|
||||||
|
|
||||||
/* If system does not define in_port_t, define it to what it should be. */
|
|
||||||
#undef in_port_t
|
|
||||||
|
|
||||||
/* Define to `__inline__' or `__inline' if that's what the C compiler
|
|
||||||
calls it, or to nothing if 'inline' is not supported under any name. */
|
|
||||||
#ifndef __cplusplus
|
|
||||||
#undef inline
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/* Define to `int' if <sys/types.h> does not define. */
|
|
||||||
#undef pid_t
|
|
||||||
|
|
||||||
/* If system does not define sa_family_t, define it here. */
|
|
||||||
#undef sa_family_t
|
|
||||||
|
|
||||||
/* Define to `unsigned int' if <sys/types.h> does not define. */
|
|
||||||
#undef size_t
|
|
||||||
|
|
||||||
/* If we don't have a real socklen_t, unsigned int is good enough. */
|
|
||||||
#undef socklen_t
|
|
||||||
|
|
||||||
/* If system does not define u_int16_t, define a usable substitute. */
|
|
||||||
#undef u_int16_t
|
|
||||||
|
|
||||||
/* If system does not define u_int32_t, define to unsigned long int here. */
|
|
||||||
#undef u_int32_t
|
|
|
@ -22,7 +22,6 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "rb_lib.h"
|
#include "rb_lib.h"
|
||||||
#include "config.h" /* Gotta pull in the autoconf stuff */
|
|
||||||
#include "ircd_defs.h" /* Needed for some reasons here -- dwr */
|
#include "ircd_defs.h" /* Needed for some reasons here -- dwr */
|
||||||
|
|
||||||
/* AIX requires this to be the first thing in the file. */
|
/* AIX requires this to be the first thing in the file. */
|
||||||
|
@ -93,7 +92,6 @@ typedef bool _Bool;
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <time.h>
|
#include <time.h>
|
||||||
#include <fcntl.h>
|
#include <fcntl.h>
|
||||||
#include <netdb.h>
|
|
||||||
#include <stdarg.h>
|
#include <stdarg.h>
|
||||||
#include <signal.h>
|
#include <signal.h>
|
||||||
#include <dirent.h>
|
#include <dirent.h>
|
||||||
|
@ -113,16 +111,11 @@ typedef bool _Bool;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
#include <sys/socket.h>
|
|
||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
#include <sys/wait.h>
|
|
||||||
|
|
||||||
#ifdef HAVE_SYS_PARAM_H
|
#ifdef HAVE_SYS_PARAM_H
|
||||||
#include <sys/param.h>
|
#include <sys/param.h>
|
||||||
#endif
|
#endif
|
||||||
#include <netinet/in.h>
|
|
||||||
#include <netinet/tcp.h>
|
|
||||||
#include <arpa/inet.h>
|
|
||||||
|
|
||||||
#ifdef HAVE_ERRNO_H
|
#ifdef HAVE_ERRNO_H
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
|
|
0
install-sh
Normal file → Executable file
0
install-sh
Normal file → Executable file
|
@ -14,6 +14,10 @@ version.c: version.c.SH ../CREDITS ../include/patchlevel.h ../include/serno.h
|
||||||
$(CP) version.c version.c.last
|
$(CP) version.c version.c.last
|
||||||
touch version.c.SH
|
touch version.c.SH
|
||||||
|
|
||||||
|
if MINGW
|
||||||
|
EXTRA_FLAGS = -Wl,--enable-runtime-pseudo-reloc -export-symbols-regex '*'
|
||||||
|
endif
|
||||||
|
|
||||||
libircd_la_SOURCES = \
|
libircd_la_SOURCES = \
|
||||||
authd.c \
|
authd.c \
|
||||||
bandbi.c \
|
bandbi.c \
|
||||||
|
@ -63,7 +67,7 @@ libircd_la_SOURCES = \
|
||||||
tgchange.c \
|
tgchange.c \
|
||||||
version.c \
|
version.c \
|
||||||
whowas.c
|
whowas.c
|
||||||
libircd_la_LDFLAGS = $(EXTRA_FLAGS) -avoid-version
|
libircd_la_LDFLAGS = $(EXTRA_FLAGS) -avoid-version -no-undefined
|
||||||
libircd_la_LIBADD = @LIBLTDL@ -L$(top_srcdir)/librb/src -lrb
|
libircd_la_LIBADD = @LIBLTDL@ -L$(top_srcdir)/librb/src -lrb
|
||||||
libircd_LTLIBRARIES = libircd.la
|
libircd_LTLIBRARIES = libircd.la
|
||||||
|
|
||||||
|
|
47
ircd/authd.c
47
ircd/authd.c
|
@ -55,20 +55,20 @@ start_authd(void)
|
||||||
#endif
|
#endif
|
||||||
if(authd_path == NULL)
|
if(authd_path == NULL)
|
||||||
{
|
{
|
||||||
snprintf(fullpath, sizeof(fullpath), "%s/authd%s", PKGLIBEXECDIR, suffix);
|
snprintf(fullpath, sizeof(fullpath), "%s%cauthd%s", ircd_paths[IRCD_PATH_LIBEXEC], RB_PATH_SEPARATOR, suffix);
|
||||||
|
|
||||||
if(access(fullpath, X_OK) == -1)
|
if(access(fullpath, X_OK) == -1)
|
||||||
{
|
{
|
||||||
snprintf(fullpath, sizeof(fullpath), "%s/libexec/charybdis/authd%s",
|
snprintf(fullpath, sizeof(fullpath), "%s%cbin%cauthd%s",
|
||||||
ConfigFileEntry.dpath, suffix);
|
ConfigFileEntry.dpath, RB_PATH_SEPARATOR, RB_PATH_SEPARATOR, suffix);
|
||||||
if(access(fullpath, X_OK) == -1)
|
if(access(fullpath, X_OK) == -1)
|
||||||
{
|
{
|
||||||
ilog(L_MAIN,
|
ilog(L_MAIN,
|
||||||
"Unable to execute authd in %s or %s/libexec/charybdis",
|
"Unable to execute authd in %s or %s/bin",
|
||||||
PKGLIBEXECDIR, ConfigFileEntry.dpath);
|
ircd_paths[IRCD_PATH_LIBEXEC], ConfigFileEntry.dpath);
|
||||||
sendto_realops_snomask(SNO_GENERAL, L_ALL,
|
sendto_realops_snomask(SNO_GENERAL, L_ALL,
|
||||||
"Unable to execute authd in %s or %s/libexec/charybdis",
|
"Unable to execute authd in %s or %s/bin",
|
||||||
PKGLIBEXECDIR, ConfigFileEntry.dpath);
|
ircd_paths[IRCD_PATH_LIBEXEC], ConfigFileEntry.dpath);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -114,6 +114,39 @@ parse_authd_reply(rb_helper * helper)
|
||||||
}
|
}
|
||||||
dns_results_callback(parv[1], parv[2], parv[3], parv[4]);
|
dns_results_callback(parv[1], parv[2], parv[3], parv[4]);
|
||||||
break;
|
break;
|
||||||
|
case 'W':
|
||||||
|
if(parc != 3)
|
||||||
|
{
|
||||||
|
ilog(L_MAIN, "authd sent a result with wrong number of arguments: got %d", parc);
|
||||||
|
restart_authd();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
switch(*parv[2])
|
||||||
|
{
|
||||||
|
case 'D': /* debug */
|
||||||
|
sendto_realops_snomask(SNO_DEBUG, L_ALL, "authd debug: %s", parv[3]);
|
||||||
|
break;
|
||||||
|
case 'I': /* Info */
|
||||||
|
sendto_realops_snomask(SNO_GENERAL, L_ALL, "authd info: %s", parv[3]);
|
||||||
|
inotice("authd info: %s", parv[3]);
|
||||||
|
break;
|
||||||
|
case 'W': /* Warning */
|
||||||
|
sendto_realops_snomask(SNO_GENERAL, L_ALL, "authd WARNING: %s", parv[3]);
|
||||||
|
iwarn("authd warning: %s", parv[3]);
|
||||||
|
break;
|
||||||
|
case 'C': /* Critical (error) */
|
||||||
|
sendto_realops_snomask(SNO_GENERAL, L_ALL, "authd CRITICAL: %s", parv[3]);
|
||||||
|
ierror("authd critical: %s", parv[3]);
|
||||||
|
break;
|
||||||
|
default: /* idk */
|
||||||
|
sendto_realops_snomask(SNO_GENERAL, L_ALL, "authd sent us an unknown oper notice type (%s): %s", parv[2], parv[3]);
|
||||||
|
ilog(L_MAIN, "authd unknown oper notice type (%s): %s", parv[2], parv[3]);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* NOTREACHED */
|
||||||
|
break;
|
||||||
case 'X':
|
case 'X':
|
||||||
case 'Y':
|
case 'Y':
|
||||||
case 'Z':
|
case 'Z':
|
||||||
|
|
|
@ -80,21 +80,21 @@ start_bandb(void)
|
||||||
const char *suffix = "";
|
const char *suffix = "";
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
rb_setenv("BANDB_DBPATH", PKGLOCALSTATEDIR "/ban.db", 1);
|
rb_setenv("BANDB_DBPATH", ircd_paths[IRCD_PATH_BANDB], 1);
|
||||||
if(bandb_path == NULL)
|
if(bandb_path == NULL)
|
||||||
{
|
{
|
||||||
snprintf(fullpath, sizeof(fullpath), "%s/bandb%s", PKGLIBEXECDIR, suffix);
|
snprintf(fullpath, sizeof(fullpath), "%s%cbandb%s", ircd_paths[IRCD_PATH_LIBEXEC], RB_PATH_SEPARATOR, suffix);
|
||||||
|
|
||||||
if(access(fullpath, X_OK) == -1)
|
if(access(fullpath, X_OK) == -1)
|
||||||
{
|
{
|
||||||
snprintf(fullpath, sizeof(fullpath), "%s/bin/bandb%s",
|
snprintf(fullpath, sizeof(fullpath), "%s%cbin%cbandb%s",
|
||||||
ConfigFileEntry.dpath, suffix);
|
ConfigFileEntry.dpath, RB_PATH_SEPARATOR, RB_PATH_SEPARATOR, suffix);
|
||||||
|
|
||||||
if(access(fullpath, X_OK) == -1)
|
if(access(fullpath, X_OK) == -1)
|
||||||
{
|
{
|
||||||
ilog(L_MAIN,
|
ilog(L_MAIN,
|
||||||
"Unable to execute bandb%s in %s or %s/bin",
|
"Unable to execute bandb%s in %s or %s/bin",
|
||||||
suffix, PKGLIBEXECDIR, ConfigFileEntry.dpath);
|
suffix, ircd_paths[IRCD_PATH_LIBEXEC], ConfigFileEntry.dpath);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -156,7 +156,7 @@ static void initiate_blacklist_dnsquery(struct Blacklist *blptr, struct Client *
|
||||||
blcptr->client_p = client_p;
|
blcptr->client_p = client_p;
|
||||||
|
|
||||||
/* IPv4 */
|
/* IPv4 */
|
||||||
if ((client_p->localClient->ip.ss_family == AF_INET) && blptr->ipv4)
|
if ((GET_SS_FAMILY(&client_p->localClient->ip) == AF_INET) && blptr->ipv4)
|
||||||
{
|
{
|
||||||
ip = (uint8_t *)&((struct sockaddr_in *)&client_p->localClient->ip)->sin_addr.s_addr;
|
ip = (uint8_t *)&((struct sockaddr_in *)&client_p->localClient->ip)->sin_addr.s_addr;
|
||||||
|
|
||||||
|
@ -168,8 +168,9 @@ static void initiate_blacklist_dnsquery(struct Blacklist *blptr, struct Client *
|
||||||
(unsigned int) ip[0],
|
(unsigned int) ip[0],
|
||||||
blptr->host);
|
blptr->host);
|
||||||
}
|
}
|
||||||
|
#ifdef RB_IPV6
|
||||||
/* IPv6 */
|
/* IPv6 */
|
||||||
else if ((client_p->localClient->ip.ss_family == AF_INET6) && blptr->ipv6)
|
else if ((GET_SS_FAMILY(&client_p->localClient->ip) == AF_INET6) && blptr->ipv6)
|
||||||
{
|
{
|
||||||
/* Split up for rDNS lookup
|
/* Split up for rDNS lookup
|
||||||
* ex: ip[0] = 0x00, ip[1] = 0x00... ip[16] = 0x01 for localhost
|
* ex: ip[0] = 0x00, ip[1] = 0x00... ip[16] = 0x01 for localhost
|
||||||
|
@ -197,6 +198,7 @@ static void initiate_blacklist_dnsquery(struct Blacklist *blptr, struct Client *
|
||||||
/* Tack host on */
|
/* Tack host on */
|
||||||
strcpy(bufptr, blptr->host);
|
strcpy(bufptr, blptr->host);
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
/* This shouldn't happen... */
|
/* This shouldn't happen... */
|
||||||
else
|
else
|
||||||
return;
|
return;
|
||||||
|
@ -225,7 +227,7 @@ struct Blacklist *new_blacklist(char *name, char *reject_reason, int ipv4, int i
|
||||||
blptr->status &= ~CONF_ILLEGAL;
|
blptr->status &= ~CONF_ILLEGAL;
|
||||||
|
|
||||||
rb_strlcpy(blptr->host, name, IRCD_RES_HOSTLEN + 1);
|
rb_strlcpy(blptr->host, name, IRCD_RES_HOSTLEN + 1);
|
||||||
rb_strlcpy(blptr->reject_reason, reject_reason, IRCD_BUFSIZE);
|
rb_strlcpy(blptr->reject_reason, reject_reason, BUFSIZE);
|
||||||
blptr->ipv4 = ipv4;
|
blptr->ipv4 = ipv4;
|
||||||
blptr->ipv6 = ipv6;
|
blptr->ipv6 = ipv6;
|
||||||
|
|
||||||
|
|
27
ircd/cache.c
27
ircd/cache.c
|
@ -32,7 +32,6 @@
|
||||||
|
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "ircd_defs.h"
|
#include "ircd_defs.h"
|
||||||
#include "common.h"
|
|
||||||
#include "s_conf.h"
|
#include "s_conf.h"
|
||||||
#include "client.h"
|
#include "client.h"
|
||||||
#include "hash.h"
|
#include "hash.h"
|
||||||
|
@ -47,8 +46,8 @@ struct cacheline *emptyline = NULL;
|
||||||
rb_dlink_list links_cache_list;
|
rb_dlink_list links_cache_list;
|
||||||
char user_motd_changed[MAX_DATE_STRING];
|
char user_motd_changed[MAX_DATE_STRING];
|
||||||
|
|
||||||
struct Dictionary *help_dict_oper = NULL;
|
rb_dictionary *help_dict_oper = NULL;
|
||||||
struct Dictionary *help_dict_user = NULL;
|
rb_dictionary *help_dict_user = NULL;
|
||||||
|
|
||||||
/* init_cache()
|
/* init_cache()
|
||||||
*
|
*
|
||||||
|
@ -65,8 +64,8 @@ init_cache(void)
|
||||||
|
|
||||||
user_motd_changed[0] = '\0';
|
user_motd_changed[0] = '\0';
|
||||||
|
|
||||||
user_motd = cache_file(MPATH, "ircd.motd", 0);
|
user_motd = cache_file(ircd_paths[IRCD_PATH_IRCD_MOTD], "ircd.motd", 0);
|
||||||
oper_motd = cache_file(OPATH, "opers.motd", 0);
|
oper_motd = cache_file(ircd_paths[IRCD_PATH_IRCD_OMOTD], "opers.motd", 0);
|
||||||
memset(&links_cache_list, 0, sizeof(links_cache_list));
|
memset(&links_cache_list, 0, sizeof(links_cache_list));
|
||||||
|
|
||||||
help_dict_oper = rb_dictionary_create("oper help", strcasecmp);
|
help_dict_oper = rb_dictionary_create("oper help", strcasecmp);
|
||||||
|
@ -237,24 +236,24 @@ load_help(void)
|
||||||
struct dirent *ldirent= NULL;
|
struct dirent *ldirent= NULL;
|
||||||
char filename[PATH_MAX];
|
char filename[PATH_MAX];
|
||||||
struct cachefile *cacheptr;
|
struct cachefile *cacheptr;
|
||||||
struct DictionaryIter iter;
|
rb_dictionary_iter iter;
|
||||||
|
|
||||||
#if defined(S_ISLNK) && defined(HAVE_LSTAT)
|
#if defined(S_ISLNK) && defined(HAVE_LSTAT)
|
||||||
struct stat sb;
|
struct stat sb;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
DICTIONARY_FOREACH(cacheptr, &iter, help_dict_oper)
|
RB_DICTIONARY_FOREACH(cacheptr, &iter, help_dict_oper)
|
||||||
{
|
{
|
||||||
rb_dictionary_delete(help_dict_oper, cacheptr->name);
|
rb_dictionary_delete(help_dict_oper, cacheptr->name);
|
||||||
free_cachefile(cacheptr);
|
free_cachefile(cacheptr);
|
||||||
}
|
}
|
||||||
DICTIONARY_FOREACH(cacheptr, &iter, help_dict_user)
|
RB_DICTIONARY_FOREACH(cacheptr, &iter, help_dict_user)
|
||||||
{
|
{
|
||||||
rb_dictionary_delete(help_dict_user, cacheptr->name);
|
rb_dictionary_delete(help_dict_user, cacheptr->name);
|
||||||
free_cachefile(cacheptr);
|
free_cachefile(cacheptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
helpfile_dir = opendir(HPATH);
|
helpfile_dir = opendir(ircd_paths[IRCD_PATH_OPERHELP]);
|
||||||
|
|
||||||
if(helpfile_dir == NULL)
|
if(helpfile_dir == NULL)
|
||||||
return;
|
return;
|
||||||
|
@ -263,13 +262,13 @@ load_help(void)
|
||||||
{
|
{
|
||||||
if(ldirent->d_name[0] == '.')
|
if(ldirent->d_name[0] == '.')
|
||||||
continue;
|
continue;
|
||||||
snprintf(filename, sizeof(filename), "%s/%s", HPATH, ldirent->d_name);
|
snprintf(filename, sizeof(filename), "%s%c%s", ircd_paths[IRCD_PATH_OPERHELP], RB_PATH_SEPARATOR, ldirent->d_name);
|
||||||
cacheptr = cache_file(filename, ldirent->d_name, HELP_OPER);
|
cacheptr = cache_file(filename, ldirent->d_name, HELP_OPER);
|
||||||
rb_dictionary_add(help_dict_oper, cacheptr->name, cacheptr);
|
rb_dictionary_add(help_dict_oper, cacheptr->name, cacheptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
closedir(helpfile_dir);
|
closedir(helpfile_dir);
|
||||||
helpfile_dir = opendir(UHPATH);
|
helpfile_dir = opendir(ircd_paths[IRCD_PATH_USERHELP]);
|
||||||
|
|
||||||
if(helpfile_dir == NULL)
|
if(helpfile_dir == NULL)
|
||||||
return;
|
return;
|
||||||
|
@ -278,7 +277,7 @@ load_help(void)
|
||||||
{
|
{
|
||||||
if(ldirent->d_name[0] == '.')
|
if(ldirent->d_name[0] == '.')
|
||||||
continue;
|
continue;
|
||||||
snprintf(filename, sizeof(filename), "%s/%s", UHPATH, ldirent->d_name);
|
snprintf(filename, sizeof(filename), "%s%c%s", ircd_paths[IRCD_PATH_USERHELP], RB_PATH_SEPARATOR, ldirent->d_name);
|
||||||
|
|
||||||
#if defined(S_ISLNK) && defined(HAVE_LSTAT)
|
#if defined(S_ISLNK) && defined(HAVE_LSTAT)
|
||||||
if(lstat(filename, &sb) < 0)
|
if(lstat(filename, &sb) < 0)
|
||||||
|
@ -342,7 +341,7 @@ cache_user_motd(void)
|
||||||
struct stat sb;
|
struct stat sb;
|
||||||
struct tm *local_tm;
|
struct tm *local_tm;
|
||||||
|
|
||||||
if(stat(MPATH, &sb) == 0)
|
if(stat(ircd_paths[IRCD_PATH_IRCD_MOTD], &sb) == 0)
|
||||||
{
|
{
|
||||||
local_tm = localtime(&sb.st_mtime);
|
local_tm = localtime(&sb.st_mtime);
|
||||||
|
|
||||||
|
@ -356,7 +355,7 @@ cache_user_motd(void)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
free_cachefile(user_motd);
|
free_cachefile(user_motd);
|
||||||
user_motd = cache_file(MPATH, "ircd.motd", 0);
|
user_motd = cache_file(ircd_paths[IRCD_PATH_IRCD_MOTD], "ircd.motd", 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -129,7 +129,7 @@ capability_require(struct CapabilityIndex *idx, const char *cap)
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
capability_destroy(struct DictionaryElement *delem, void *privdata)
|
capability_destroy(rb_dictionary_element *delem, void *privdata)
|
||||||
{
|
{
|
||||||
s_assert(delem != NULL);
|
s_assert(delem != NULL);
|
||||||
|
|
||||||
|
@ -165,7 +165,7 @@ capability_index_destroy(struct CapabilityIndex *idx)
|
||||||
const char *
|
const char *
|
||||||
capability_index_list(struct CapabilityIndex *idx, unsigned int cap_mask)
|
capability_index_list(struct CapabilityIndex *idx, unsigned int cap_mask)
|
||||||
{
|
{
|
||||||
struct DictionaryIter iter;
|
rb_dictionary_iter iter;
|
||||||
struct CapabilityEntry *entry;
|
struct CapabilityEntry *entry;
|
||||||
static char buf[BUFSIZE];
|
static char buf[BUFSIZE];
|
||||||
char *t = buf;
|
char *t = buf;
|
||||||
|
@ -175,7 +175,7 @@ capability_index_list(struct CapabilityIndex *idx, unsigned int cap_mask)
|
||||||
|
|
||||||
*t = '\0';
|
*t = '\0';
|
||||||
|
|
||||||
DICTIONARY_FOREACH(entry, &iter, idx->cap_dict)
|
RB_DICTIONARY_FOREACH(entry, &iter, idx->cap_dict)
|
||||||
{
|
{
|
||||||
if ((1 << entry->value) & cap_mask)
|
if ((1 << entry->value) & cap_mask)
|
||||||
{
|
{
|
||||||
|
@ -193,13 +193,13 @@ capability_index_list(struct CapabilityIndex *idx, unsigned int cap_mask)
|
||||||
unsigned int
|
unsigned int
|
||||||
capability_index_mask(struct CapabilityIndex *idx)
|
capability_index_mask(struct CapabilityIndex *idx)
|
||||||
{
|
{
|
||||||
struct DictionaryIter iter;
|
rb_dictionary_iter iter;
|
||||||
struct CapabilityEntry *entry;
|
struct CapabilityEntry *entry;
|
||||||
unsigned int mask = 0;
|
unsigned int mask = 0;
|
||||||
|
|
||||||
s_assert(idx != NULL);
|
s_assert(idx != NULL);
|
||||||
|
|
||||||
DICTIONARY_FOREACH(entry, &iter, idx->cap_dict)
|
RB_DICTIONARY_FOREACH(entry, &iter, idx->cap_dict)
|
||||||
{
|
{
|
||||||
if (!(entry->flags & CAP_ORPHANED))
|
if (!(entry->flags & CAP_ORPHANED))
|
||||||
mask |= (1 << entry->value);
|
mask |= (1 << entry->value);
|
||||||
|
@ -211,13 +211,13 @@ capability_index_mask(struct CapabilityIndex *idx)
|
||||||
unsigned int
|
unsigned int
|
||||||
capability_index_get_required(struct CapabilityIndex *idx)
|
capability_index_get_required(struct CapabilityIndex *idx)
|
||||||
{
|
{
|
||||||
struct DictionaryIter iter;
|
rb_dictionary_iter iter;
|
||||||
struct CapabilityEntry *entry;
|
struct CapabilityEntry *entry;
|
||||||
unsigned int mask = 0;
|
unsigned int mask = 0;
|
||||||
|
|
||||||
s_assert(idx != NULL);
|
s_assert(idx != NULL);
|
||||||
|
|
||||||
DICTIONARY_FOREACH(entry, &iter, idx->cap_dict)
|
RB_DICTIONARY_FOREACH(entry, &iter, idx->cap_dict)
|
||||||
{
|
{
|
||||||
if (!(entry->flags & CAP_ORPHANED) && (entry->flags & CAP_REQUIRED))
|
if (!(entry->flags & CAP_ORPHANED) && (entry->flags & CAP_REQUIRED))
|
||||||
mask |= (1 << entry->value);
|
mask |= (1 << entry->value);
|
||||||
|
@ -235,13 +235,13 @@ capability_index_stats(void (*cb)(const char *line, void *privdata), void *privd
|
||||||
RB_DLINK_FOREACH(node, capability_indexes.head)
|
RB_DLINK_FOREACH(node, capability_indexes.head)
|
||||||
{
|
{
|
||||||
struct CapabilityIndex *idx = node->data;
|
struct CapabilityIndex *idx = node->data;
|
||||||
struct DictionaryIter iter;
|
rb_dictionary_iter iter;
|
||||||
struct CapabilityEntry *entry;
|
struct CapabilityEntry *entry;
|
||||||
|
|
||||||
snprintf(buf, sizeof buf, "'%s': allocated bits - %d", idx->name, (idx->highest_bit - 1));
|
snprintf(buf, sizeof buf, "'%s': allocated bits - %d", idx->name, (idx->highest_bit - 1));
|
||||||
cb(buf, privdata);
|
cb(buf, privdata);
|
||||||
|
|
||||||
DICTIONARY_FOREACH(entry, &iter, idx->cap_dict)
|
RB_DICTIONARY_FOREACH(entry, &iter, idx->cap_dict)
|
||||||
{
|
{
|
||||||
snprintf(buf, sizeof buf, "bit %d: '%s'", entry->value, entry->cap);
|
snprintf(buf, sizeof buf, "bit %d: '%s'", entry->value, entry->cap);
|
||||||
cb(buf, privdata);
|
cb(buf, privdata);
|
||||||
|
|
|
@ -26,7 +26,6 @@
|
||||||
#include "channel.h"
|
#include "channel.h"
|
||||||
#include "chmode.h"
|
#include "chmode.h"
|
||||||
#include "client.h"
|
#include "client.h"
|
||||||
#include "common.h"
|
|
||||||
#include "hash.h"
|
#include "hash.h"
|
||||||
#include "hook.h"
|
#include "hook.h"
|
||||||
#include "match.h"
|
#include "match.h"
|
||||||
|
@ -337,23 +336,23 @@ invalidate_bancache_user(struct Client *client_p)
|
||||||
/* check_channel_name()
|
/* check_channel_name()
|
||||||
*
|
*
|
||||||
* input - channel name
|
* input - channel name
|
||||||
* output - 1 if valid channel name, else 0
|
* output - true if valid channel name, else false
|
||||||
* side effects -
|
* side effects -
|
||||||
*/
|
*/
|
||||||
int
|
bool
|
||||||
check_channel_name(const char *name)
|
check_channel_name(const char *name)
|
||||||
{
|
{
|
||||||
s_assert(name != NULL);
|
s_assert(name != NULL);
|
||||||
if(name == NULL)
|
if(name == NULL)
|
||||||
return 0;
|
return false;
|
||||||
|
|
||||||
for (; *name; ++name)
|
for (; *name; ++name)
|
||||||
{
|
{
|
||||||
if(!IsChanChar(*name))
|
if(!IsChanChar(*name))
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return 1;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* free_channel_list()
|
/* free_channel_list()
|
||||||
|
@ -581,7 +580,7 @@ is_banned_list(struct Channel *chptr, rb_dlink_list *list,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#ifdef RB_IPV6
|
#ifdef RB_IPV6
|
||||||
if(who->localClient->ip.ss_family == AF_INET6 &&
|
if(GET_SS_FAMILY(&who->localClient->ip) == AF_INET6 &&
|
||||||
ipv4_from_ipv6((const struct sockaddr_in6 *)&who->localClient->ip, &ip4))
|
ipv4_from_ipv6((const struct sockaddr_in6 *)&who->localClient->ip, &ip4))
|
||||||
{
|
{
|
||||||
sprintf(src_ip4host, "%s!%s@", who->name, who->username);
|
sprintf(src_ip4host, "%s!%s@", who->name, who->username);
|
||||||
|
@ -903,10 +902,10 @@ can_send(struct Channel *chptr, struct Client *source_p, struct membership *mspt
|
||||||
* says NOTICE must not auto reply
|
* says NOTICE must not auto reply
|
||||||
* - pointer to source Client
|
* - pointer to source Client
|
||||||
* - pointer to target channel
|
* - pointer to target channel
|
||||||
* output - 1 if target is under flood attack
|
* output - true if target is under flood attack
|
||||||
* side effects - check for flood attack on target chptr
|
* side effects - check for flood attack on target chptr
|
||||||
*/
|
*/
|
||||||
int
|
bool
|
||||||
flood_attack_channel(int p_or_n, struct Client *source_p, struct Channel *chptr, char *chname)
|
flood_attack_channel(int p_or_n, struct Client *source_p, struct Channel *chptr, char *chname)
|
||||||
{
|
{
|
||||||
int delta;
|
int delta;
|
||||||
|
@ -944,13 +943,13 @@ flood_attack_channel(int p_or_n, struct Client *source_p, struct Channel *chptr,
|
||||||
sendto_one(source_p,
|
sendto_one(source_p,
|
||||||
":%s NOTICE %s :*** Message to %s throttled due to flooding",
|
":%s NOTICE %s :*** Message to %s throttled due to flooding",
|
||||||
me.name, source_p->name, chptr->chname);
|
me.name, source_p->name, chptr->chname);
|
||||||
return 1;
|
return true;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
chptr->received_number_of_privmsgs++;
|
chptr->received_number_of_privmsgs++;
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* find_bannickchange_channel()
|
/* find_bannickchange_channel()
|
||||||
|
|
|
@ -26,7 +26,6 @@
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "channel.h"
|
#include "channel.h"
|
||||||
#include "client.h"
|
#include "client.h"
|
||||||
#include "common.h"
|
|
||||||
#include "hash.h"
|
#include "hash.h"
|
||||||
#include "hook.h"
|
#include "hook.h"
|
||||||
#include "match.h"
|
#include "match.h"
|
||||||
|
@ -203,10 +202,10 @@ get_channel_access(struct Client *source_p, struct Channel *chptr, struct member
|
||||||
* Checks if mlock and chanops permit a mode change.
|
* Checks if mlock and chanops permit a mode change.
|
||||||
*
|
*
|
||||||
* inputs - client, channel, access level, errors pointer, mode char
|
* inputs - client, channel, access level, errors pointer, mode char
|
||||||
* outputs - 0 on failure, 1 on success
|
* outputs - false on failure, true on success
|
||||||
* side effects - error message sent on failure
|
* side effects - error message sent on failure
|
||||||
*/
|
*/
|
||||||
static int
|
static bool
|
||||||
allow_mode_change(struct Client *source_p, struct Channel *chptr, int alevel,
|
allow_mode_change(struct Client *source_p, struct Channel *chptr, int alevel,
|
||||||
int *errors, char c)
|
int *errors, char c)
|
||||||
{
|
{
|
||||||
|
@ -221,7 +220,7 @@ allow_mode_change(struct Client *source_p, struct Channel *chptr, int alevel,
|
||||||
c,
|
c,
|
||||||
chptr->mode_lock);
|
chptr->mode_lock);
|
||||||
*errors |= SM_ERR_MLOCK;
|
*errors |= SM_ERR_MLOCK;
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
if(alevel < CHFL_CHANOP)
|
if(alevel < CHFL_CHANOP)
|
||||||
{
|
{
|
||||||
|
@ -229,18 +228,18 @@ allow_mode_change(struct Client *source_p, struct Channel *chptr, int alevel,
|
||||||
sendto_one(source_p, form_str(ERR_CHANOPRIVSNEEDED),
|
sendto_one(source_p, form_str(ERR_CHANOPRIVSNEEDED),
|
||||||
me.name, source_p->name, chptr->chname);
|
me.name, source_p->name, chptr->chname);
|
||||||
*errors |= SM_ERR_NOOPS;
|
*errors |= SM_ERR_NOOPS;
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
return 1;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* add_id()
|
/* add_id()
|
||||||
*
|
*
|
||||||
* inputs - client, channel, id to add, type, forward
|
* inputs - client, channel, id to add, type, forward
|
||||||
* outputs - 0 on failure, 1 on success
|
* outputs - false on failure, true on success
|
||||||
* side effects - given id is added to the appropriate list
|
* side effects - given id is added to the appropriate list
|
||||||
*/
|
*/
|
||||||
int
|
bool
|
||||||
add_id(struct Client *source_p, struct Channel *chptr, const char *banid, const char *forward,
|
add_id(struct Client *source_p, struct Channel *chptr, const char *banid, const char *forward,
|
||||||
rb_dlink_list * list, long mode_type)
|
rb_dlink_list * list, long mode_type)
|
||||||
{
|
{
|
||||||
|
@ -258,14 +257,14 @@ add_id(struct Client *source_p, struct Channel *chptr, const char *banid, const
|
||||||
{
|
{
|
||||||
sendto_one(source_p, form_str(ERR_BANLISTFULL),
|
sendto_one(source_p, form_str(ERR_BANLISTFULL),
|
||||||
me.name, source_p->name, chptr->chname, realban);
|
me.name, source_p->name, chptr->chname, realban);
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
RB_DLINK_FOREACH(ptr, list->head)
|
RB_DLINK_FOREACH(ptr, list->head)
|
||||||
{
|
{
|
||||||
actualBan = ptr->data;
|
actualBan = ptr->data;
|
||||||
if(mask_match(actualBan->banstr, realban))
|
if(mask_match(actualBan->banstr, realban))
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/* dont let remotes set duplicates */
|
/* dont let remotes set duplicates */
|
||||||
|
@ -275,7 +274,7 @@ add_id(struct Client *source_p, struct Channel *chptr, const char *banid, const
|
||||||
{
|
{
|
||||||
actualBan = ptr->data;
|
actualBan = ptr->data;
|
||||||
if(!irccmp(actualBan->banstr, realban))
|
if(!irccmp(actualBan->banstr, realban))
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -294,7 +293,7 @@ add_id(struct Client *source_p, struct Channel *chptr, const char *banid, const
|
||||||
if(mode_type == CHFL_BAN || mode_type == CHFL_QUIET || mode_type == CHFL_EXCEPTION)
|
if(mode_type == CHFL_BAN || mode_type == CHFL_QUIET || mode_type == CHFL_EXCEPTION)
|
||||||
chptr->bants++;
|
chptr->bants++;
|
||||||
|
|
||||||
return 1;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* del_id()
|
/* del_id()
|
||||||
|
@ -487,7 +486,7 @@ pretty_mask(const char *idmask)
|
||||||
* output - true if forwarding should be allowed
|
* output - true if forwarding should be allowed
|
||||||
* side effects - numeric sent if not allowed
|
* side effects - numeric sent if not allowed
|
||||||
*/
|
*/
|
||||||
static int
|
static bool
|
||||||
check_forward(struct Client *source_p, struct Channel *chptr,
|
check_forward(struct Client *source_p, struct Channel *chptr,
|
||||||
const char *forward)
|
const char *forward)
|
||||||
{
|
{
|
||||||
|
@ -498,20 +497,20 @@ check_forward(struct Client *source_p, struct Channel *chptr,
|
||||||
(MyClient(source_p) && (strlen(forward) > LOC_CHANNELLEN || hash_find_resv(forward))))
|
(MyClient(source_p) && (strlen(forward) > LOC_CHANNELLEN || hash_find_resv(forward))))
|
||||||
{
|
{
|
||||||
sendto_one_numeric(source_p, ERR_BADCHANNAME, form_str(ERR_BADCHANNAME), forward);
|
sendto_one_numeric(source_p, ERR_BADCHANNAME, form_str(ERR_BADCHANNAME), forward);
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
/* don't forward to inconsistent target -- jilles */
|
/* don't forward to inconsistent target -- jilles */
|
||||||
if(chptr->chname[0] == '#' && forward[0] == '&')
|
if(chptr->chname[0] == '#' && forward[0] == '&')
|
||||||
{
|
{
|
||||||
sendto_one_numeric(source_p, ERR_BADCHANNAME,
|
sendto_one_numeric(source_p, ERR_BADCHANNAME,
|
||||||
form_str(ERR_BADCHANNAME), forward);
|
form_str(ERR_BADCHANNAME), forward);
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
if(MyClient(source_p) && (targptr = find_channel(forward)) == NULL)
|
if(MyClient(source_p) && (targptr = find_channel(forward)) == NULL)
|
||||||
{
|
{
|
||||||
sendto_one_numeric(source_p, ERR_NOSUCHCHANNEL,
|
sendto_one_numeric(source_p, ERR_NOSUCHCHANNEL,
|
||||||
form_str(ERR_NOSUCHCHANNEL), forward);
|
form_str(ERR_NOSUCHCHANNEL), forward);
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
if(MyClient(source_p) && !(targptr->mode.mode & MODE_FREETARGET))
|
if(MyClient(source_p) && !(targptr->mode.mode & MODE_FREETARGET))
|
||||||
{
|
{
|
||||||
|
@ -520,10 +519,10 @@ check_forward(struct Client *source_p, struct Channel *chptr,
|
||||||
{
|
{
|
||||||
sendto_one(source_p, form_str(ERR_CHANOPRIVSNEEDED),
|
sendto_one(source_p, form_str(ERR_CHANOPRIVSNEEDED),
|
||||||
me.name, source_p->name, targptr->chname);
|
me.name, source_p->name, targptr->chname);
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return 1;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* fix_key()
|
/* fix_key()
|
||||||
|
@ -536,9 +535,9 @@ check_forward(struct Client *source_p, struct Channel *chptr,
|
||||||
static char *
|
static char *
|
||||||
fix_key(char *arg)
|
fix_key(char *arg)
|
||||||
{
|
{
|
||||||
u_char *s, *t, c;
|
unsigned char *s, *t, c;
|
||||||
|
|
||||||
for(s = t = (u_char *) arg; (c = *s); s++)
|
for(s = t = (unsigned char *) arg; (c = *s); s++)
|
||||||
{
|
{
|
||||||
c &= 0x7f;
|
c &= 0x7f;
|
||||||
if(c != ':' && c != ',' && c > ' ')
|
if(c != ':' && c != ',' && c > ' ')
|
||||||
|
@ -559,9 +558,9 @@ fix_key(char *arg)
|
||||||
static char *
|
static char *
|
||||||
fix_key_remote(char *arg)
|
fix_key_remote(char *arg)
|
||||||
{
|
{
|
||||||
u_char *s, *t, c;
|
unsigned char *s, *t, c;
|
||||||
|
|
||||||
for(s = t = (u_char *) arg; (c = *s); s++)
|
for(s = t = (unsigned char *) arg; (c = *s); s++)
|
||||||
{
|
{
|
||||||
c &= 0x7f;
|
c &= 0x7f;
|
||||||
if((c != 0x0a) && (c != ':') && (c != ',') && (c != 0x0d) && (c != ' '))
|
if((c != 0x0a) && (c != ':') && (c != ',') && (c != 0x0d) && (c != ' '))
|
||||||
|
@ -889,7 +888,7 @@ chm_ban(struct Client *source_p, struct Channel *chptr,
|
||||||
* also make sure it will always fit on a line with channel
|
* also make sure it will always fit on a line with channel
|
||||||
* name etc.
|
* name etc.
|
||||||
*/
|
*/
|
||||||
if(strlen(mask) > IRCD_MIN(BANLEN, MODEBUFLEN - 5))
|
if(strlen(mask) > MIN(BANLEN, MODEBUFLEN - 5))
|
||||||
{
|
{
|
||||||
sendto_one_numeric(source_p, ERR_INVALIDBAN,
|
sendto_one_numeric(source_p, ERR_INVALIDBAN,
|
||||||
form_str(ERR_INVALIDBAN),
|
form_str(ERR_INVALIDBAN),
|
||||||
|
|
|
@ -23,11 +23,10 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
|
|
||||||
#include "class.h"
|
#include "class.h"
|
||||||
#include "client.h"
|
#include "client.h"
|
||||||
#include "common.h"
|
|
||||||
#include "ircd.h"
|
#include "ircd.h"
|
||||||
#include "numeric.h"
|
#include "numeric.h"
|
||||||
#include "s_conf.h"
|
#include "s_conf.h"
|
||||||
|
|
108
ircd/client.c
108
ircd/client.c
|
@ -23,11 +23,10 @@
|
||||||
* USA
|
* USA
|
||||||
*/
|
*/
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
|
|
||||||
#include "client.h"
|
#include "client.h"
|
||||||
#include "class.h"
|
#include "class.h"
|
||||||
#include "common.h"
|
|
||||||
#include "hash.h"
|
#include "hash.h"
|
||||||
#include "match.h"
|
#include "match.h"
|
||||||
#include "ircd.h"
|
#include "ircd.h"
|
||||||
|
@ -77,9 +76,9 @@ static rb_bh *pclient_heap = NULL;
|
||||||
static rb_bh *user_heap = NULL;
|
static rb_bh *user_heap = NULL;
|
||||||
static rb_bh *away_heap = NULL;
|
static rb_bh *away_heap = NULL;
|
||||||
static char current_uid[IDLEN];
|
static char current_uid[IDLEN];
|
||||||
static int32_t current_connid = 0;
|
static uint32_t current_connid = 0;
|
||||||
|
|
||||||
struct Dictionary *nd_dict = NULL;
|
rb_dictionary *nd_dict = NULL;
|
||||||
|
|
||||||
enum
|
enum
|
||||||
{
|
{
|
||||||
|
@ -130,6 +129,78 @@ init_client(void)
|
||||||
nd_dict = rb_dictionary_create("nickdelay", irccmp);
|
nd_dict = rb_dictionary_create("nickdelay", irccmp);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* connid_get - allocate a connid
|
||||||
|
*
|
||||||
|
* inputs - none
|
||||||
|
* outputs - a connid token which is used to represent a logical circuit
|
||||||
|
* side effects - current_connid is incremented, possibly multiple times.
|
||||||
|
* the association of the connid to it's client is committed.
|
||||||
|
*/
|
||||||
|
uint32_t
|
||||||
|
connid_get(struct Client *client_p)
|
||||||
|
{
|
||||||
|
s_assert(MyClient(client_p));
|
||||||
|
if (!MyClient(client_p))
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
/* find a connid that is available */
|
||||||
|
while (find_cli_connid_hash(++current_connid) != NULL)
|
||||||
|
{
|
||||||
|
/* handle wraparound, current_connid must NEVER be 0 */
|
||||||
|
if (current_connid == 0)
|
||||||
|
++current_connid;
|
||||||
|
}
|
||||||
|
|
||||||
|
add_to_cli_connid_hash(client_p, current_connid);
|
||||||
|
rb_dlinkAddAlloc(RB_UINT_TO_POINTER(current_connid), &client_p->localClient->connids);
|
||||||
|
|
||||||
|
return current_connid;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* connid_put - free a connid
|
||||||
|
*
|
||||||
|
* inputs - connid to free
|
||||||
|
* outputs - nothing
|
||||||
|
* side effects - connid bookkeeping structures are freed
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
connid_put(uint32_t id)
|
||||||
|
{
|
||||||
|
struct Client *client_p;
|
||||||
|
|
||||||
|
s_assert(id != 0);
|
||||||
|
if (id == 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
client_p = find_cli_connid_hash(id);
|
||||||
|
if (client_p == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
|
del_from_cli_connid_hash(id);
|
||||||
|
rb_dlinkFindDestroy(RB_UINT_TO_POINTER(id), &client_p->localClient->connids);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* client_release_connids - release any connids still attached to a client
|
||||||
|
*
|
||||||
|
* inputs - client to garbage collect
|
||||||
|
* outputs - none
|
||||||
|
* side effects - client's connids are garbage collected
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
client_release_connids(struct Client *client_p)
|
||||||
|
{
|
||||||
|
rb_dlink_node *ptr, *ptr2;
|
||||||
|
|
||||||
|
s_assert(MyClient(client_p));
|
||||||
|
if (!MyClient(client_p))
|
||||||
|
return;
|
||||||
|
|
||||||
|
RB_DLINK_FOREACH_SAFE(ptr, ptr2, client_p->localClient->connids.head)
|
||||||
|
connid_put(RB_POINTER_TO_UINT(ptr->data));
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* make_client - create a new Client struct and set it to initial state.
|
* make_client - create a new Client struct and set it to initial state.
|
||||||
|
@ -161,17 +232,6 @@ make_client(struct Client *from)
|
||||||
|
|
||||||
client_p->localClient->F = NULL;
|
client_p->localClient->F = NULL;
|
||||||
|
|
||||||
if(current_connid+1 == 0)
|
|
||||||
current_connid++;
|
|
||||||
|
|
||||||
client_p->localClient->connid = ++current_connid;
|
|
||||||
|
|
||||||
if(current_connid+1 == 0)
|
|
||||||
current_connid++;
|
|
||||||
|
|
||||||
client_p->localClient->zconnid = ++current_connid;
|
|
||||||
add_to_cli_connid_hash(client_p);
|
|
||||||
|
|
||||||
client_p->preClient = rb_bh_alloc(pclient_heap);
|
client_p->preClient = rb_bh_alloc(pclient_heap);
|
||||||
|
|
||||||
/* as good a place as any... */
|
/* as good a place as any... */
|
||||||
|
@ -230,7 +290,7 @@ free_local_client(struct Client *client_p)
|
||||||
client_p->localClient->listener = 0;
|
client_p->localClient->listener = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
del_from_cli_connid_hash(client_p);
|
client_release_connids(client_p);
|
||||||
if(client_p->localClient->F != NULL)
|
if(client_p->localClient->F != NULL)
|
||||||
{
|
{
|
||||||
rb_close(client_p->localClient->F);
|
rb_close(client_p->localClient->F);
|
||||||
|
@ -542,7 +602,7 @@ check_dlines(void)
|
||||||
if(IsMe(client_p))
|
if(IsMe(client_p))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if((aconf = find_dline((struct sockaddr *)&client_p->localClient->ip,client_p->localClient->ip.ss_family)) != NULL)
|
if((aconf = find_dline((struct sockaddr *)&client_p->localClient->ip, GET_SS_FAMILY(&client_p->localClient->ip))) != NULL)
|
||||||
{
|
{
|
||||||
if(aconf->status & CONF_EXEMPTDLINE)
|
if(aconf->status & CONF_EXEMPTDLINE)
|
||||||
continue;
|
continue;
|
||||||
|
@ -561,7 +621,7 @@ check_dlines(void)
|
||||||
{
|
{
|
||||||
client_p = ptr->data;
|
client_p = ptr->data;
|
||||||
|
|
||||||
if((aconf = find_dline((struct sockaddr *)&client_p->localClient->ip,client_p->localClient->ip.ss_family)) != NULL)
|
if((aconf = find_dline((struct sockaddr *)&client_p->localClient->ip, GET_SS_FAMILY(&client_p->localClient->ip))) != NULL)
|
||||||
{
|
{
|
||||||
if(aconf->status & CONF_EXEMPTDLINE)
|
if(aconf->status & CONF_EXEMPTDLINE)
|
||||||
continue;
|
continue;
|
||||||
|
@ -1802,15 +1862,15 @@ free_user(struct User *user, struct Client *client_p)
|
||||||
if(user->refcnt < 0 || user->invited.head || user->channel.head)
|
if(user->refcnt < 0 || user->invited.head || user->channel.head)
|
||||||
{
|
{
|
||||||
sendto_realops_snomask(SNO_GENERAL, L_ALL,
|
sendto_realops_snomask(SNO_GENERAL, L_ALL,
|
||||||
"* %#lx user (%s!%s@%s) %#lx %#lx %#lx %lu %d *",
|
"* %p user (%s!%s@%s) %p %p %p %lu %d *",
|
||||||
(unsigned long) client_p,
|
client_p,
|
||||||
client_p ? client_p->
|
client_p ? client_p->
|
||||||
name : "<noname>",
|
name : "<noname>",
|
||||||
client_p->username,
|
client_p->username,
|
||||||
client_p->host,
|
client_p->host,
|
||||||
(unsigned long) user,
|
user,
|
||||||
(unsigned long) user->invited.head,
|
user->invited.head,
|
||||||
(unsigned long) user->channel.head,
|
user->channel.head,
|
||||||
rb_dlink_list_length(&user->channel),
|
rb_dlink_list_length(&user->channel),
|
||||||
user->refcnt);
|
user->refcnt);
|
||||||
s_assert(!user->refcnt);
|
s_assert(!user->refcnt);
|
||||||
|
@ -1950,7 +2010,7 @@ close_connection(struct Client *client_p)
|
||||||
else
|
else
|
||||||
ServerStats.is_ni++;
|
ServerStats.is_ni++;
|
||||||
|
|
||||||
del_from_cli_connid_hash(client_p);
|
client_release_connids(client_p);
|
||||||
|
|
||||||
if(client_p->localClient->F != NULL)
|
if(client_p->localClient->F != NULL)
|
||||||
{
|
{
|
||||||
|
|
206
ircd/dns.c
206
ircd/dns.c
|
@ -37,16 +37,13 @@
|
||||||
#include "msg.h"
|
#include "msg.h"
|
||||||
#include "hash.h"
|
#include "hash.h"
|
||||||
|
|
||||||
#define DNS_IDTABLE_SIZE 0x2000
|
|
||||||
#define DNS_STATTABLE_SIZE 0x10
|
|
||||||
|
|
||||||
#define DNS_HOST_IPV4 ((char)'4')
|
#define DNS_HOST_IPV4 ((char)'4')
|
||||||
#define DNS_HOST_IPV6 ((char)'6')
|
#define DNS_HOST_IPV6 ((char)'6')
|
||||||
#define DNS_REVERSE_IPV4 ((char)'R')
|
#define DNS_REVERSE_IPV4 ((char)'R')
|
||||||
#define DNS_REVERSE_IPV6 ((char)'S')
|
#define DNS_REVERSE_IPV6 ((char)'S')
|
||||||
|
|
||||||
static void submit_dns(uint16_t uid, char type, const char *addr);
|
static void submit_dns(uint32_t uid, char type, const char *addr);
|
||||||
static void submit_dns_stat(uint16_t uid);
|
static void submit_dns_stat(uint32_t uid);
|
||||||
|
|
||||||
struct dnsreq
|
struct dnsreq
|
||||||
{
|
{
|
||||||
|
@ -60,55 +57,24 @@ struct dnsstatreq
|
||||||
void *data;
|
void *data;
|
||||||
};
|
};
|
||||||
|
|
||||||
static struct dnsreq querytable[DNS_IDTABLE_SIZE];
|
/* These serve as a form of sparse array */
|
||||||
static struct dnsstatreq stattable[DNS_STATTABLE_SIZE];
|
static rb_dictionary *query_dict;
|
||||||
|
static rb_dictionary *stat_dict;
|
||||||
|
|
||||||
rb_dlink_list nameservers;
|
rb_dlink_list nameservers;
|
||||||
|
|
||||||
|
static uint32_t query_id = 0;
|
||||||
|
static uint32_t stat_id = 0;
|
||||||
|
|
||||||
static uint16_t
|
#define ASSIGN_ID(id) (id++)
|
||||||
assign_dns_id(void)
|
|
||||||
{
|
|
||||||
static uint16_t id = 1;
|
|
||||||
int loopcnt = 0;
|
|
||||||
while(1)
|
|
||||||
{
|
|
||||||
if(++loopcnt > DNS_IDTABLE_SIZE)
|
|
||||||
return 0;
|
|
||||||
if(id < DNS_IDTABLE_SIZE - 1 || id == 0)
|
|
||||||
id++;
|
|
||||||
else
|
|
||||||
id = 1;
|
|
||||||
if(querytable[id].callback == NULL)
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
return (id);
|
|
||||||
}
|
|
||||||
|
|
||||||
static uint8_t
|
|
||||||
assign_dns_stat_id(void)
|
|
||||||
{
|
|
||||||
static uint8_t id = 1;
|
|
||||||
int loopcnt = 0;
|
|
||||||
while(1)
|
|
||||||
{
|
|
||||||
if(++loopcnt > DNS_STATTABLE_SIZE)
|
|
||||||
return 0;
|
|
||||||
if(id < DNS_STATTABLE_SIZE - 1 || id == 0)
|
|
||||||
id++;
|
|
||||||
else
|
|
||||||
id = 1;
|
|
||||||
if(stattable[id].callback == NULL)
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
return (id);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
handle_dns_failure(uint16_t xid)
|
handle_dns_failure(uint32_t xid)
|
||||||
{
|
{
|
||||||
struct dnsreq *req;
|
struct dnsreq *req = rb_dictionary_retrieve(query_dict, RB_UINT_TO_POINTER(xid));
|
||||||
|
s_assert(req);
|
||||||
|
|
||||||
req = &querytable[xid];
|
|
||||||
if(req->callback == NULL)
|
if(req->callback == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
@ -118,47 +84,49 @@ handle_dns_failure(uint16_t xid)
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
handle_dns_stat_failure(uint8_t xid)
|
handle_dns_stat_failure(uint32_t xid)
|
||||||
{
|
{
|
||||||
struct dnsstatreq *req;
|
struct dnsstatreq *req = rb_dictionary_retrieve(stat_dict, RB_UINT_TO_POINTER(xid));
|
||||||
const char *err[] = { "Unknown failure" };
|
s_assert(req);
|
||||||
|
|
||||||
req = &stattable[xid];
|
|
||||||
if(req->callback == NULL)
|
if(req->callback == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
req->callback(1, err, 2, req->data);
|
req->callback(1, NULL, 2, req->data);
|
||||||
|
req->callback = NULL;
|
||||||
|
req->data = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
cancel_lookup(uint32_t xid)
|
||||||
|
{
|
||||||
|
struct dnsreq *req = rb_dictionary_retrieve(query_dict, RB_UINT_TO_POINTER(xid));
|
||||||
|
s_assert(req);
|
||||||
req->callback = NULL;
|
req->callback = NULL;
|
||||||
req->data = NULL;
|
req->data = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
cancel_lookup(uint16_t xid)
|
cancel_dns_stats(uint32_t xid)
|
||||||
{
|
{
|
||||||
querytable[xid].callback = NULL;
|
struct dnsstatreq *req = rb_dictionary_retrieve(stat_dict, RB_UINT_TO_POINTER(xid));
|
||||||
querytable[xid].data = NULL;
|
s_assert(req);
|
||||||
|
req->callback = NULL;
|
||||||
|
req->data = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
|
||||||
cancel_dns_stats(uint16_t xid)
|
|
||||||
{
|
|
||||||
stattable[xid].callback = NULL;
|
|
||||||
stattable[xid].data = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
uint16_t
|
uint32_t
|
||||||
lookup_hostname(const char *hostname, int aftype, DNSCB callback, void *data)
|
lookup_hostname(const char *hostname, int aftype, DNSCB callback, void *data)
|
||||||
{
|
{
|
||||||
struct dnsreq *req;
|
struct dnsreq *req = rb_malloc(sizeof(struct dnsreq));
|
||||||
int aft;
|
int aft;
|
||||||
uint16_t nid;
|
uint32_t rid = ASSIGN_ID(query_id);
|
||||||
check_authd();
|
|
||||||
nid = assign_dns_id();
|
|
||||||
if((nid = assign_dns_id()) == 0)
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
req = &querytable[nid];
|
check_authd();
|
||||||
|
|
||||||
|
rb_dictionary_add(query_dict, RB_UINT_TO_POINTER(rid), req);
|
||||||
|
|
||||||
req->callback = callback;
|
req->callback = callback;
|
||||||
req->data = data;
|
req->data = data;
|
||||||
|
@ -170,22 +138,20 @@ lookup_hostname(const char *hostname, int aftype, DNSCB callback, void *data)
|
||||||
#endif
|
#endif
|
||||||
aft = 4;
|
aft = 4;
|
||||||
|
|
||||||
submit_dns(nid, aft == 4 ? DNS_HOST_IPV4 : DNS_HOST_IPV6, hostname);
|
submit_dns(rid, aft == 4 ? DNS_HOST_IPV4 : DNS_HOST_IPV6, hostname);
|
||||||
return (nid);
|
return (rid);
|
||||||
}
|
}
|
||||||
|
|
||||||
uint16_t
|
uint32_t
|
||||||
lookup_ip(const char *addr, int aftype, DNSCB callback, void *data)
|
lookup_ip(const char *addr, int aftype, DNSCB callback, void *data)
|
||||||
{
|
{
|
||||||
struct dnsreq *req;
|
struct dnsreq *req = rb_malloc(sizeof(struct dnsreq));
|
||||||
int aft;
|
int aft;
|
||||||
uint16_t nid;
|
uint32_t rid = ASSIGN_ID(query_id);
|
||||||
|
|
||||||
check_authd();
|
check_authd();
|
||||||
|
|
||||||
if((nid = assign_dns_id()) == 0)
|
rb_dictionary_add(query_dict, RB_UINT_TO_POINTER(rid), req);
|
||||||
return 0;
|
|
||||||
|
|
||||||
req = &querytable[nid];
|
|
||||||
|
|
||||||
req->callback = callback;
|
req->callback = callback;
|
||||||
req->data = data;
|
req->data = data;
|
||||||
|
@ -197,41 +163,45 @@ lookup_ip(const char *addr, int aftype, DNSCB callback, void *data)
|
||||||
#endif
|
#endif
|
||||||
aft = 4;
|
aft = 4;
|
||||||
|
|
||||||
submit_dns(nid, aft == 4 ? DNS_REVERSE_IPV4 : DNS_REVERSE_IPV6, addr);
|
submit_dns(rid, aft == 4 ? DNS_REVERSE_IPV4 : DNS_REVERSE_IPV6, addr);
|
||||||
return (nid);
|
return (rid);
|
||||||
}
|
}
|
||||||
|
|
||||||
uint8_t
|
uint32_t
|
||||||
get_nameservers(DNSLISTCB callback, void *data)
|
get_nameservers(DNSLISTCB callback, void *data)
|
||||||
{
|
{
|
||||||
struct dnsstatreq *req;
|
struct dnsstatreq *req = rb_malloc(sizeof(struct dnsstatreq));
|
||||||
uint8_t nid;
|
uint32_t qid = ASSIGN_ID(stat_id);
|
||||||
|
|
||||||
check_authd();
|
check_authd();
|
||||||
|
|
||||||
if((nid = assign_dns_stat_id()) == 0)
|
rb_dictionary_add(stat_dict, RB_UINT_TO_POINTER(qid), req);
|
||||||
return 0;
|
|
||||||
|
|
||||||
req = &stattable[nid];
|
|
||||||
req->callback = callback;
|
req->callback = callback;
|
||||||
req->data = data;
|
req->data = data;
|
||||||
|
|
||||||
submit_dns_stat(nid);
|
submit_dns_stat(qid);
|
||||||
return (nid);
|
return (qid);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
dns_results_callback(const char *callid, const char *status, const char *type, const char *results)
|
dns_results_callback(const char *callid, const char *status, const char *type, const char *results)
|
||||||
{
|
{
|
||||||
struct dnsreq *req;
|
struct dnsreq *req;
|
||||||
uint16_t nid;
|
uint32_t rid;
|
||||||
int st;
|
int st;
|
||||||
int aft;
|
int aft;
|
||||||
long lnid = strtol(callid, NULL, 16);
|
long lrid = strtol(callid, NULL, 16);
|
||||||
|
|
||||||
if(lnid > DNS_IDTABLE_SIZE || lnid == 0)
|
if(lrid > UINT32_MAX)
|
||||||
return;
|
return;
|
||||||
nid = (uint16_t)lnid;
|
|
||||||
req = &querytable[nid];
|
rid = (uint32_t)lrid;
|
||||||
|
req = rb_dictionary_retrieve(query_dict, RB_UINT_TO_POINTER(rid));
|
||||||
|
if(req == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
st = (*status == 'O');
|
st = (*status == 'O');
|
||||||
aft = *type == '6' || *type == 'S' ? 6 : 4;
|
aft = *type == '6' || *type == 'S' ? 6 : 4;
|
||||||
if(req->callback == NULL)
|
if(req->callback == NULL)
|
||||||
|
@ -248,22 +218,26 @@ dns_results_callback(const char *callid, const char *status, const char *type, c
|
||||||
aft = AF_INET;
|
aft = AF_INET;
|
||||||
|
|
||||||
req->callback(results, st, aft, req->data);
|
req->callback(results, st, aft, req->data);
|
||||||
req->callback = NULL;
|
|
||||||
req->data = NULL;
|
rb_free(req);
|
||||||
|
rb_dictionary_delete(query_dict, RB_UINT_TO_POINTER(rid));
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
dns_stats_results_callback(const char *callid, const char *status, int resc, const char *resv[])
|
dns_stats_results_callback(const char *callid, const char *status, int resc, const char *resv[])
|
||||||
{
|
{
|
||||||
struct dnsstatreq *req;
|
struct dnsstatreq *req;
|
||||||
uint8_t nid;
|
uint32_t qid;
|
||||||
int st, i;
|
int st;
|
||||||
long lnid = strtol(callid, NULL, 16);
|
long lqid = strtol(callid, NULL, 16);
|
||||||
|
|
||||||
if(lnid > DNS_STATTABLE_SIZE || lnid == 0)
|
if(lqid > UINT32_MAX)
|
||||||
return;
|
return;
|
||||||
nid = (uint8_t)lnid;
|
|
||||||
req = &stattable[nid];
|
qid = (uint32_t)lqid;
|
||||||
|
req = rb_dictionary_retrieve(stat_dict, RB_UINT_TO_POINTER(qid));
|
||||||
|
|
||||||
|
s_assert(req);
|
||||||
|
|
||||||
if(req->callback == NULL)
|
if(req->callback == NULL)
|
||||||
{
|
{
|
||||||
|
@ -286,14 +260,14 @@ dns_stats_results_callback(const char *callid, const char *status, int resc, con
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Query complete */
|
/* Query complete */
|
||||||
req->callback(resc, resv, st, stattable[nid].data);
|
req->callback(resc, resv, st, req->data);
|
||||||
|
|
||||||
req->data = NULL;
|
rb_free(req);
|
||||||
req->callback = NULL;
|
rb_dictionary_delete(stat_dict, RB_UINT_TO_POINTER(qid));
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
get_nameservers_cb(int resc, const char *resv[], int status, void *data)
|
stats_results_callback(int resc, const char *resv[], int status, void *data)
|
||||||
{
|
{
|
||||||
if(status == 0)
|
if(status == 0)
|
||||||
{
|
{
|
||||||
|
@ -316,28 +290,26 @@ get_nameservers_cb(int resc, const char *resv[], int status, void *data)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
init_nameserver_cache(void)
|
init_dns(void)
|
||||||
{
|
{
|
||||||
(void)get_nameservers(get_nameservers_cb, NULL);
|
query_dict = rb_dictionary_create("dns queries", rb_uint32cmp);
|
||||||
|
stat_dict = rb_dictionary_create("dns stat queries", rb_uint32cmp);
|
||||||
|
(void)get_nameservers(stats_results_callback, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
void
|
||||||
reload_nameservers(void)
|
reload_nameservers(void)
|
||||||
{
|
{
|
||||||
if(authd_helper == NULL)
|
check_authd();
|
||||||
{
|
rb_helper_write(authd_helper, "R D");
|
||||||
/* Shit */
|
(void)get_nameservers(stats_results_callback, NULL);
|
||||||
return false;
|
|
||||||
}
|
|
||||||
rb_helper_write(authd_helper, "H D");
|
|
||||||
init_nameserver_cache();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
submit_dns(uint16_t nid, char type, const char *addr)
|
submit_dns(uint32_t nid, char type, const char *addr)
|
||||||
{
|
{
|
||||||
if(authd_helper == NULL)
|
if(authd_helper == NULL)
|
||||||
{
|
{
|
||||||
|
@ -348,7 +320,7 @@ submit_dns(uint16_t nid, char type, const char *addr)
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
submit_dns_stat(uint16_t nid)
|
submit_dns_stat(uint32_t nid)
|
||||||
{
|
{
|
||||||
if(authd_helper == NULL)
|
if(authd_helper == NULL)
|
||||||
{
|
{
|
||||||
|
|
|
@ -23,7 +23,6 @@
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "channel.h"
|
#include "channel.h"
|
||||||
#include "client.h"
|
#include "client.h"
|
||||||
#include "common.h"
|
|
||||||
|
|
||||||
ExtbanFunc extban_table[256] = { NULL };
|
ExtbanFunc extban_table[256] = { NULL };
|
||||||
|
|
||||||
|
|
65
ircd/hash.c
65
ircd/hash.c
|
@ -27,7 +27,6 @@
|
||||||
#include "s_conf.h"
|
#include "s_conf.h"
|
||||||
#include "channel.h"
|
#include "channel.h"
|
||||||
#include "client.h"
|
#include "client.h"
|
||||||
#include "common.h"
|
|
||||||
#include "hash.h"
|
#include "hash.h"
|
||||||
#include "match.h"
|
#include "match.h"
|
||||||
#include "ircd.h"
|
#include "ircd.h"
|
||||||
|
@ -40,14 +39,13 @@
|
||||||
#include "rb_dictionary.h"
|
#include "rb_dictionary.h"
|
||||||
#include "rb_radixtree.h"
|
#include "rb_radixtree.h"
|
||||||
|
|
||||||
struct Dictionary *client_connid_tree = NULL;
|
rb_dictionary *client_connid_tree = NULL;
|
||||||
struct Dictionary *client_zconnid_tree = NULL;
|
rb_radixtree *client_id_tree = NULL;
|
||||||
struct rb_radixtree *client_id_tree = NULL;
|
rb_radixtree *client_name_tree = NULL;
|
||||||
struct rb_radixtree *client_name_tree = NULL;
|
|
||||||
|
|
||||||
struct rb_radixtree *channel_tree = NULL;
|
rb_radixtree *channel_tree = NULL;
|
||||||
struct rb_radixtree *resv_tree = NULL;
|
rb_radixtree *resv_tree = NULL;
|
||||||
struct rb_radixtree *hostname_tree = NULL;
|
rb_radixtree *hostname_tree = NULL;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* look in whowas.c for the missing ...[WW_MAX]; entry
|
* look in whowas.c for the missing ...[WW_MAX]; entry
|
||||||
|
@ -61,7 +59,6 @@ void
|
||||||
init_hash(void)
|
init_hash(void)
|
||||||
{
|
{
|
||||||
client_connid_tree = rb_dictionary_create("client connid", rb_uint32cmp);
|
client_connid_tree = rb_dictionary_create("client connid", rb_uint32cmp);
|
||||||
client_zconnid_tree = rb_dictionary_create("client zconnid", rb_uint32cmp);
|
|
||||||
client_id_tree = rb_radixtree_create("client id", NULL);
|
client_id_tree = rb_radixtree_create("client id", NULL);
|
||||||
client_name_tree = rb_radixtree_create("client name", irccasecanon);
|
client_name_tree = rb_radixtree_create("client name", irccasecanon);
|
||||||
|
|
||||||
|
@ -71,10 +68,10 @@ init_hash(void)
|
||||||
hostname_tree = rb_radixtree_create("hostname", irccasecanon);
|
hostname_tree = rb_radixtree_create("hostname", irccasecanon);
|
||||||
}
|
}
|
||||||
|
|
||||||
u_int32_t
|
uint32_t
|
||||||
fnv_hash_upper(const unsigned char *s, int bits)
|
fnv_hash_upper(const unsigned char *s, int bits)
|
||||||
{
|
{
|
||||||
u_int32_t h = FNV1_32_INIT;
|
uint32_t h = FNV1_32_INIT;
|
||||||
|
|
||||||
while (*s)
|
while (*s)
|
||||||
{
|
{
|
||||||
|
@ -86,10 +83,10 @@ fnv_hash_upper(const unsigned char *s, int bits)
|
||||||
return h;
|
return h;
|
||||||
}
|
}
|
||||||
|
|
||||||
u_int32_t
|
uint32_t
|
||||||
fnv_hash(const unsigned char *s, int bits)
|
fnv_hash(const unsigned char *s, int bits)
|
||||||
{
|
{
|
||||||
u_int32_t h = FNV1_32_INIT;
|
uint32_t h = FNV1_32_INIT;
|
||||||
|
|
||||||
while (*s)
|
while (*s)
|
||||||
{
|
{
|
||||||
|
@ -101,10 +98,10 @@ fnv_hash(const unsigned char *s, int bits)
|
||||||
return h;
|
return h;
|
||||||
}
|
}
|
||||||
|
|
||||||
u_int32_t
|
uint32_t
|
||||||
fnv_hash_len(const unsigned char *s, int bits, int len)
|
fnv_hash_len(const unsigned char *s, int bits, int len)
|
||||||
{
|
{
|
||||||
u_int32_t h = FNV1_32_INIT;
|
uint32_t h = FNV1_32_INIT;
|
||||||
const unsigned char *x = s + len;
|
const unsigned char *x = s + len;
|
||||||
while (*s && s < x)
|
while (*s && s < x)
|
||||||
{
|
{
|
||||||
|
@ -116,10 +113,10 @@ fnv_hash_len(const unsigned char *s, int bits, int len)
|
||||||
return h;
|
return h;
|
||||||
}
|
}
|
||||||
|
|
||||||
u_int32_t
|
uint32_t
|
||||||
fnv_hash_upper_len(const unsigned char *s, int bits, int len)
|
fnv_hash_upper_len(const unsigned char *s, int bits, int len)
|
||||||
{
|
{
|
||||||
u_int32_t h = FNV1_32_INIT;
|
uint32_t h = FNV1_32_INIT;
|
||||||
const unsigned char *x = s + len;
|
const unsigned char *x = s + len;
|
||||||
while (*s && s < x)
|
while (*s && s < x)
|
||||||
{
|
{
|
||||||
|
@ -480,7 +477,7 @@ void
|
||||||
clear_resv_hash(void)
|
clear_resv_hash(void)
|
||||||
{
|
{
|
||||||
struct ConfItem *aconf;
|
struct ConfItem *aconf;
|
||||||
struct rb_radixtree_iteration_state iter;
|
rb_radixtree_iteration_state iter;
|
||||||
|
|
||||||
RB_RADIXTREE_FOREACH(aconf, &iter, resv_tree)
|
RB_RADIXTREE_FOREACH(aconf, &iter, resv_tree)
|
||||||
{
|
{
|
||||||
|
@ -494,41 +491,19 @@ clear_resv_hash(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
add_to_zconnid_hash(struct Client *client_p)
|
add_to_cli_connid_hash(struct Client *client_p, uint32_t id)
|
||||||
{
|
{
|
||||||
rb_dictionary_add(client_zconnid_tree, RB_UINT_TO_POINTER(client_p->localClient->zconnid), client_p);
|
rb_dictionary_add(client_connid_tree, RB_UINT_TO_POINTER(id), client_p);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
del_from_zconnid_hash(struct Client *client_p)
|
del_from_cli_connid_hash(uint32_t id)
|
||||||
{
|
{
|
||||||
rb_dictionary_delete(client_zconnid_tree, RB_UINT_TO_POINTER(client_p->localClient->zconnid));
|
rb_dictionary_delete(client_connid_tree, RB_UINT_TO_POINTER(id));
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
add_to_cli_connid_hash(struct Client *client_p)
|
|
||||||
{
|
|
||||||
rb_dictionary_add(client_connid_tree, RB_UINT_TO_POINTER(client_p->localClient->connid), client_p);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
del_from_cli_connid_hash(struct Client *client_p)
|
|
||||||
{
|
|
||||||
rb_dictionary_delete(client_connid_tree, RB_UINT_TO_POINTER(client_p->localClient->connid));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
struct Client *
|
struct Client *
|
||||||
find_cli_connid_hash(uint32_t connid)
|
find_cli_connid_hash(uint32_t connid)
|
||||||
{
|
{
|
||||||
struct Client *target_p;
|
return rb_dictionary_retrieve(client_connid_tree, RB_UINT_TO_POINTER(connid));
|
||||||
|
|
||||||
target_p = rb_dictionary_retrieve(client_connid_tree, RB_UINT_TO_POINTER(connid));
|
|
||||||
if (target_p != NULL)
|
|
||||||
return target_p;
|
|
||||||
|
|
||||||
target_p = rb_dictionary_retrieve(client_zconnid_tree, RB_UINT_TO_POINTER(connid));
|
|
||||||
if (target_p != NULL)
|
|
||||||
return target_p;
|
|
||||||
|
|
||||||
return NULL;
|
|
||||||
}
|
}
|
||||||
|
|
165
ircd/ircd.c
165
ircd/ircd.c
|
@ -26,12 +26,11 @@
|
||||||
#include "rb_lib.h"
|
#include "rb_lib.h"
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "setup.h"
|
#include "setup.h"
|
||||||
#include "config.h"
|
#include "defaults.h"
|
||||||
#include "ircd.h"
|
#include "ircd.h"
|
||||||
#include "channel.h"
|
#include "channel.h"
|
||||||
#include "class.h"
|
#include "class.h"
|
||||||
#include "client.h"
|
#include "client.h"
|
||||||
#include "common.h"
|
|
||||||
#include "hash.h"
|
#include "hash.h"
|
||||||
#include "match.h"
|
#include "match.h"
|
||||||
#include "ircd_signal.h"
|
#include "ircd_signal.h"
|
||||||
|
@ -95,9 +94,6 @@ rb_dlink_list global_serv_list; /* global servers on the network */
|
||||||
rb_dlink_list local_oper_list; /* our opers, duplicated in lclient_list */
|
rb_dlink_list local_oper_list; /* our opers, duplicated in lclient_list */
|
||||||
rb_dlink_list oper_list; /* network opers */
|
rb_dlink_list oper_list; /* network opers */
|
||||||
|
|
||||||
const char *logFileName = LPATH;
|
|
||||||
const char *pidFileName = PPATH;
|
|
||||||
|
|
||||||
char **myargv;
|
char **myargv;
|
||||||
bool dorehash = false;
|
bool dorehash = false;
|
||||||
bool dorehashbans = false;
|
bool dorehashbans = false;
|
||||||
|
@ -105,8 +101,8 @@ bool doremotd = false;
|
||||||
bool kline_queued = false;
|
bool kline_queued = false;
|
||||||
bool server_state_foreground = false;
|
bool server_state_foreground = false;
|
||||||
bool opers_see_all_users = false;
|
bool opers_see_all_users = false;
|
||||||
bool ssl_ok = false;
|
bool ircd_ssl_ok = false;
|
||||||
bool zlib_ok = true;
|
bool ircd_zlib_ok = true;
|
||||||
|
|
||||||
int testing_conf = 0;
|
int testing_conf = 0;
|
||||||
time_t startup_time;
|
time_t startup_time;
|
||||||
|
@ -119,6 +115,28 @@ int split_users;
|
||||||
int split_servers;
|
int split_servers;
|
||||||
int eob_count;
|
int eob_count;
|
||||||
|
|
||||||
|
const char *ircd_paths[IRCD_PATH_COUNT] = {
|
||||||
|
[IRCD_PATH_PREFIX] = DPATH,
|
||||||
|
[IRCD_PATH_MODULES] = MODPATH,
|
||||||
|
[IRCD_PATH_AUTOLOAD_MODULES] = AUTOMODPATH,
|
||||||
|
[IRCD_PATH_ETC] = ETCPATH,
|
||||||
|
[IRCD_PATH_LOG] = LOGPATH,
|
||||||
|
[IRCD_PATH_USERHELP] = UHPATH,
|
||||||
|
[IRCD_PATH_OPERHELP] = HPATH,
|
||||||
|
[IRCD_PATH_IRCD_EXEC] = SPATH,
|
||||||
|
[IRCD_PATH_IRCD_CONF] = CPATH,
|
||||||
|
[IRCD_PATH_IRCD_MOTD] = MPATH,
|
||||||
|
[IRCD_PATH_IRCD_LOG] = LPATH,
|
||||||
|
[IRCD_PATH_IRCD_PID] = PPATH,
|
||||||
|
[IRCD_PATH_IRCD_OMOTD] = OPATH,
|
||||||
|
[IRCD_PATH_BANDB] = DBPATH,
|
||||||
|
[IRCD_PATH_BIN] = BINPATH,
|
||||||
|
[IRCD_PATH_LIBEXEC] = PKGLIBEXECDIR,
|
||||||
|
};
|
||||||
|
|
||||||
|
const char *logFileName = NULL;
|
||||||
|
const char *pidFileName = NULL;
|
||||||
|
|
||||||
void
|
void
|
||||||
ircd_shutdown(const char *reason)
|
ircd_shutdown(const char *reason)
|
||||||
{
|
{
|
||||||
|
@ -156,6 +174,7 @@ print_startup(int pid)
|
||||||
{
|
{
|
||||||
int fd;
|
int fd;
|
||||||
|
|
||||||
|
#ifndef _WIN32
|
||||||
close(1);
|
close(1);
|
||||||
fd = open("/dev/null", O_RDWR);
|
fd = open("/dev/null", O_RDWR);
|
||||||
if (fd == -1) {
|
if (fd == -1) {
|
||||||
|
@ -166,19 +185,30 @@ print_startup(int pid)
|
||||||
fd = dup(fd);
|
fd = dup(fd);
|
||||||
if (fd != 1)
|
if (fd != 1)
|
||||||
abort();
|
abort();
|
||||||
|
#endif
|
||||||
|
inotice("runtime path: %s", rb_path_to_self());
|
||||||
inotice("now running in %s mode from %s as pid %d ...",
|
inotice("now running in %s mode from %s as pid %d ...",
|
||||||
!server_state_foreground ? "background" : "foreground",
|
!server_state_foreground ? "background" : "foreground",
|
||||||
ConfigFileEntry.dpath, pid);
|
ConfigFileEntry.dpath, pid);
|
||||||
|
|
||||||
|
#ifndef _WIN32
|
||||||
/* let the parent process know the initialization was successful
|
/* let the parent process know the initialization was successful
|
||||||
* -- jilles */
|
* -- jilles */
|
||||||
if (!server_state_foreground)
|
if (!server_state_foreground)
|
||||||
write(0, ".", 1);
|
{
|
||||||
|
/* GCC complains on Linux if we don't check the value of write pedantically.
|
||||||
|
* Technically you're supposed to check the value, yes, but it probably can't fail.
|
||||||
|
* No, casting to void is of no use to shut the warning up. You HAVE to use the value.
|
||||||
|
* --Elizfaox
|
||||||
|
*/
|
||||||
|
if(write(0, ".", 1) < 1)
|
||||||
|
abort();
|
||||||
|
}
|
||||||
if (dup2(1, 0) == -1)
|
if (dup2(1, 0) == -1)
|
||||||
abort();
|
abort();
|
||||||
if (dup2(1, 2) == -1)
|
if (dup2(1, 2) == -1)
|
||||||
abort();
|
abort();
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -191,7 +221,7 @@ print_startup(int pid)
|
||||||
static void
|
static void
|
||||||
init_sys(void)
|
init_sys(void)
|
||||||
{
|
{
|
||||||
#if defined(RLIMIT_NOFILE) && defined(HAVE_SYS_RESOURCE_H)
|
#if !defined(_WIN32) && defined(RLIMIT_NOFILE) && defined(HAVE_SYS_RESOURCE_H)
|
||||||
struct rlimit limit;
|
struct rlimit limit;
|
||||||
|
|
||||||
if(!getrlimit(RLIMIT_NOFILE, &limit))
|
if(!getrlimit(RLIMIT_NOFILE, &limit))
|
||||||
|
@ -212,6 +242,7 @@ init_sys(void)
|
||||||
static int
|
static int
|
||||||
make_daemon(void)
|
make_daemon(void)
|
||||||
{
|
{
|
||||||
|
#ifndef _WIN32
|
||||||
int pid;
|
int pid;
|
||||||
int pip[2];
|
int pip[2];
|
||||||
char c;
|
char c;
|
||||||
|
@ -246,7 +277,7 @@ make_daemon(void)
|
||||||
/* fclose(stdin);
|
/* fclose(stdin);
|
||||||
fclose(stdout);
|
fclose(stdout);
|
||||||
fclose(stderr); */
|
fclose(stderr); */
|
||||||
|
#endif
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -277,13 +308,13 @@ check_rehash(void *unused)
|
||||||
*/
|
*/
|
||||||
if(dorehash)
|
if(dorehash)
|
||||||
{
|
{
|
||||||
rehash(1);
|
rehash(true);
|
||||||
dorehash = false;
|
dorehash = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(dorehashbans)
|
if(dorehashbans)
|
||||||
{
|
{
|
||||||
rehash_bans(1);
|
rehash_bans();
|
||||||
dorehashbans = false;
|
dorehashbans = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -358,6 +389,85 @@ initialize_server_capabs(void)
|
||||||
default_server_capabs &= ~CAP_ZIP;
|
default_server_capabs &= ~CAP_ZIP;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* relocate_paths
|
||||||
|
*
|
||||||
|
* inputs - none
|
||||||
|
* output - none
|
||||||
|
* side effects - items in ircd_paths[] array are relocated
|
||||||
|
*/
|
||||||
|
#ifdef _WIN32
|
||||||
|
static void
|
||||||
|
relocate_paths(void)
|
||||||
|
{
|
||||||
|
char prefix[PATH_MAX], workbuf[PATH_MAX];
|
||||||
|
char *p;
|
||||||
|
|
||||||
|
rb_strlcpy(prefix, rb_path_to_self(), sizeof prefix);
|
||||||
|
|
||||||
|
ircd_paths[IRCD_PATH_IRCD_EXEC] = rb_strdup(prefix);
|
||||||
|
|
||||||
|
/* if we're running from inside the source tree, we probably do not want to relocate any other paths */
|
||||||
|
if (strstr(prefix, ".libs") != NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
|
/* prefix = /home/kaniini/ircd/bin/ircd */
|
||||||
|
p = strrchr(prefix, RB_PATH_SEPARATOR);
|
||||||
|
if (rb_unlikely(p == NULL))
|
||||||
|
return;
|
||||||
|
*p = 0;
|
||||||
|
|
||||||
|
/* prefix = /home/kaniini/ircd/bin */
|
||||||
|
p = strrchr(prefix, RB_PATH_SEPARATOR);
|
||||||
|
if (rb_unlikely(p == NULL))
|
||||||
|
return;
|
||||||
|
*p = 0;
|
||||||
|
|
||||||
|
/* prefix = /home/kaniini/ircd */
|
||||||
|
ircd_paths[IRCD_PATH_PREFIX] = rb_strdup(prefix);
|
||||||
|
|
||||||
|
/* now that we have our prefix, we can relocate the other paths... */
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%cmodules", prefix, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_MODULES] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%cmodules%cautoload", prefix, RB_PATH_SEPARATOR, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_AUTOLOAD_MODULES] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%cetc", prefix, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_ETC] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%clog", prefix, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_LOG] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%chelp%cusers", prefix, RB_PATH_SEPARATOR, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_USERHELP] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%chelp%copers", prefix, RB_PATH_SEPARATOR, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_OPERHELP] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%cetc%circd.conf", prefix, RB_PATH_SEPARATOR, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_IRCD_CONF] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%cetc%circd.motd", prefix, RB_PATH_SEPARATOR, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_IRCD_MOTD] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%cetc%copers.motd", prefix, RB_PATH_SEPARATOR, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_IRCD_OMOTD] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%cetc%cban.db", prefix, RB_PATH_SEPARATOR, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_BANDB] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%cetc%circd.pid", prefix, RB_PATH_SEPARATOR, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_IRCD_PID] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%clogs%circd.log", prefix, RB_PATH_SEPARATOR, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_IRCD_LOG] = rb_strdup(workbuf);
|
||||||
|
|
||||||
|
snprintf(workbuf, sizeof workbuf, "%s%cbin", prefix, RB_PATH_SEPARATOR);
|
||||||
|
ircd_paths[IRCD_PATH_BIN] = rb_strdup(workbuf);
|
||||||
|
ircd_paths[IRCD_PATH_LIBEXEC] = rb_strdup(workbuf);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* write_pidfile
|
* write_pidfile
|
||||||
|
@ -412,7 +522,7 @@ check_pidfile(const char *filename)
|
||||||
if(fgets(buff, 20, fb) != NULL)
|
if(fgets(buff, 20, fb) != NULL)
|
||||||
{
|
{
|
||||||
pidfromfile = atoi(buff);
|
pidfromfile = atoi(buff);
|
||||||
if(!kill(pidfromfile, 0))
|
if(!rb_kill(pidfromfile, 0))
|
||||||
{
|
{
|
||||||
printf("ircd: daemon is already running\n");
|
printf("ircd: daemon is already running\n");
|
||||||
exit(-1);
|
exit(-1);
|
||||||
|
@ -539,19 +649,28 @@ charybdis_main(int argc, char *argv[])
|
||||||
{
|
{
|
||||||
int fd;
|
int fd;
|
||||||
|
|
||||||
|
#ifndef _WIN32
|
||||||
/* Check to see if the user is running us as root, which is a nono */
|
/* Check to see if the user is running us as root, which is a nono */
|
||||||
if(geteuid() == 0)
|
if(geteuid() == 0)
|
||||||
{
|
{
|
||||||
fprintf(stderr, "Don't run ircd as root!!!\n");
|
fprintf(stderr, "Don't run ircd as root!!!\n");
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
relocate_paths();
|
||||||
|
#endif
|
||||||
|
|
||||||
|
logFileName = ircd_paths[IRCD_PATH_IRCD_LOG];
|
||||||
|
pidFileName = ircd_paths[IRCD_PATH_IRCD_PID];
|
||||||
|
|
||||||
|
ConfigFileEntry.dpath = ircd_paths[IRCD_PATH_PREFIX];
|
||||||
|
ConfigFileEntry.configfile = ircd_paths[IRCD_PATH_IRCD_CONF]; /* Server configuration file */
|
||||||
|
ConfigFileEntry.connect_timeout = 30; /* Default to 30 */
|
||||||
|
|
||||||
init_sys();
|
init_sys();
|
||||||
|
|
||||||
ConfigFileEntry.dpath = DPATH;
|
|
||||||
ConfigFileEntry.configfile = CPATH; /* Server configuration file */
|
|
||||||
ConfigFileEntry.connect_timeout = 30; /* Default to 30 */
|
|
||||||
|
|
||||||
umask(077); /* better safe than sorry --SRB */
|
umask(077); /* better safe than sorry --SRB */
|
||||||
|
|
||||||
myargv = argv;
|
myargv = argv;
|
||||||
|
@ -607,6 +726,7 @@ charybdis_main(int argc, char *argv[])
|
||||||
if (testing_conf)
|
if (testing_conf)
|
||||||
server_state_foreground = true;
|
server_state_foreground = true;
|
||||||
|
|
||||||
|
#ifndef _WIN32
|
||||||
/* Make sure fd 0, 1 and 2 are in use -- jilles */
|
/* Make sure fd 0, 1 and 2 are in use -- jilles */
|
||||||
do
|
do
|
||||||
{
|
{
|
||||||
|
@ -616,6 +736,7 @@ charybdis_main(int argc, char *argv[])
|
||||||
close(fd);
|
close(fd);
|
||||||
else if (fd == -1)
|
else if (fd == -1)
|
||||||
exit(1);
|
exit(1);
|
||||||
|
#endif
|
||||||
|
|
||||||
/* Check if there is pidfile and daemon already running */
|
/* Check if there is pidfile and daemon already running */
|
||||||
if(!testing_conf)
|
if(!testing_conf)
|
||||||
|
@ -663,7 +784,7 @@ charybdis_main(int argc, char *argv[])
|
||||||
|
|
||||||
init_auth(); /* Initialise the auth code */
|
init_auth(); /* Initialise the auth code */
|
||||||
init_authd(); /* Start up authd. */
|
init_authd(); /* Start up authd. */
|
||||||
init_nameserver_cache(); /* Get our nameserver cache for STATS a/A */
|
init_dns(); /* Start up DNS query system */
|
||||||
|
|
||||||
privilegeset_set_new("default", "", 0);
|
privilegeset_set_new("default", "", 0);
|
||||||
|
|
||||||
|
@ -679,7 +800,7 @@ charybdis_main(int argc, char *argv[])
|
||||||
init_bandb();
|
init_bandb();
|
||||||
init_ssld();
|
init_ssld();
|
||||||
|
|
||||||
rehash_bans(0);
|
rehash_bans();
|
||||||
|
|
||||||
initialize_server_capabs(); /* Set up default_server_capabs */
|
initialize_server_capabs(); /* Set up default_server_capabs */
|
||||||
initialize_global_set_options();
|
initialize_global_set_options();
|
||||||
|
@ -713,10 +834,10 @@ charybdis_main(int argc, char *argv[])
|
||||||
if(!rb_setup_ssl_server(ServerInfo.ssl_cert, ServerInfo.ssl_private_key, ServerInfo.ssl_dh_params, ServerInfo.ssl_cipher_list))
|
if(!rb_setup_ssl_server(ServerInfo.ssl_cert, ServerInfo.ssl_private_key, ServerInfo.ssl_dh_params, ServerInfo.ssl_cipher_list))
|
||||||
{
|
{
|
||||||
ilog(L_MAIN, "WARNING: Unable to setup SSL.");
|
ilog(L_MAIN, "WARNING: Unable to setup SSL.");
|
||||||
ssl_ok = false;
|
ircd_ssl_ok = false;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
ssl_ok = true;
|
ircd_ssl_ok = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (testing_conf)
|
if (testing_conf)
|
||||||
|
|
2022
ircd/ircd_lexer.c
2022
ircd/ircd_lexer.c
File diff suppressed because it is too large
Load diff
|
@ -25,8 +25,6 @@
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
|
|
||||||
#include <netinet/in.h>
|
|
||||||
|
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <limits.h>
|
#include <limits.h>
|
||||||
|
@ -35,8 +33,7 @@
|
||||||
|
|
||||||
#include "stdinc.h"
|
#include "stdinc.h"
|
||||||
#include "ircd_defs.h"
|
#include "ircd_defs.h"
|
||||||
#include "common.h"
|
#include "defaults.h"
|
||||||
#include "config.h"
|
|
||||||
#include "logger.h"
|
#include "logger.h"
|
||||||
#include "s_conf.h"
|
#include "s_conf.h"
|
||||||
#include "newconf.h"
|
#include "newconf.h"
|
||||||
|
@ -55,8 +52,8 @@ void cinclude(void);
|
||||||
void hashcomment(void);
|
void hashcomment(void);
|
||||||
int ieof(void);
|
int ieof(void);
|
||||||
int lineno_stack[MAX_INCLUDE_DEPTH];
|
int lineno_stack[MAX_INCLUDE_DEPTH];
|
||||||
char conffile_stack[MAX_INCLUDE_DEPTH][IRCD_BUFSIZE];
|
char conffile_stack[MAX_INCLUDE_DEPTH][BUFSIZE];
|
||||||
char conffilebuf[IRCD_BUFSIZE+1];
|
char conffilebuf[BUFSIZE+1];
|
||||||
char *current_file = conffilebuf;
|
char *current_file = conffilebuf;
|
||||||
|
|
||||||
FILE *inc_fbfile_in[MAX_INCLUDE_DEPTH];
|
FILE *inc_fbfile_in[MAX_INCLUDE_DEPTH];
|
||||||
|
@ -196,10 +193,10 @@ void cinclude(void)
|
||||||
|
|
||||||
if (tmp_fbfile_in == NULL)
|
if (tmp_fbfile_in == NULL)
|
||||||
{
|
{
|
||||||
/* if its not found in PREFIX, look in ETCPATH */
|
/* if its not found in PREFIX, look in IRCD_PATH_ETC */
|
||||||
char fnamebuf[IRCD_BUFSIZE];
|
char fnamebuf[BUFSIZE];
|
||||||
|
|
||||||
snprintf(fnamebuf, sizeof(fnamebuf), "%s/%s", ETCPATH, c);
|
snprintf(fnamebuf, sizeof(fnamebuf), "%s%c%s", IRCD_PATH_ETC, RB_PATH_SEPARATOR, c);
|
||||||
tmp_fbfile_in = fopen(fnamebuf, "r");
|
tmp_fbfile_in = fopen(fnamebuf, "r");
|
||||||
|
|
||||||
/* wasnt found there either.. error. */
|
/* wasnt found there either.. error. */
|
||||||
|
|
1817
ircd/ircd_parser.c
1817
ircd/ircd_parser.c
File diff suppressed because it is too large
Load diff
|
@ -1,86 +0,0 @@
|
||||||
/* A Bison parser, made by GNU Bison 3.0.4. */
|
|
||||||
|
|
||||||
/* Bison interface for Yacc-like parsers in C
|
|
||||||
|
|
||||||
Copyright (C) 1984, 1989-1990, 2000-2015 Free Software Foundation, Inc.
|
|
||||||
|
|
||||||
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 3 of the License, 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, see <http://www.gnu.org/licenses/>. */
|
|
||||||
|
|
||||||
/* As a special exception, you may create a larger work that contains
|
|
||||||
part or all of the Bison parser skeleton and distribute that work
|
|
||||||
under terms of your choice, so long as that work isn't itself a
|
|
||||||
parser generator using the skeleton or a modified version thereof
|
|
||||||
as a parser skeleton. Alternatively, if you modify or redistribute
|
|
||||||
the parser skeleton itself, you may (at your option) remove this
|
|
||||||
special exception, which will cause the skeleton and the resulting
|
|
||||||
Bison output files to be licensed under the GNU General Public
|
|
||||||
License without this special exception.
|
|
||||||
|
|
||||||
This special exception was added by the Free Software Foundation in
|
|
||||||
version 2.2 of Bison. */
|
|
||||||
|
|
||||||
#ifndef YY_YY_IRCD_PARSER_H_INCLUDED
|
|
||||||
# define YY_YY_IRCD_PARSER_H_INCLUDED
|
|
||||||
/* Debug traces. */
|
|
||||||
#ifndef YYDEBUG
|
|
||||||
# define YYDEBUG 0
|
|
||||||
#endif
|
|
||||||
#if YYDEBUG
|
|
||||||
extern int yydebug;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/* Token type. */
|
|
||||||
#ifndef YYTOKENTYPE
|
|
||||||
# define YYTOKENTYPE
|
|
||||||
enum yytokentype
|
|
||||||
{
|
|
||||||
LOADMODULE = 258,
|
|
||||||
TWODOTS = 259,
|
|
||||||
QSTRING = 260,
|
|
||||||
STRING = 261,
|
|
||||||
NUMBER = 262
|
|
||||||
};
|
|
||||||
#endif
|
|
||||||
/* Tokens. */
|
|
||||||
#define LOADMODULE 258
|
|
||||||
#define TWODOTS 259
|
|
||||||
#define QSTRING 260
|
|
||||||
#define STRING 261
|
|
||||||
#define NUMBER 262
|
|
||||||
|
|
||||||
/* Value type. */
|
|
||||||
#if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED
|
|
||||||
|
|
||||||
union YYSTYPE
|
|
||||||
{
|
|
||||||
#line 164 "ircd_parser.y" /* yacc.c:1909 */
|
|
||||||
|
|
||||||
int number;
|
|
||||||
char string[IRCD_BUFSIZE + 1];
|
|
||||||
conf_parm_t * conf_parm;
|
|
||||||
|
|
||||||
#line 74 "ircd_parser.h" /* yacc.c:1909 */
|
|
||||||
};
|
|
||||||
|
|
||||||
typedef union YYSTYPE YYSTYPE;
|
|
||||||
# define YYSTYPE_IS_TRIVIAL 1
|
|
||||||
# define YYSTYPE_IS_DECLARED 1
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
extern YYSTYPE yylval;
|
|
||||||
|
|
||||||
int yyparse (void);
|
|
||||||
|
|
||||||
#endif /* !YY_YY_IRCD_PARSER_H_INCLUDED */
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue