Initial revision

This commit is contained in:
fishwaldo 2002-08-13 14:34:25 +00:00
commit f95e6db9bf
474 changed files with 147790 additions and 0 deletions

7
.cvsignore Normal file
View file

@ -0,0 +1,7 @@
config.log
config.cache
config.status
Makefile
lint.out
rsa_respond.tar.gz
.depend

474
.gitattributes vendored Normal file
View file

@ -0,0 +1,474 @@
* text=auto !eol
/.cvsignore -text
/.indent.pro -text
/BUGS -text
/ChangeLog -text
/Hybrid-team -text
/INSTALL -text
/LICENSE -text
/Makefile.in -text
/README.FIRST -text
/README.PLATFORMS -text
/README.VMS -text
/RELNOTES -text
/TODO -text
adns/.cvsignore -text
adns/COPYING -text
adns/GPL-vs-LGPL -text
adns/Makefile.in -text
adns/README -text
adns/README.ircd -text
adns/adns.h -text
adns/check.c -text
adns/descrip.mms -text
adns/dlist.h -text
adns/event.c -text
adns/general.c -text
adns/internal.h -text
adns/parse.c -text
adns/query.c -text
adns/reply.c -text
adns/setup.c -text
adns/transmit.c -text
adns/tvarith.h -text
adns/types.c -text
autoconf/acconfig.h -text
autoconf/configure.in -text
autoconf/install-sh -text
/clean.com -text
/configure -text
contrib/.cvsignore -text
contrib/Makefile.in -text
contrib/README -text
contrib/README.LMH -text
contrib/README.disable_identd -text
contrib/disable_identd.diff -text
contrib/example_module.c -text
contrib/lmh.diff -text
contrib/m_clearchan.c -text
contrib/m_flags.c -text
contrib/m_force.c -text
contrib/m_jupe.c -text
contrib/m_ltrace.c -text
contrib/m_map.c -text
contrib/m_mkpasswd.c -text
contrib/m_ojoin.c -text
contrib/m_opme.c -text
contrib/m_tburst.c -text
contrib/spy_admin_notice.c -text
contrib/spy_info_notice.c -text
contrib/spy_links_notice.c -text
contrib/spy_motd_notice.c -text
contrib/spy_stats_notice.c -text
contrib/spy_stats_p_notice.c -text
contrib/spy_trace_notice.c -text
contrib/spy_whois_notice.c -text
doc/.cvsignore -text
doc/CIDR.txt -text
doc/LazyLinks.txt -text
doc/Makefile.in -text
doc/Tao-of-IRC.940110 -text
doc/challenge.txt -text
doc/convertconf-example.conf -text
doc/dline.conf -text
doc/example.conf -text
doc/example.efnet.conf -text
doc/guidelines.txt -text
doc/index.txt -text
doc/ircd.8 -text
doc/ircd.motd -text
doc/kline.conf -text
doc/kline.txt -text
doc/messages.txt -text
doc/modeg.txt -text
doc/modes.txt -text
doc/old/Authors -text
doc/old/Etiquette -text
doc/old/README -text
doc/old/US-Admin/Networking -text
doc/old/US-Admin/Operators -text
doc/old/US-Admin/README -text
doc/old/example.conf.trillian -text
doc/old/example_old.conf -text
doc/old/ircd.8 -text
doc/old/simple.conf -text
doc/operguide.txt -text
doc/opermyth.txt -text
doc/resv.txt -text
doc/server-version-info -text
doc/serverhide.txt -text
doc/simple.conf -text
doc/technical/Persistent_Clients.txt -text
doc/technical/README.TSora -text
doc/technical/README.openssl -text
doc/technical/cryptlink.txt -text
doc/technical/debug_api.txt -text
doc/technical/event.txt -text
doc/technical/fd-management.txt -text
doc/technical/file-management.txt -text
doc/technical/hostmask.txt -text
doc/technical/iauth.txt -text
doc/technical/index.txt -text
doc/technical/linebuf.txt -text
doc/technical/message-customisation.txt -text
doc/technical/network.txt -text
doc/technical/rfc1459.txt -text
doc/technical/send.txt -text
doc/technical/ts5.txt -text
doc/technical/whats-new-code.txt -text
doc/vchans.txt -text
doc/whats-new.txt -text
help/.cvsignore -text
help/Makefile.in -text
help/opers/accept -text
help/opers/admin -text
help/opers/away -text
help/opers/capab -text
help/opers/cburst -text
help/opers/challenge -text
help/opers/cjoin -text
help/opers/client -text
help/opers/close -text
help/opers/cmode -text
help/opers/connect -text
help/opers/credits -text
help/opers/cryptlink -text
help/opers/die -text
help/opers/dline -text
help/opers/dmem -text
help/opers/drop -text
help/opers/eob -text
help/opers/error -text
help/opers/gline -text
help/opers/help -text
help/opers/index -text
help/opers/info -text
help/opers/invite -text
help/opers/ison -text
help/opers/join -text
help/opers/kick -text
help/opers/kill -text
help/opers/kline -text
help/opers/knock -text
help/opers/knockll -text
help/opers/links -text
help/opers/list -text
help/opers/lljoin -text
help/opers/llnick -text
help/opers/locops -text
help/opers/lusers -text
help/opers/modlist -text
help/opers/modload -text
help/opers/modrestart -text
help/opers/modunload -text
help/opers/motd -text
help/opers/names -text
help/opers/nburst -text
help/opers/nick -text
help/opers/notice -text
help/opers/oper -text
help/opers/operwall -text
help/opers/part -text
help/opers/pass -text
help/opers/ping -text
help/opers/pong -text
help/opers/post -text
help/opers/privmsg -text
help/opers/quit -text
help/opers/rehash -text
help/opers/restart -text
help/opers/resv -text
help/opers/server -text
help/opers/set -text
help/opers/sjoin -text
help/opers/squit -text
help/opers/stats -text
help/opers/svinfo -text
help/opers/testline -text
help/opers/time -text
help/opers/topic -text
help/opers/trace -text
help/opers/uhelp -text
help/opers/umode -text
help/opers/undline -text
help/opers/ungline -text
help/opers/unkline -text
help/opers/unresv -text
help/opers/user -text
help/opers/userhost -text
help/opers/users -text
help/opers/version -text
help/opers/wallops -text
help/opers/who -text
help/opers/whois -text
help/opers/whowas -text
help/users/index -text
help/users/info -text
help/users/notice -text
help/users/privmsg -text
help/users/stats -text
help/users/umode -text
iauth/.cvsignore -text
iauth/Makefile.in -text
iauth/include/auth.h -text
iauth/include/class.h -text
iauth/include/commands.h -text
iauth/include/conf.h -text
iauth/include/iauth.h -text
iauth/include/log.h -text
iauth/include/match.h -text
iauth/include/misc.h -text
iauth/include/mtree.h -text
iauth/include/res.h -text
iauth/include/setup.h -text
iauth/include/sock.h -text
iauth/source/.cvsignore -text
iauth/source/.depend -text
iauth/source/Makefile.in -text
iauth/source/auth.c -text
iauth/source/class.c -text
iauth/source/commands.c -text
iauth/source/conf.c -text
iauth/source/iauth.c -text
iauth/source/log.c -text
iauth/source/match.c -text
iauth/source/misc.c -text
iauth/source/mtree.c -text
iauth/source/res.c -text
iauth/source/sock.c -text
include/.cvsignore -text
include/Makefile.in -text
include/balloc.h -text
include/channel.h -text
include/channel_mode.h -text
include/class.h -text
include/client.h -text
include/common.h -text
include/config.h -text
include/config.h.dist -text
include/defaults.h -text
include/event.h -text
include/fdlist.h -text
include/fileio.h -text
include/handlers.h -text
include/hash.h -text
include/hook.h -text
include/hostmask.h -text
include/irc_string.h -text
include/ircd.h -text
include/ircd_defs.h -text
include/ircd_getopt.h -text
include/ircd_handler.h -text
include/ircd_signal.h -text
include/ircdauth.h -text
include/linebuf.h -text
include/list.h -text
include/listener.h -text
include/m_info.h -text
include/m_kline.h -text
include/md5.h -text
include/memory.h -text
include/modules.h -text
include/motd.h -text
include/msg.h -text
include/numeric.h -text
include/packet.h -text
include/parse.h -text
include/patchlevel.h -text
include/res.h -text
include/restart.h -text
include/resv.h -text
include/rsa.h -text
include/s_auth.h -text
include/s_bsd.h -text
include/s_conf.h -text
include/s_debug.h -text
include/s_gline.h -text
include/s_log.h -text
include/s_misc.h -text
include/s_serv.h -text
include/s_stats.h -text
include/s_user.h -text
include/s_zip.h -text
include/scache.h -text
include/send.h -text
include/serno.h -text
include/setup.h.in -text
include/setup.h_vms -text
include/sprintf_irc.h -text
include/stdinc.h -text
include/supported.h -text
include/tools.h -text
include/vchannel.h -text
include/whowas.h -text
/make.com -text
messages/.cvsignore -text
messages/Makefile.in -text
messages/ayb.po -text
messages/build_one -text
messages/create_po -text
messages/custom.po -text
messages/translations/.cvsignore -text
messages/translations/Makefile.in -text
messages/translations/README -text
messages/translations/ircd-croatian.po -text
messages/translations/ircd-danish.po -text
messages/translations/ircd-dutch.po -text
messages/translations/ircd-german.po -text
messages/translations/ircd-norwegian.po -text
messages/translations/ircd-spanish.po -text
messages/translations/ircd-swedish.po -text
modules/.cvsignore -text
modules/.depend -text
modules/Makefile.in -text
modules/descrip.mms -text
modules/m_accept.c -text
modules/m_admin.c -text
modules/m_away.c -text
modules/m_capab.c -text
modules/m_cburst.c -text
modules/m_challenge.c -text
modules/m_cjoin.c -text
modules/m_close.c -text
modules/m_connect.c -text
modules/m_cryptlink.c -text
modules/m_dmem.c -text
modules/m_drop.c -text
modules/m_eob.c -text
modules/m_gline.c -text
modules/m_help.c -text
modules/m_info.c -text
modules/m_invite.c -text
modules/m_ison.c -text
modules/m_join.c -text
modules/m_kline.c -text
modules/m_knock.c -text
modules/m_links.c -text
modules/m_list.c -text
modules/m_lljoin.c -text
modules/m_llnick.c -text
modules/m_locops.c -text
modules/m_lusers.c -text
modules/m_motd.c -text
modules/m_names.c -text
modules/m_nburst.c -text
modules/m_oper.c -text
modules/m_operwall.c -text
modules/m_pass.c -text
modules/m_ping.c -text
modules/m_pong.c -text
modules/m_post.c -text
modules/m_rehash.c -text
modules/m_restart.c -text
modules/m_resv.c -text
modules/m_set.c -text
modules/m_stats.c -text
modules/m_svinfo.c -text
modules/m_testline.c -text
modules/m_time.c -text
modules/m_topic.c -text
modules/m_trace.c -text
modules/m_unkline.c -text
modules/m_user.c -text
modules/m_userhost.c -text
modules/m_users.c -text
modules/m_version.c -text
modules/m_wallops.c -text
modules/m_who.c -text
modules/m_whois.c -text
modules/m_whowas.c -text
servlink/.cvsignore -text
servlink/Makefile.in -text
servlink/README -text
servlink/TODO -text
servlink/control.c -text
servlink/control.h -text
servlink/descrip.mms -text
servlink/io.c -text
servlink/io.h -text
servlink/servlink.c -text
servlink/servlink.h -text
servlink/setup.h.in -text
src/.cvsignore -text
src/.depend -text
src/Makefile.in -text
src/adns.c -text
src/balloc.c -text
src/channel.c -text
src/channel_mode.c -text
src/class.c -text
src/client.c -text
src/crypt.c -text
src/descrip.mms -text
src/dynlink.c -text
src/event.c -text
src/fdlist.c -text
src/fileio.c -text
src/getopt.c -text
src/hash.c -text
src/hook.c -text
src/hostmask.c -text
src/irc_string.c -text
src/ircd.c -text
src/ircd_lexer.l -text
src/ircd_parser.y -text
src/ircd_signal.c -text
src/ircdauth.c -text
src/kdparse.c -text
src/linebuf.c -text
src/list.c -text
src/listener.c -text
src/m_error.c -text
src/match.c -text
src/md5.c -text
src/memory.c -text
src/messages.tab -text
src/modules.c -text
src/motd.c -text
src/numeric.c -text
src/packet.c -text
src/parse.c -text
src/restart.c -text
src/resv.c -text
src/rsa.c -text
src/s_auth.c -text
src/s_bsd.c -text
src/s_bsd_devpoll.c -text
src/s_bsd_kqueue.c -text
src/s_bsd_poll.c -text
src/s_bsd_select.c -text
src/s_bsd_sigio.c -text
src/s_conf.c -text
src/s_debug.c -text
src/s_gline.c -text
src/s_log.c -text
src/s_misc.c -text
src/s_serv.c -text
src/s_stats.c -text
src/s_user.c -text
src/scache.c -text
src/send.c -text
src/snprintf.c -text
src/sprintf_irc.c -text
src/tools.c -text
src/vchannel.c -text
src/version.c.SH -text
src/version.com -text
src/whowas.c -text
tools/.cvsignore -text
tools/Makefile.in -text
tools/README -text
tools/README.mkpasswd -text
tools/convertconf.c -text
tools/convertilines.c -text
tools/convertklines.c -text
tools/descrip.mms -text
tools/encspeed.c -text
tools/mkkeypair -text
tools/mkpasswd.c -text
tools/rsa_respond/.cvsignore -text
tools/rsa_respond/Makefile -text
tools/rsa_respond/README -text
tools/rsa_respond/respond.c -text
tools/untabify -text
tools/viconf.c -text

17
.indent.pro vendored Normal file
View file

@ -0,0 +1,17 @@
/* $Id: .indent.pro,v 1.1 2002/08/13 14:34:26 fishwaldo Exp $ */
/* copy this file to the source dir then run indent file.c */
--gnu-style
/* Disable tabs... */
-nut
/* This is the indent before the brace not inside the block. */
--brace-indent0
/* Indent case: by 2 and braces inside case by 0(then by 0)... */
--case-brace-indentation0
--case-indentation2
/* Put while() on the brace from do... */
--cuddle-do-while
/* Disable an annoying format... */
--no-space-after-function-call-names
/* Disable an annoying format... */
--no-space-after-casts

63
BUGS Normal file
View file

@ -0,0 +1,63 @@
Known Bugs worthy of a mention:
--------------------------------------------------------------------------------
1. Issues with server hostmasking.
- If for example the new servername is blah.blah.blah.nl, the following
servernames will be checked, in this order: *.blah.blah.nl, *.blah.nl,
*.nl, one of which will match the host-masked server they are
connecting behind. This will be accepted by the host-masked server it
is connected behind, but when it reaches the server the host-masked
server is connected to, the find_server will match, so the host-masked
server will be dropped.
--> This corrected?
2. /MODUNLOAD causes cores:
- If a module is modified before being unloaded, /MODUNLOAD (and
therefore /MODRELOAD) may cause a core.
This problem is caused by the behaviour of the OS, which treats
shared libraries differently to executables (modifying the ircd
binary whilst it is running would also cause a core, but is denied
by the OS). There is no way to fix this at the application level,
and fixing the OS to do the right thing is also difficult.
A workaround to avoid coring is possible however. To install new
modules, first remove or rename the old module, then copy/move the
new file into place. /MODUNLOAD will then work successfully.
Alternatively, running ./configure with the --disable-shared-modules
argument will link all the commands statically, losing the advantages
of upgrading at runtime, but reducing the chances of accidentally
coring your server.
3. Problem with msgfmt command building custom msgs using gettext
- Please ensure you are using GNU gettext version 0.10.35.
Other versions are untested, and some are known to be
incompatible.
4. Problems with quote set msglocale not working on linux.
This seems to be a linux problem, /quote set msglocale will sometimes
get "undone" when a new client connects. The server will also sometimes
not correctly set the locale from ircd.conf on startup.
The solution is if a locale is needed, to have the message_locale="x"
in ircd.conf, and then rehash to make it take effect. A rehash after
startup will also need to be performed to set the locale.
5. When updating a message file, in certain unknown situations it will core
if the file in use is being accessed. To prevent this from happening,
use '/quote SET MSGLOCALE standard' BEFORE issuing make install. When
the file is installed, you can SET MSGLOCALE back to the language that
was just updated.
6. IAuthd is broken beyond belief. It does not work at this time. If this
bothers you, fix it for us.
BUG REPORTS: If you run this code and encounter problems, you must report
the bug in by E-MAIL to ircd-hybrid@the-project.org.
Please include a gdb backtrace and a copy of your config.h and ircd.conf
with any report (with passwords and other sensitive information masked).
--------------------------------------------------------------------------------
$Id: BUGS,v 1.1 2002/08/13 14:34:26 fishwaldo Exp $

29956
ChangeLog Normal file

File diff suppressed because it is too large Load diff

58
Hybrid-team Normal file
View file

@ -0,0 +1,58 @@
$Id: Hybrid-team,v 1.1 2002/08/13 14:34:54 fishwaldo Exp $
The hybrid team is a group of ircd coders who were frustrated
with the instability and all-out "dirtiness" of the EFnet ircd's
available. "hybrid" is the name for the collective efforts of a group
of people, all of us.
Anyone is welcome to contribute to this effort. You are encouraged
to participate in the Hybrid mailing list. To subscribe to the
Hybrid List, send email to listmanager@the-project.org with the
subject "subscribe hybrid".
The core team as, of this major release:
A1kmm, Andrew Miller <a1kmm@mware.virtualave.net>
adrian, Adrian Chadd <adrian@creative.net.au>
AndroSyn, Aaron Sethman <androsyn@ratbox.org>
billy-jon, Bill Jonus <bill@mu.org>
cosine, Patrick Alken <wnder@uwns.underworld.net>
David-T, David Taylor <davidt@yadt.co.uk>
Dianora, Diane Bruce <db@db.net>
einride, Erik S. Johansen, <einride@einride.org>
fl, Lee Hardy <lee@leeh.co.uk>
Hwy101, W. Campbell <wcampbel@botbay.net>
larne, Edward Brocklesby <ejb@sdf.lonestar.org>
isomer, Perry Lorier <perry@coders.net>
jmallett, Juli Mallett <jmallett@FreeBSD.org>
k9, Jeremy Chadwick <yoshi@parodius.com>
Rodder, Jon Lusky <lusky@blown.net>
toot, Toby Verrall <to7@antipope.fsnet.co.uk>
Wohali, Joan Touzet <joant@ieee.org>
xyst, Greg Prosser <gnp@arrogant.org>
The following people have contributed blood, sweat, and/or code to
this release of hybrid, in nick alphabetical order:
adx, Piotr Nizynski <adx@crashnet.pl>
bysin, Ben Kittridge <bkittridge@cfl.rr.com>
desrt, Ryan Lortie <desertangel@mindless.com>
Habeeb, David Supuran <habeeb@cfl.rr.com>
jv, Jakub Vlasek <jv@pilsedu.cz>
kre, Dinko Korunic <kreator@fly.srk.fer.hr>
madmax, Paul Lomax <madmax@efnet.org>
Neph|l|m, Adel Mezibra <adel@cybercable.fr>
Riedel, Dennis Vink, <vink@vuurwerk.nl>
Robert Alan Byer <byer@mail.ourservers.net>
scuzzy, David Todd <scuzzy@aniverse.net>
spookey, David Colburn <spookey@spookey.org>
vulture, Sean Stanek <vulture@cs.iastate.edu>
vx0, Mark Miller <mark@vx0.net>
zb^3, Alfred Perlstein <alfred@freebsd.org>
Others are welcome. Always. And if we left anyone off the above list,
be sure to let us know that too. Many others have contributed to
previous versions of this ircd and it's ancestors, too many to list
here.
Send bug fixes/complaints/rotten tomatoes to ircd-hybrid@the-project.org.

273
INSTALL Normal file
View file

@ -0,0 +1,273 @@
Hybrid INSTALL Document
$Id: INSTALL,v 1.1 2002/08/13 14:34:55 fishwaldo Exp $
Copyright (c) 2001 by ircd-hybrid team
----------------------------------------------------------------------
+------------------------------------------------------------------------+
| Note for those who dont bother reading docs |
| |
| Reading INSTALL is now a must, as the old DPATH is now specified when |
| configure is run. |
| |
| - You now need to ./configure --prefix="/path/to/install/it" |
| |
| Important: The old config format WILL NOT WORK. Please see point 6! |
| |
| The old kline format WILL NOT WORK. Please see point 7! |
+------------------------------------------------------------------------+
***** EFNET NOTE *****
You should run ./configure with the option '--enable-efnet' to tweak
some options to be EFNet based. You must also use the example.efnet.conf
instead of example.conf. Please see note 7 for information about
converting old configs to new.
**********************
----------------------------------------------------------------------
HOW TO BUILD
As of hybrid-4, the distribution uses GNU autoconf instead of the old
Config script. The Makefile has also been updated to include CFLAGS
defines for popular modern OSes.
1.
Read the ChangeLog file to find out about the exciting new features in
this version. Other good reads are doc/whats-new.txt, BUGS,
doc/example.conf, and README.FIRST.
An example.conf for EFnet is in doc/ with the values "approved" on 12
December 2001.
2.
Run the configure script. It will create include/setup.h and the
Makefiles to match your system. In hybrid-7, the paths are now handled
with the --prefix option to configure, not in config.h.
/usr/local/ircd is the default if no prefix is specified.
./configure --prefix="/usr/local/ircd"
Note: There are some special optional parameters to the configure
script that some admins may wish to use.
*
--enable-kqueue - Use the superior kqueue(2) system call as
opposed to the default poll(2). This is currently only available
on FreeBSD 4.1 or higher.
*
--enable-devpoll - Enable the superior /dev/poll support on
Solaris. Linux /dev/poll is broken and will not work with this
option.
*
--enable-rtsigio - Enable the superior Linux RealTime Signal I/O
system. This is currently only available on 2.4 Linux kernel
versions or later.
*
--enable-openssl - Enable the openssl dependent crypto functions.
This will allow CHALLENGE to work and encrypted links. On systems
where the configure script can automatically detect OpenSSL, this
option is not necessary. If configure cannot find OpenSSL, you
must specify a path with this option
(--enable-openssl=/path/to/openssl)
*
--enable-ipv6 - Enable IPv6 support.
*
--disable-shared-modules - Disable module support. This option is
more secure, but reduces a lot of the flexibility in Hybrid 7.
This may need to be used on some systems without a working dl
library.
*
--disable-assert - Disable some of the debugging code. This
should be used on all production servers for maximum speed and to
prevent cores from things that shouldn't normally happen.
*
--enable-small-net - Tunes the server for smaller networks by
reducing the startup memory footprint. This should really only be
used for *small* networks, as this tends to be a performance hit
on larger networks.
*
--with-nicklen - Sets the maximum NICK length. Note that this
must be consistant across your entire network.
*
--with-maxclients - Sets the maximum number of clients support by
the server. Note that this also twiddles the HARD_FDLIMIT_ define
so it is no longer necessary to modify include/config.h for this.
If HARD_FDLIMIT_ ends up being larger that FD_SETSIZE when using
select() for your I/O loop, s_bsd_select.c will refuse to compile
(and tell you to use poll instead). Take this error's advice and
use --enable-poll or something a bit more efficient. You'll be
happier at the end of the day for it.
3.
Look over the "include/config.h" file. This allows you to change the
few remaining hard coded options of how the ircd will operate. Most
admins will only have to change a few settings. USE_SYSLOG is the only
one that most admins will need to edit.
Note: Note that you must have permission by the sysadmin to send
messages to the system log files.
All other settings in config.h are not necessary to edit.
4.
make should build ircd.
5.
make install will install the server, modules(1), and tools in the
path defined in config.h and the prefix specified when configure was
run.
(1) Unless the server was compiled without module support.
6.
If you wish to enable the user log, oper log, and failed oper log,
issue these commands at the shell prompt (in the prefix directory)
$ touch logs/userlog
$ touch logs/operlog
$ touch logs/foperlog
Note: If you use different names in ircd.conf, you must 'touch' the
specific names.
7.
If you are upgrading from Hybrid 5 or Hybrid 6, the config file has
changed drastically...
There is a utility to convert your old config file to the new format.
In prefix/bin there is something called "convertconf". Its usage is:
./convertconf (old config file to convert) (converted file name)
Convertconf will NOT convert I: lines. You must use "convertilines"
for this which contains a much superior method of conversion and
will group I: together under one auth {};.
Once this is done, move your new config to prefix/etc/ircd.conf and
EDIT IT! There are still things that need changing in the config,
including the fact that classes MUST be above auth/connect blocks!
8.
If you are upgrading from Hybrid 5 or Hybrid 6, the kline file has
also changed...
There is a utility to convert the old kline configuration file to the
new format. In prefix/bin there is a program called "convertklines".
Its usage is: ./convertklines (old kline.conf filename) (new
kline.conf filename) (dline.conf filename).
Once this is done, move the new files into the prefix/etc/ directory
under their proper names. By default, the kline file is named
kline.conf and the dline file is named dline.conf.
----------------------------------------------------------------------
HOW TO GET HELP
Send Check or Money Order to... just kidding! You're on your own for
support. Try asking other ircd-hybrid admins on EFnet if you can't fix it
yourself. If you do fix anything, however, please send context or unified
diffs to ircd-hybrid@the-project.org so the fixes can be incorporated into
the next release of ircd-hybrid. If hybrid crashes on you, PLEASE contact
ircd-hybrid@the-project.org ASAP with a backtrace of the core. The Hybrid
team can't fix bugs if no one tells us about them!
There is now a mailing list for general discussion of Hybrid. To subscribe,
send an emal to listmanager@the-project.org with a single line in the body
containing "subscribe hybrid".
----------------------------------------------------------------------
NOTES
The best way to get a backtrace of the core is to follow this sequence of
instructions:
1.
Change to the directory containing the core file
2.
Run gdb on the binary and the core file. With an unmodified Hybrid-7
installation, an example command line is below (in the /usr/local/ircd
directory)
$ gdb bin/ircd ircd.core
3.
At the "(gdb)" prompt, enter the command "bt"
4.
Save the output of the backtrace command and send it to
ircd-hybrid@the-project.org.
5.
Be sure to save the ircd binary, the modules, and the core file in a
safe place in case the developers need to look deeper than a backtrace
provides.
----------------------------------------------------------------------
OPENSSL NOTES
Older FreeBSD machines sometimes have the obsolete ports version of
OpenSSL libcrypto in /usr/local/lib. When configure is used with
--enable-openssl, and libintl is detected in /usr/local/lib, the
/usr/local/lib directory will be searched BEFORE the system /usr/lib for
libraries by the linker. The linker may try to link to the old
/usr/local/lib libcrypto instead of the system /usr/lib libcrypto. Some
older versions may cause error messages similar to the following:
gcc -g -O2 -DIRCD_PREFIX=\"/home/wcampbel/ircd\" -Wl,-export-dynamic
-L/usr/local/lib -o ircd blalloc.o channel.o vchannel.o class.o client.o
dline_conf.o event.o fdlist.o fileio.o hash.o irc_string.o ircd.o ircdauth.o
ircd_signal.o linebuf.o list.o listener.o m_error.o match.o memdebug.o
modules.o motd.o mtrie_conf.o oldparse.o numeric.o packet.o parse.o res.o rsa.o
restart.o s_auth.o s_bsd.o s_bsd_kqueue.o s_conf.o s_debug.o s_gline.o s_log.o
s_misc.o s_serv.o s_stats.o s_user.o scache.o send.o sprintf_irc.o tools.o
whowas.o lex.yy.o y.tab.o version.o -lintl -ldescrypt -lcrypto -lfl
rsa.o: In function `get_randomness':
/home/wcampbel/dev/ircd-hybrid-7/src/rsa.c(.text+0x60): undefined reference to
`RAND_pseudo_bytes'
/usr/local/lib/libcrypto.so: undefined reference to `ERR_load_RSAREF_strings'
/usr/local/lib/libcrypto.so: undefined reference to `RSA_PKCS1_RSAref'
*** Error code 1
If this is the case, you may need to rerun configure without the
--enable-openssl option, manually edit src/Makefile and modules/Makefile
to put -L/usr/lib before the -L/usr/local/lib in LDFLAGS, or remove the
old OpenSSL from /usr/local, and recompile all applications that use
libcrypto to use the system one.

341
LICENSE Normal file
View file

@ -0,0 +1,341 @@
# $Id: LICENSE,v 1.1 2002/08/13 14:34:56 fishwaldo Exp $
GNU GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1989, 1991 Free Software Foundation, Inc.
59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. This
General Public License applies to most of the Free Software
Foundation's software and to any other program whose authors commit to
using it. (Some other Free Software Foundation software is covered by
the GNU Library General Public License instead.) You can apply it to
your programs, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must show them these terms so they know their
rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that redistributors of a free
program will individually obtain patent licenses, in effect making the
program proprietary. To prevent this, we have made it clear that any
patent must be licensed for everyone's free use or not licensed at all.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License applies to any program or other work which contains
a notice placed by the copyright holder saying it may be distributed
under the terms of this General Public License. The "Program", below,
refers to any such program or work, and a "work based on the Program"
means either the Program or any derivative work under copyright law:
that is to say, a work containing the Program or a portion of it,
either verbatim or with modifications and/or translated into another
language. (Hereinafter, translation is included without limitation in
the term "modification".) Each licensee is addressed as "you".
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running the Program is not restricted, and the output from the Program
is covered only if its contents constitute a work based on the
Program (independent of having been made by running the Program).
Whether that is true depends on what the Program does.
1. You may copy and distribute verbatim copies of the Program's
source code as you receive it, in any medium, provided that you
conspicuously and appropriately publish on each copy an appropriate
copyright notice and disclaimer of warranty; keep intact all the
notices that refer to this License and to the absence of any warranty;
and give any other recipients of the Program a copy of this License
along with the Program.
You may charge a fee for the physical act of transferring a copy, and
you may at your option offer warranty protection in exchange for a fee.
2. You may modify your copy or copies of the Program or any portion
of it, thus forming a work based on the Program, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) You must cause the modified files to carry prominent notices
stating that you changed the files and the date of any change.
b) You must cause any work that you distribute or publish, that in
whole or in part contains or is derived from the Program or any
part thereof, to be licensed as a whole at no charge to all third
parties under the terms of this License.
c) If the modified program normally reads commands interactively
when run, you must cause it, when started running for such
interactive use in the most ordinary way, to print or display an
announcement including an appropriate copyright notice and a
notice that there is no warranty (or else, saying that you provide
a warranty) and that users may redistribute the program under
these conditions, and telling the user how to view a copy of this
License. (Exception: if the Program itself is interactive but
does not normally print such an announcement, your work based on
the Program is not required to print an announcement.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Program,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Program, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Program.
In addition, mere aggregation of another work not based on the Program
with the Program (or with a work based on the Program) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may copy and distribute the Program (or a work based on it,
under Section 2) in object code or executable form under the terms of
Sections 1 and 2 above provided that you also do one of the following:
a) Accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of Sections
1 and 2 above on a medium customarily used for software interchange; or,
b) Accompany it with a written offer, valid for at least three
years, to give any third party, for a charge no more than your
cost of physically performing source distribution, a complete
machine-readable copy of the corresponding source code, to be
distributed under the terms of Sections 1 and 2 above on a medium
customarily used for software interchange; or,
c) Accompany it with the information you received as to the offer
to distribute corresponding source code. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form with such
an offer, in accord with Subsection b above.)
The source code for a work means the preferred form of the work for
making modifications to it. For an executable work, complete source
code means all the source code for all modules it contains, plus any
associated interface definition files, plus the scripts used to
control compilation and installation of the executable. However, as a
special exception, the source code distributed need not include
anything that is normally distributed (in either source or binary
form) with the major components (compiler, kernel, and so on) of the
operating system on which the executable runs, unless that component
itself accompanies the executable.
If distribution of executable or object code is made by offering
access to copy from a designated place, then offering equivalent
access to copy the source code from the same place counts as
distribution of the source code, even though third parties are not
compelled to copy the source along with the object code.
4. You may not copy, modify, sublicense, or distribute the Program
except as expressly provided under this License. Any attempt
otherwise to copy, modify, sublicense or distribute the Program is
void, and will automatically terminate your rights under this License.
However, parties who have received copies, or rights, from you under
this License will not have their licenses terminated so long as such
parties remain in full compliance.
5. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Program or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Program (or any work based on the
Program), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Program or works based on it.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the
original licensor to copy, distribute or modify the Program subject to
these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
7. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Program at all. For example, if a patent
license would not permit royalty-free redistribution of the Program by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Program.
If any portion of this section is held invalid or unenforceable under
any particular circumstance, the balance of the section is intended to
apply and the section as a whole is intended to apply in other
circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system, which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
8. If the distribution and/or use of the Program is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Program under this License
may add an explicit geographical distribution limitation excluding
those countries, so that distribution is permitted only in or among
countries not thus excluded. In such case, this License incorporates
the limitation as if written in the body of this License.
9. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of this License which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
this License, you may choose any version ever published by the Free Software
Foundation.
10. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to the public, the best way to achieve this is to make it
free software which everyone can redistribute and change under these terms.
To do so, attach the following notices to the program. It is safest
to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least
the "copyright" line and a pointer to where the full notice is found.
<one line to give the program's name and a brief idea of what it does.>
Copyright (C) 19yy <name of author>
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
Also add information on how to contact you by electronic and paper mail.
If the program is interactive, make it output a short notice like this
when it starts in an interactive mode:
Gnomovision version 69, Copyright (C) 19yy name of author
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the appropriate
parts of the General Public License. Of course, the commands you use may
be called something other than `show w' and `show c'; they could even be
mouse-clicks or menu items--whatever suits your program.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the program, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
`Gnomovision' (which makes passes at compilers) written by James Hacker.
<signature of Ty Coon>, 1 April 1989
Ty Coon, President of Vice
This General Public License does not permit incorporating your program into
proprietary programs. If your program is a subroutine library, you may
consider it more useful to permit linking proprietary applications with the
library. If this is what you want to do, use the GNU Library General
Public License instead of this License.

117
Makefile.in Normal file
View file

@ -0,0 +1,117 @@
#************************************************************************
#* IRC - Internet Relay Chat, Makefile
#* Copyright (C) 1990, Jarkko Oikarinen
#*
#* This program is free software; you can redistribute it and/or modify
#* it under the terms of the GNU General Public License as published by
#* the Free Software Foundation; either version 1, or (at your option)
#* any later version.
#*
#* This program is distributed in the hope that it will be useful,
#* but WITHOUT ANY WARRANTY; without even the implied warranty of
#* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
#* GNU General Public License for more details.
#*
#* You should have received a copy of the GNU General Public License
#* along with this program; if not, write to the Free Software
#* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
#*
#* $Id: Makefile.in,v 1.1 2002/08/13 14:34:56 fishwaldo Exp $
#*/
RM=@RM@
# Default CFLAGS
# CFLAGS = -g -O2 -DNDEBUG
CFLAGS = @CFLAGS@
# Developers CFLAGS
#CFLAGS= -g -O2 -Wunused -Wall -ggdb -pedantic -Wshadow -Wmissing-declarations
# Default make flags - you may want to uncomment this on a multicpu machine
#MFLAGS = -j 4
#
# For developers
#CFLAGS= -g -O2 -Wall
# You may need to define the FD_SETSIZE in order to overrule
# the system one.
#CFLAGS= -DNDEBUG -g -O2 -D"FD_SETSIZE=1024"
SHELL=/bin/sh
SUBDIRS=modules adns src tools doc @SUBDIR_MESSAGES@ include servlink help
CLEANDIRS = ${SUBDIRS} contrib iauth
# XXX removed `iauth' from the build since it doesn't compile currently
# SUBDIRS=src tools iauth
RSA_FILES=rsa_respond/README rsa_respond/respond.c rsa_respond/Makefile
MAKE = make ${MFLAGS}
all: build
autoconf: autoconf/configure.in
autoconf autoconf/configure.in >configure
autoheader -l autoconf autoconf/configure.in > include/setup.h.in
${RM} -f config.cache
build:
-@if [ ! -f include/setup.h ] ; then \
echo "Hmm...doesn't look like you've run configure..."; \
echo "Doing so now."; \
sh configure; \
fi
@for i in $(SUBDIRS); do \
echo "build ==> $$i";\
cd $$i;\
${MAKE} build || exit; cd ..;\
done
clean:
${RM} -f *~ core rsa_respond.tar rsa_respond.tar.gz
@for i in $(CLEANDIRS); do \
echo "clean ==> $$i";\
cd $$i;\
${MAKE} clean; cd ..;\
done
-@if [ -f include/setup.h ] ; then \
echo "To really restart installation, make distclean" ; \
fi
distclean:
${RM} -f Makefile *~ *.rej *.orig core ircd.core
${RM} -f config.status config.cache config.log
cd include; ${RM} -f setup.h *~ *.rej *.orig ; cd ..
@for i in $(CLEANDIRS); do \
echo "distclean ==> $$i";\
cd $$i;\
${MAKE} distclean; cd ..;\
done
depend:
@for i in $(SUBDIRS); do \
echo "depend ==> $$i";\
cd $$i;\
${MAKE} depend; cd ..;\
done
lint:
@for i in $(SUBDIRS); do \
echo "lint ==> $$i";\
cd $$i;\
${MAKE} lint; cd ..;\
done
install: all
@for i in $(SUBDIRS); do \
echo "install ==> $$i";\
cd $$i;\
${MAKE} install; \
cd ..; \
done
rsa_respond:
@cd tools;\
echo "Creating rsa_respond.tar.gz";\
tar cf ../rsa_respond.tar $(RSA_FILES);\
cd ..;\
gzip rsa_respond.tar

115
README.FIRST Normal file
View file

@ -0,0 +1,115 @@
If you don't read this first, we won't help you.
:-)
******************************* IMPORTANT *************************************
*********** Note for those who dont bother reading docs *****************
* - Reading INSTALL is now a must, as the old DPATH is now specified *
* when configure is run. *
* You now need to ./configure --prefix="/path/to/install/it" *
* - The old config format WILL NOT WORK. Please see doc/example.conf ! *
* - The old kline format WILL NOT WORK. Please use convertklines which *
* will be installed with your ircd! *
* - If you get errors compiling custom.mo, check if you are using the *
* most recent version of gettext. Tested with GNU gettext 0.10.35. *
*************************************************************************
ALSO, IF YOU ARE UPGRADING YOUR CURRENT SOURCE TREE, AND YOU TRY TO BUILD
IN IT WITHOUT PERFORMING AT LEAST 'make clean', THINGS _WILL_ BREAK. IT IS
RECOMMENDED THAT YOU RUN 'make distclean' AND THEN RERUN './configure'!
******************************* REQUIREMENTS **********************************
Necessary Requirements:
- A supported platform (look below)
- A working dynamic load library, unless
compiling as static, without module
support.
- A working lex. Solaris /usr/ccs/bin/lex
appears to be broken, on this system flex
should be used.
- A working bison or byacc. FreeBSD and BSD/OS
byacc are broken in some releases, and will
dump core when building the ircd_parser.y. The
solution to this is to upgrade to the most
recent release, or to simply obtain a current
copy of byacc (such as building source from
FreeBSD CVS/CVSup). This is fixed in FreeBSD
4.4-STABLE and later.
Feature Specific Requirements:
- For the SSL Challenge controlled OPER feature and encrypted server links,
a working OpenSSL library
- For dynamic message locale support, a working gettext (intl) library
- For encrypted oper and (optional) server passwords, a working DES and/or
MD5 library
*******************************************************************************
- To report bugs in hybrid, send the bug report to ircd-hybrid@the-project.org
- Known bugs are listed in the BUGS file
- See the INSTALL document for info on configuring and compiling
ircd-hybrid.
- Please read doc/index.txt to get an overview of the current documentation.
- Old Hybrid 5/6 configuration files are no longer supported. All conf
files will have to be converted to the Hybrid 7 format. A convertconf
utility is provided and installed into bin/.
- If you are wondering why config.h is practically empty, its because many
things that were once in config.h are now specified in the 'general'
block of ircd.conf. Look at example.conf for more information about
these options.
- The files, /etc/services, /etc/protocols, and /etc/resolv.conf, MUST be
readable by the user running the server in order for ircd to start.
Errors from adns causing the ircd to refuse to start up are often related
to permission problems on these files.
- There is now a mailing list for general discussion of Hybrid. To subscribe
to the Hybrid List, send email to listmanager@the-project.org with
the subject "subscribe hybrid".
- If you run in to a problem you think may be specific to your platform,
check README.PLATFORMS for some hints.
- 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.
- DARWIN AND MACOS X USERS: You must be using at least the December 2001
Development Tools from Apple to build ircd-hybrid with shared modules.
Before then you MUST disable shared modules, as we do not have the proper
flags for cc(1) prior to that point to produce shared modules.
- SUPPORTED PLATFORMS: this code should compile without any warnings
on FreeBSD 3.x/4.x, RedHat 6.2, Debian Potato and Solaris 7/8 sparc.
Please let us know if you find otherwise.
It probably does not compile on AIX, IRIX or libc5 Linux.
- TESTED PLATFORMS: The code has been tested on the following platforms, and
is known to run properly.
FreeBSD 3.x/4.x
Linux glibc
Solaris 2.6/7/8
OpenBSD 2.8
NetBSD 1.4
Cygwin 1.3+ (static modules, no servlink)
OpenVMS/Alpha 7.2 (static modules, no servlink)
- Please read doc/whats-new.txt for information about what is in this release
- Other files recommended for reading: BUGS, INSTALL
--------------------------------------------------------------------------------
$Id: README.FIRST,v 1.1 2002/08/13 14:34:56 fishwaldo Exp $

36
README.PLATFORMS Normal file
View file

@ -0,0 +1,36 @@
IRCD-Hybrid Platforms Information
Sometimes problems and inconsistencies in the Hybrid code may only occur
on a specific platform (architecture and/or operating system and/or
compiler). In these cases you may want to directly contact a person who
is interested in maintaining Hybrid on that platform. Below is a list of
people who have jumped up and taken responsibility for Hybrid, including
making sure it compiles, runs, and doesn't crash.
Platforms marked with a '*' are known to be broken. In general, README.FIRST
will include specific notes on broken platforms.
ARCHITECTURE COMPILER SYSTEM MAINTAINER
============ ================ ============= ===================================
MIPS gcc IRIX Juli Mallett <jmallett@FreeBSD.org>
MIPS MIPSPro IRIX Juli Mallett <jmallett@FreeBSD.org>
PowerPC Apple gcc Darwin Juli Mallett <jmallett@FreeBSD.org>
PowerPC Apple gcc Mac OS X Juli Mallett <jmallett@FreeBSD.org>
SPARC gcc OpenBSD Juli Mallett <jmallett@FreeBSD.org>
SPARC gcc NetBSD Juli Mallett <jmallett@FreeBSD.org>
x86 gcc FreeBSD Juli Mallett <jmallett@FreeBSD.org>
x86 TenDRA FreeBSD Juli Mallett <jmallett@FreeBSD.org>
SPARC Forte C v6,v7 Solaris Joan Touzet <joant@ieee.org>
SPARC gcc Solaris Joan Touzet <joant@ieee.org>
x86 Cygwin gcc Windows W. Campbell <wcampbel@botbay.net>
x86 gcc Linux Aaron Sethman <androsyn@ratbox.org>
SPARC gcc Linux Aaron Sethman <androsyn@ratbox.org>
Alpha DEC C V6.0 OpenVMS 7.2 Edward Brocklesby
<ejb@sdf.lonestar.org>
PA-RISC 2.0 cc HP-UX B.11 Yusuf Iskenderoglu
<uhc0@stud.uni-karlsruhe.de>
x86 NeXTGCC NEXTSTEP Juli Mallett <jmallett@FreeBSD.org>
SPARC NeXTGCC NEXTSTEP Juli Mallett <jmallett@FreeBSD.org>
m68k NeXTGCC NEXTSTEP Juli Mallett <jmallett@FreeBSD.org>
$Id: README.PLATFORMS,v 1.1 2002/08/13 14:34:56 fishwaldo Exp $

47
README.VMS Normal file
View file

@ -0,0 +1,47 @@
Last tested version: hybrid-7beta9 20020205_1
To compile ircd on VMS, simply execute the make.com script
from the top-level ircd directory:
$ SET DEF [.IRCD-HYBRID-7]
$ @MAKE
This should build [.SRC]IRCD.EXE (servlink is not yet supported
for VMS).
You may want to edit [.INCLUDE]CONFIG.H, but there is no longer
anything very interesting there.
IRCD needs the following logical names defined: IRCD$BASEDIR, IRCD$CONFDIR,
IRCD$BINDIR, and IRCD$LOGDIR.
For example:
$ ASSIGN DISK$USER:[EBROCKLESBY.IRCD.BIN] IRCD$BASEDIR:
$ ASSIGN DISK$USER:[EBROCKLESBY.IRCD.BIN.BIN] IRCD$BINDIR:
$ ASSIGN DISK$USER:[EBROCKLESBY.IRCD.BIN.ETC] IRCD$CONFDIR:
$ ASSIGN DISK$USER:[EBROCKLESBY.IRCD.BIN.LOG] IRCD$LOGDIR:
After IRCD.EXE is built, you'll have to install it by hand. Create
the above directories, and put IRCD.EXE into IRCD$BINDIR:. The sample
[.doc]example.conf should be modified as needed and placed in
IRCD$CONFDIR:IRCD.CONF.
Known problems on VMS:
- Lack of SERVLINK support means that ZIP and SSL aren't yet possible
for VMS.
- If IRCD.EXE exits immediately after startup, make sure that IRCD$CONFDIR:IRCD.PID
doesn't exist.
It should work fine when started with RUN/DETACH.
So far, IRCD has been tested on OpenVMS 7.2/Alpha using DEC C V6.0-001.
If anyone gets ircd working on VMS (or has problems with it), please mail me
(ejb@sdf.lonestar.org) with any comments you have.
If you have problem compiling from source, or are on a slow system
(building IRCD on a VAXstation 3000 takes about two hours),
binary distributions are available on the FTP site.
(actually, they aren't yet, but at some time in the future they should be)
$Id: README.VMS,v 1.1 2002/08/13 14:34:56 fishwaldo Exp $

56
RELNOTES Normal file
View file

@ -0,0 +1,56 @@
-- ircd-hybrid-7rc1 RELNOTES
o) Made topiclen configurable with autoconf
o) Autoconf fixes for Forte C
o) Bugfixes for m_jupe.c in contrib/
o) Fixed bug where we would give away spoofed IPs
o) You may now disable the help system for users, by setting
"use_help = no;" in your general {}; block.
--------------------------------------------------------------------------------
This is the current release candidate version of ircd-hybrid-7.
NOTE: This is still BETA code. Run it at your own risk. By running this
code you assume FULL responsibility for any problems it may cause. We do
NOT recommend that you run BETA code on production IRC networks such
as EFnet.
BUGS: Major bugs in this release are listed in BUGS
BUG REPORTS: If you run this code and encounter problems, you must report
the bug in one of the following ways:
a) By EMAIL to ircd-hybrid@the-project.org.
Please include a gdb backtrace and a copy of your config.h and ircd.conf
with any report (with passwords and other sensitive information masked).
DISCUSSION: There is a mailing list for discussion of hybrid issues,
including betas. To subscribe, send an emal to listmanager@the-project.org
with a single line in the body containing "subscribe hybrid". This is the
proper place to discuss new features, bugs, etc. Posting here is much more
likely to get something done than ranting on #TZ.
TESTING: This code is under active development, and a lot changes from beta
to beta. As the user of this code, we request that you help us test things
which have changed recently, and which would benefeit from being tested
much as possible. The following are some things that have changed, and what
you can do to help us test them.
o) Exiting Clients
- The way clients are exited and cleaned from memory has been largely
redone since the last release. Unusual situations involving clients
exiting will help expose any remaining problems.
o) Mac OS X Modules
- Support for Darwin and Mac OS X style modules, through the
NSModule(3) interface has been added, and is designed to work as
loadable modules do on most UNIX systems. Feeding it bad or
duplicate modules to find bugs would be appriciated.
Questions/comments directed to ircd-hybrid@the-project.org
Please read doc/whats-new.txt for information about what is in this release
Other files recommended for reading: BUGS, README.FIRST, INSTALL
--------------------------------------------------------------------------------
$Id: RELNOTES,v 1.1 2002/08/13 14:34:56 fishwaldo Exp $

122
TODO Normal file
View file

@ -0,0 +1,122 @@
$Id: TODO,v 1.1 2002/08/13 14:34:56 fishwaldo Exp $
- add more stderr debugging (ircd -s)... one for every place we syslog()
- ircd -s doesn't work through a restart
- re-implement first param in m_lusers()
- trie' channel name list
- finish RFC'ing m_message.c
----
is-'s TODO list
- umode +R for registered nick
- TBURST
- change nick instead of kill on nick collide
- dynamically extensible parser for modules
- modularize channel, network code etc (not just commands)
we can use override_function() or similar for this
- username/passwords (iauth ?)
- channel modes to allow/prevent talking on channel
by hostmasks.
-----------------------------------------------------------------------------
madmax's TODO
- Make stats p just notice opers, rather than return a list, when
server_hide is on (#13)
- Client UIDs (ts4 style?) for cookies (later for persistent nicks)
- Definable server region or 'global' (open I) for /links output (#20)
-----------------------------------------------------------------------------
Adrian's TODO list
* make the reserved FD limit run-time tunable, esp from comm_open()
This involves making fd_table[] a dynamically growing/(don't bother with
shrinking) list.. have the max fd list configurable in the conf file..
* Fix the anti-client flood code to not be so anal when people connect -
I've counted all lines from a client as being a flood, so if a client
connects and issues JOIN's to a whole bunch of channels the flood
protection stops everything coming through at once .. (not that I mind.. :)
* PLEASE redo all dlink_list management with the stuff in src/tools.c
* In the server outbound connection code, make the sendto_realops()
logging more sane. Ie, if there's an error, also log the errno string.
* look at the old Listener code in s_bsd.c before I chopped it. Notice
the anti-flood code in there. Make sure the same load-checking stuff
is in listener.c
* get send_message(), replace comm_setselect() with send_queued_write(), see
if the optimization works
* remove aconf->ipnum, since we're doing a DNS lookup each time we
connect. If people don't like this, they can (should!) be running
a name cache locally!
db-->>ummm aconf->ipnum is used for IP based klines only, not for DNS
* Add the IRCnet(?) split logic for nick collisions - on a nick collision,
change to "%d-%s", random, nick
* Hrm. Since Diane changed the user->channel code to use dlink_lists,
she's made some things faster (deopping lists of people in a net.join,
finding an op, etc) but some things slower (deleting from the channel,
change_channel_membership(), etc.) What needs to happen is that for
each channel a user is on, a flag needs to be set tracking which list
they're on so we don't have to search the lists when we want to change
their status. This could become a slow-CPU sticking point.
db-->> Actually, the old code was just as slow at doing that, since
it was a link list of SLink's with a flag denoting whether client
on channel was an op or not... With a channel of 100 clients and
thats 100 link SLink's
------------------------------------------------------------------------------
Little things to be done given enough time and initiative -Hwy
. The 3 logging path settings are NOOP in the conf (logpath, oper_log,
gline_log)
. Fix convertconf more
. 2 pass conf parser (grab classes before anything that uses them)
. Re-add the ability to set usermodes from the conf (oldconf field after the
O: line class)
. <Riedel> walter : have you implemented the motd= thing in the auth block ?
. Fix topic bursting to LL servers (broke lately for some reason)
--> Unknown status
. A FAQ
--> Dracus is working on this, I will try to put something together too
. Major cleanup of example.conf, it's a disgrace
--> Still a disgrace
. chkconf
--> SCARY!!!
. More translations!
-- Rodder's list
. Add scalable database-based authentication. Probably part of Iauth.
Also add support for server-side notify with the list stored in the
auth database. This would make ircd an awesome instant messaging
back-end.
-- jdc's list
* Re-write m_stats.c to be table-based, similar to m_set. Also change
to support funtion exit code values (int), so that STATS output can
be "successful" or "unsuccessful" (eg. "STATS i requested by <nick>
[unsuccessful]" vs. "STATS i requested by <nick>").
--> Table part I know is done, what about the success status?
* Re-write proper startup procedure for daemon; procedure should be
done in stages, similar to boot0/1/2 stages in FreeBSD.
* Write secure cryptlink protocol with help from Sean.
-- Diane's list
* add logging to ircd.log of possible channel floods
* add code to log a minute worth of flooding if the ircd gets n possible
flood messages on a channel in t seconds.. This log would be available
to hand to authorities if requested.

1
adns/.cvsignore Normal file
View file

@ -0,0 +1 @@
Makefile

340
adns/COPYING Normal file
View file

@ -0,0 +1,340 @@
GNU GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1989, 1991 Free Software Foundation, Inc.
59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. This
General Public License applies to most of the Free Software
Foundation's software and to any other program whose authors commit to
using it. (Some other Free Software Foundation software is covered by
the GNU Library General Public License instead.) You can apply it to
your programs, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must show them these terms so they know their
rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that redistributors of a free
program will individually obtain patent licenses, in effect making the
program proprietary. To prevent this, we have made it clear that any
patent must be licensed for everyone's free use or not licensed at all.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License applies to any program or other work which contains
a notice placed by the copyright holder saying it may be distributed
under the terms of this General Public License. The "Program", below,
refers to any such program or work, and a "work based on the Program"
means either the Program or any derivative work under copyright law:
that is to say, a work containing the Program or a portion of it,
either verbatim or with modifications and/or translated into another
language. (Hereinafter, translation is included without limitation in
the term "modification".) Each licensee is addressed as "you".
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running the Program is not restricted, and the output from the Program
is covered only if its contents constitute a work based on the
Program (independent of having been made by running the Program).
Whether that is true depends on what the Program does.
1. You may copy and distribute verbatim copies of the Program's
source code as you receive it, in any medium, provided that you
conspicuously and appropriately publish on each copy an appropriate
copyright notice and disclaimer of warranty; keep intact all the
notices that refer to this License and to the absence of any warranty;
and give any other recipients of the Program a copy of this License
along with the Program.
You may charge a fee for the physical act of transferring a copy, and
you may at your option offer warranty protection in exchange for a fee.
2. You may modify your copy or copies of the Program or any portion
of it, thus forming a work based on the Program, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) You must cause the modified files to carry prominent notices
stating that you changed the files and the date of any change.
b) You must cause any work that you distribute or publish, that in
whole or in part contains or is derived from the Program or any
part thereof, to be licensed as a whole at no charge to all third
parties under the terms of this License.
c) If the modified program normally reads commands interactively
when run, you must cause it, when started running for such
interactive use in the most ordinary way, to print or display an
announcement including an appropriate copyright notice and a
notice that there is no warranty (or else, saying that you provide
a warranty) and that users may redistribute the program under
these conditions, and telling the user how to view a copy of this
License. (Exception: if the Program itself is interactive but
does not normally print such an announcement, your work based on
the Program is not required to print an announcement.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Program,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Program, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Program.
In addition, mere aggregation of another work not based on the Program
with the Program (or with a work based on the Program) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may copy and distribute the Program (or a work based on it,
under Section 2) in object code or executable form under the terms of
Sections 1 and 2 above provided that you also do one of the following:
a) Accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of Sections
1 and 2 above on a medium customarily used for software interchange; or,
b) Accompany it with a written offer, valid for at least three
years, to give any third party, for a charge no more than your
cost of physically performing source distribution, a complete
machine-readable copy of the corresponding source code, to be
distributed under the terms of Sections 1 and 2 above on a medium
customarily used for software interchange; or,
c) Accompany it with the information you received as to the offer
to distribute corresponding source code. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form with such
an offer, in accord with Subsection b above.)
The source code for a work means the preferred form of the work for
making modifications to it. For an executable work, complete source
code means all the source code for all modules it contains, plus any
associated interface definition files, plus the scripts used to
control compilation and installation of the executable. However, as a
special exception, the source code distributed need not include
anything that is normally distributed (in either source or binary
form) with the major components (compiler, kernel, and so on) of the
operating system on which the executable runs, unless that component
itself accompanies the executable.
If distribution of executable or object code is made by offering
access to copy from a designated place, then offering equivalent
access to copy the source code from the same place counts as
distribution of the source code, even though third parties are not
compelled to copy the source along with the object code.
4. You may not copy, modify, sublicense, or distribute the Program
except as expressly provided under this License. Any attempt
otherwise to copy, modify, sublicense or distribute the Program is
void, and will automatically terminate your rights under this License.
However, parties who have received copies, or rights, from you under
this License will not have their licenses terminated so long as such
parties remain in full compliance.
5. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Program or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Program (or any work based on the
Program), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Program or works based on it.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the
original licensor to copy, distribute or modify the Program subject to
these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
7. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Program at all. For example, if a patent
license would not permit royalty-free redistribution of the Program by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Program.
If any portion of this section is held invalid or unenforceable under
any particular circumstance, the balance of the section is intended to
apply and the section as a whole is intended to apply in other
circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system, which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
8. If the distribution and/or use of the Program is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Program under this License
may add an explicit geographical distribution limitation excluding
those countries, so that distribution is permitted only in or among
countries not thus excluded. In such case, this License incorporates
the limitation as if written in the body of this License.
9. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of this License which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
this License, you may choose any version ever published by the Free Software
Foundation.
10. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to the public, the best way to achieve this is to make it
free software which everyone can redistribute and change under these terms.
To do so, attach the following notices to the program. It is safest
to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least
the "copyright" line and a pointer to where the full notice is found.
<one line to give the program's name and a brief idea of what it does.>
Copyright (C) 19yy <name of author>
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
Also add information on how to contact you by electronic and paper mail.
If the program is interactive, make it output a short notice like this
when it starts in an interactive mode:
Gnomovision version 69, Copyright (C) 19yy name of author
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the appropriate
parts of the General Public License. Of course, the commands you use may
be called something other than `show w' and `show c'; they could even be
mouse-clicks or menu items--whatever suits your program.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the program, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
`Gnomovision' (which makes passes at compilers) written by James Hacker.
<signature of Ty Coon>, 1 April 1989
Ty Coon, President of Vice
This General Public License does not permit incorporating your program into
proprietary programs. If your program is a subroutine library, you may
consider it more useful to permit linking proprietary applications with the
library. If this is what you want to do, use the GNU Library General
Public License instead of this License.

122
adns/GPL-vs-LGPL Normal file
View file

@ -0,0 +1,122 @@
GPL vs LGPL, in the context of adns
-----------------------------------
Several people have asked me to release GNU adns under the GNU Lesser
General Public Licence (LGPL, formerly the Library GPL) instead of the
`stronger' GPL. This file is intended to answer most of these
questions. If you still have questions or comments, please mail me at
<adns-maint@chiark.greenend.org.uk>.
Typically there are two or three kinds of situation where people make
this request: the first is where someone is developing a proprietary
program and wishes to make use of adns but doesn't wish to make their
program free software. The second case is where a free software
project is currently using an MIT-like licence or the LGPL and fear
`GPL infection'. The third case, which often overlaps with the
second, is where another free software project currently using a
GPL-incompatible licence, wishes to use adns.
1. Proprietary applications of adns
-----------------------------------
So, let me get this straight. You're writing a proprietary
program, by which I mean that you will not be distributing source code
and not allowing users to modify and share your software; most likely
you are doing this for your own (personal or corporate) financial
gain.
However, you want to take advantage of adns, software which I have
spent my time and effort on, and which I release as free software so
that everyone can improve, share and use it.
Don't you think that is a little hypocritical ? I'm sorry, but I
don't want you to just take my nice convenient software, without
giving something back to the free software community or giving the
same rights to your users as I do to you.
If you really aren't the nasty kind of person I've described here, for
example if you have a good reason other than your own selfishness for
wanting to restrict distribution of your program, then perhaps you
should contact me to discuss it.
2. GPL-avoiding projects (MIT licence, et al)
---------------------------------------------
Some free software projects prefer to avoid the GPL and other licences
which force the software always to be free. Instead they use
something like the MIT X licence, which allows proprietary versions of
their software, or the in the case of some free libraries, the LGPL,
which allows proprietary applications. I have to say that I think
these people are misguided, but that doesn't mean that they don't have
a perfect right to do that.
Some of these people think that merely writing to an interface
provided by GPL'd software will cause their program to become GPL'd
too, even if they don't distribute the GPL'd software. I don't think
this is the case. I'm perfectly happy for non-GPL'd but
GPL-compatible software to refer to adns in its source code. However,
I think that exectuables (or compiled libraries) which contain or are
dynamically linked against adns must be GPL'd; likewise executable
programs (whether compiled or in an interpreted language) which
require utilities from adns to function properly must be GPL'd.
So, you can distribute your non-GPL'd program source which needs adns
to compile (provided it's under a GPL-compatible licence), but people
who wish to distribute binaries must do so under the terms of the GNU
GPL. This may make sense for some GPL-avoiding free software
projects; people can still make proprietary programs from your code,
provided that they make some provision to replace adns with something
whose copyright allows proprietary versions.
However, this doesn't make much sense for the authors of LGPL'd
libraries. All I can say to them is to ask which is more important:
that their library be well-constructed and use all the best technology
available as free software, or whether it is worth degrading quality
of their library in order to allow proprietary programs to use it !
To help the case of LGPL'd libraries for which adns is not a vital
component - for example, a library which provides access to other
libraries so that programs which use it need only use certain parts,
I have released adns.h (just the public header file) under the LGPL as
well as the GPL. See the copyright notice in adns.h for details.
Note that this will not help you if it adns is essential to the
functioning of your library, because all programs using your library
must link against both your library and adns and so must be GPL'd.
For some information and views from the Free Software Foundation on
free software licensing, visit:
Various licenses and comments about them
at http://www.fsf.org/philosophy/license-list.html
Why you shouldn't use the Library GPL for your next library
at http://www.fsf.org/philosophy/why-not-lgpl.html
3. GPL-incompatible free software licences
------------------------------------------
Regrettably, there are a number of free software licences (and
semi-free licences) in existence which are not compatible with the
GPL. That is, they impose restrictions which are not present in the
GPL, and therefore distributing a whole work which contains both such
a program and a GPL'd program is not possible: either the combination
would have to be distributed under the GPL (violating the restrictions
made by the original author), or under the GPL-incompatible licence
(violating the GPL).
I may be prepared to make exceptions for such a licence. Please
contact me at <adns-maint@chiark.greenend.org.uk> with the full text
of the GPL-incompatible licence. However, I would usually prefer it
if you could use a GPL-compatible licence for your project instead.
-- Ian Jackson 17.9.2000
Local variables:
mode: text
End:

81
adns/Makefile.in Normal file
View file

@ -0,0 +1,81 @@
#
# Makefile.in for ircd/src
#
# $Id: Makefile.in,v 1.1 2002/08/13 14:35:02 fishwaldo Exp $
#
CC = @CC@
INSTALL = @INSTALL@
INSTALL_BIN = @INSTALL_PROGRAM@
INSTALL_DATA = @INSTALL_DATA@
INSTALL_SUID = @INSTALL_PROGRAM@ -o root -m 4755
RM = @RM@
LEX = @LEX@
LEXLIB = @LEXLIB@
CFLAGS = @IRC_CFLAGS@ -DIRCD_PREFIX=\"@prefix@\"
LDFLAGS = @LDFLAGS@
MKDEP = @MKDEP@ -DIRCD_PREFIX=\"@prefix@\"
MV = @MV@
RM = @RM@
YACC = @YACC@
AR = @AR@
RANLIB = @RANLIB@
prefix = @prefix@
exec_prefix = @exec_prefix@
bindir = @bindir@
libexecdir = @libexecdir@
sysconfdir = @sysconfdir@
localstatedir = @localstatedir@
# Change this later! -- adrian
moduledir = @prefix@/modules
automoduledir = @prefix@/modules/autoload
INCLUDES = -I../include -I.
CPPFLAGS = ${INCLUDES} @CPPFLAGS@
default: all
BASE_SRCS = check.c event.c general.c parse.c query.c reply.c setup.c \
transmit.c types.c
SRCS = ${BASE_SRCS} ${SELECT_SRC}
OBJS = ${SRCS:.c=.o}
all: libadns.a
build: all
libadns.a: ${OBJS}
rm -f $@
${AR} cqv $@ ${OBJS}
${RANLIB} $@
# this is really the default rule for c files
.c.o:
${CC} ${CPPFLAGS} ${CFLAGS} -c $<
.PHONY: depend clean distclean
install:
depend:
@${MKDEP} ${CPPFLAGS} ${BASE_SRCS} ${EXTRA_SRCS} > .depend.tmp
@sed -e '/^# DO NOT DELETE THIS LINE/,$$d' <Makefile >Makefile.depend
@echo '# DO NOT DELETE THIS LINE!!!' >>Makefile.depend
@echo '# make depend needs it.' >>Makefile.depend
@cat .depend.tmp >>Makefile.depend
@mv Makefile.depend Makefile
@rm -f .depend.tmp
clean:
${RM} -f *.o *.exe *~ libadns.a
lint:
distclean: clean
${RM} -f Makefile version.c.last
# DO NOT DELETE THIS LINE!!!
# make depend needs it.

167
adns/README Normal file
View file

@ -0,0 +1,167 @@
GNU adns
Advanced, easy to use, asynchronous-capable DNS client library and
utilities.
adns is a resolver library for C (and C++) programs, and a collection
of useful DNS resolver utilities.
C library
In contrast with the standard interfaces, gethostbyname et al and
libresolv, it has the following features:
* It is reasonably easy to use for simple programs which just want
to translate names to addresses, look up MX records, etc.
* It can be used in an asynchronous, non-blocking, manner. Many
queries can be handled simultaneously.
* Responses are decoded automatically into a natural representation
for a C program - there is no need to deal with DNS packet
formats.
* Sanity checking (eg, name syntax checking, reverse/forward
correspondence, CNAME pointing to CNAME) is performed
automatically.
* Time-to-live, CNAME and other similar information is returned in
an easy-to-use form, without getting in the way.
* There is no global state in the library; resolver state is an
opaque data structure which the client creates explicitly. A
program can have several instances of the resolver.
* Errors are reported to the application in a way that distinguishes
the various causes of failure properly.
* Understands conventional resolv.conf, but this can overridden by
environment variables.
* Flexibility. For example, the application can tell adns to: ignore
environment variables (for setuid programs), disable hostname
syntax sanity checks to return arbitrary data, override or ignore
resolv.conf in favour of supplied configuration, etc.
* Believed to be correct ! For example, will correctly back off to
TCP in case of long replies or queries, or to other nameservers if
several are available. It has sensible handling of bad responses
etc.
DNS utility programs
adns also comes with a number of utility programs for use from the
command line and in scripts:
* adnslogres is a much faster version of Apache's logresolv program.
* adnsresfilter is a filter which copies its input to its output,
replacing IP addresses by the corresponding names, without unduly
delaying the output. For example, you can usefully pipe the output
of netstat -n, tcpdump -ln, and the like, into it.
* adnshost is a general-purpose DNS lookup utility which can be used
easily in from the command line and from shell scripts to do
simple lookups. In a more advanced mode it can be used as a
general-purpose DNS helper program for scripting languages which
can invoke and communicate with subprocesses. See the [1]adnshost
usage message for a summary of its capabilities.
Documentation
I'm afraid there is no manual yet. However, competent C programmers
should be able to use the library based on the [2]commented adns.h
header file, and the usage messages for the programs should be
sufficient.
Feedback
I'd be pleased if you would let me know if you're using my library in
your project, and what you think of it.
If you are subscribed to adns-discuss please send feedback, including
bug reports, there; otherwise send mail to
adns-bugreports@chiark.greenend.org.uk. If you'd prefer that your
message wasn't forwarded to the adns-bugreports list, send it to
adns-maint@chiark.greenend.org.uk.
Mailinglists
I have set up mailinglists adns-announce and adns-discuss. The
announcements list is moderated and will contain only announcements of
important bugs, new versions, etc. The bug reports address mentioned
above is also a mailing list; feel free to subscribe to it.
There are [3]archives and subscription web pages, or you can subscribe
by sending mail containing the word `subscribe' to
adns-announce-REQUEST@chiark.greenend.org.uk or
adns-discuss-REQUEST@chiark.greenend.org.uk.
Download
Available for download from [4]chiark.greenend.org.uk are:
* The [5]current release as a gzipped tarfile.
* [6]adns.h API header file with comments, and [7]usage message for
adnshost (currently there is no manual, sorry).
* All versions released so far are also available via [8]anonymous
FTP and [9]HTTP,
* A mirror of my CVS repository is available via rsync from
rsync.chiark.greenend.org.uk::ftp/users/ian/cvs-pub/adns (use FTP
first to find your way around), or via [10]cvsweb.
adns is also available from the [11]GNU Project FTP servers and their
[12]mirrors.
Technical note
adns requires a real nameserver like [13]BIND or [14]Dents running on
the same system or a nearby one, which must be willing to provide
`recursive service'. I.e., adns is a `stub resolver'. All properly
configured UN*X and GNU systems will already have such nameserver(s);
they are usually listed in /etc/resolv.conf.
Copyright and licensing
adns is Copyright 1997-2000 Ian Jackson, Copyright 1999-2000 Tony
Finch, and Copyright (C) 1991 Massachusetts Institute of Technology.
adns 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 and documentation 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
[15]GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with adns, or one should be available above; if not, write to
the [16]Free Software Foundation, 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA, or email adns-maint@chiark.greenend.org.uk.
_________________________________________________________________
[17]Ian Jackson / [18]adns-maint@chiark.greenend.org.uk; more [19]free
software by me.
[20]GNU home page; [21]chiark home page; [22]site or mirror home page
This web page is Copyright (C)1996-2000 Ian Jackson. See the
[23]Copyright/acknowledgements.
Use any browser - [24]Campaign for a non-browser-specific WWW
References
1. http://www.chiark.greenend.org.uk/~ian/adns/adnshost.txt
2. http://www.chiark.greenend.org.uk/~ian/adns/adns.h.txt
3. http://www.chiark.greenend.org.uk/mailman/listinfo
4. http://www.chiark.greenend.org.uk/~ian/adns/
5. http://www.chiark.greenend.org.uk/~ian/adns/adns.tar.gz
6. http://www.chiark.greenend.org.uk/~ian/adns/adns.h.txt
7. http://www.chiark.greenend.org.uk/~ian/adns/adnshost.txt
8. ftp://ftp.chiark.greenend.org.uk/users/ian/adns/
9. http://www.chiark.greenend.org.uk/~ian/adns/ftp/
10. http://www.chiark.greenend.org.uk/ucgi/~ijackson/cvsweb/adns/
11. http://www.gnu.org/
12. http://www.gnu.org/order/ftp.html
13. http://www.isc.org/view.cgi?/products/BIND/index.phtml
14. http://www.dents.org/
15. http://www.chiark.greenend.org.uk/~ian/COPYING.txt
16. http://www.fsf.org/
17. http://www.chiark.greenend.org.uk/
18. mailto:adns-maint@chiark.greenend.org.uk
19. http://www.chiark.greenend.org.uk/~ian/software/
20. http://www.gnu.org/
21. http://www.chiark.greenend.org.uk/
22. file://localhost/
23. http://www.chiark.greenend.org.uk/~ian/sw-www-copy.html
24. http://www.anybrowser.org/campaign/

11
adns/README.ircd Normal file
View file

@ -0,0 +1,11 @@
The files in adns/ were borrowed from the ADNS library and modified quite
heavily. The original code's copyright notices are in adns/README.
The modified portions are Copyright 2000 Aaron Sethman <androsyn@ratbox.org>
Basically what has changed is getting adns to work with our event loop and
IPv6 support. Note that the IPv6 support isn't real great right now and may
not even work. The IPv4 support seems okay though.

875
adns/adns.h Normal file
View file

@ -0,0 +1,875 @@
/*
* adns.h
* - adns user-visible API (single-threaded, without any locking)
*/
/*
*
* This file is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999-2000 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
*
* For the benefit of certain LGPL'd `omnibus' software which
* provides a uniform interface to various things including adns, I
* make the following additional licence. I do this because the GPL
* would otherwise force either the omnibus software to be GPL'd or
* the adns-using part to be distributed separately.
*
* So: you may also redistribute and/or modify adns.h (but only the
* public header file adns.h and not any other part of adns) under the
* terms of the GNU Library General Public License as published by the
* Free Software Foundation; either version 2 of the License, or (at
* your option) any later version.
*
* Note that adns itself is GPL'd. Authors of adns-using applications
* with GPL-incompatible licences, and people who distribute adns with
* applications where the whole distribution is not GPL'd, are still
* likely to be in violation of the GPL. Anyone who wants to do this
* should contact Ian Jackson. Please note that to avoid encouraging
* people to infringe the GPL as it applies to the body of adns, Ian
* thinks that if you take advantage of the special exception to
* redistribute just adns.h under the LGPL, you should retain this
* paragraph in its place in the appropriate copyright statements.
*
*
* You should have received a copy of the GNU General Public License,
* or the GNU Library General Public License, as appropriate, along
* with this program; if not, write to the Free Software Foundation,
* Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*
*
* $Id: adns.h,v 1.1 2002/08/13 14:35:04 fishwaldo Exp $
*/
#ifndef ADNS_H_INCLUDED
#define ADNS_H_INCLUDED
#include "stdinc.h"
#include "ircd.h"
#include "ircd_defs.h"
#include "irc_string.h"
#include "sprintf_irc.h"
#define MAXFD_POLL 2
struct adns_pollfd { int fd; short events; short revents; };
#define ADNS_POLLIN 1
#define ADNS_POLLPRI 2
#define ADNS_POLLOUT 4
#ifndef timercmp
#define timercmp(tvp, uvp, cmp) \
(((tvp)->tv_sec == (uvp)->tv_sec) ? \
((tvp)->tv_usec cmp (uvp)->tv_usec) : \
((tvp)->tv_sec cmp (uvp)->tv_sec))
#endif
#ifndef timerclear
#define timerclear(tvp) (tvp)->tv_sec = (tvp)->tv_usec = 0
#endif
/* All struct in_addr anywhere in adns are in NETWORK byte order. */
typedef struct adns__state *adns_state;
typedef struct adns__query *adns_query;
typedef enum {
adns_if_noenv= 0x0001, /* do not look at environment */
adns_if_noerrprint= 0x0002, /* never print output to stderr (_debug overrides) */
adns_if_noserverwarn= 0x0004, /* do not warn to stderr about duff nameservers etc */
adns_if_debug= 0x0008, /* enable all output to stderr plus debug msgs */
adns_if_logpid= 0x0080, /* include pid in diagnostic output */
adns_if_noautosys= 0x0010, /* do not make syscalls at every opportunity */
adns_if_eintr= 0x0020, /* allow _wait and _synchronous to return EINTR */
adns_if_nosigpipe= 0x0040, /* applic has SIGPIPE set to SIG_IGN, do not protect */
adns_if_checkc_entex= 0x0100, /* do consistency checks on entry/exit to adns funcs */
adns_if_checkc_freq= 0x0300 /* do consistency checks very frequently (slow!) */
} adns_initflags;
typedef enum {
adns_qf_search= 0x00000001, /* use the searchlist */
adns_qf_usevc= 0x00000002, /* use a virtual circuit (TCP connection) */
adns_qf_owner= 0x00000004, /* fill in the owner field in the answer */
adns_qf_quoteok_query= 0x00000010, /* allow special chars in query domain */
adns_qf_quoteok_cname= 0x00000000, /* allow ... in CNAME we go via - now default */
adns_qf_quoteok_anshost= 0x00000040, /* allow ... in things supposed to be hostnames */
adns_qf_quotefail_cname= 0x00000080, /* refuse if quote-req chars in CNAME we go via */
adns_qf_cname_loose= 0x00000100, /* allow refs to CNAMEs - without, get _s_cname */
adns_qf_cname_forbid= 0x00000200, /* don't follow CNAMEs, instead give _s_cname */
adns__qf_internalmask= 0x0ff00000
} adns_queryflags;
typedef enum {
adns__rrt_typemask= 0x0ffff,
adns__qtf_deref= 0x10000, /* dereference domains and perhaps produce extra data */
adns__qtf_mail822= 0x20000, /* make mailboxes be in RFC822 rcpt field format */
adns__qtf_in6= 0x40000, /* ptr is IPv6 -- This is a hack but it works damnit. If you don't like it fix it yourself */
adns_r_none= 0,
adns_r_a= 1,
adns_r_ns_raw= 2,
adns_r_ns= adns_r_ns_raw|adns__qtf_deref,
adns_r_cname= 5,
adns_r_soa_raw= 6,
adns_r_soa= adns_r_soa_raw|adns__qtf_mail822,
adns_r_ptr_raw= 12,
adns_r_ptr= adns_r_ptr_raw|adns__qtf_deref,
adns_r_ptr_ip6= adns_r_ptr_raw|adns__qtf_deref|adns__qtf_in6,
adns_r_hinfo= 13,
adns_r_mx_raw= 15,
adns_r_mx= adns_r_mx_raw|adns__qtf_deref,
adns_r_txt= 16,
adns_r_rp_raw= 17,
adns_r_rp= adns_r_rp_raw|adns__qtf_mail822,
adns_r_addr= adns_r_a|adns__qtf_deref,
adns_r_aaaa= 28,
adns_r_addr6= adns_r_aaaa|adns__qtf_deref
} adns_rrtype;
/*
* In queries without qf_quoteok_*, all domains must have standard
* legal syntax, or you get adns_s_querydomainvalid (if the query
* domain contains bad characters) or adns_s_answerdomaininvalid (if
* the answer contains bad characters).
*
* In queries _with_ qf_quoteok_*, domains in the query or response
* may contain any characters, quoted according to RFC1035 5.1. On
* input to adns, the char* is a pointer to the interior of a "
* delimited string, except that " may appear in it unquoted. On
* output, the char* is a pointer to a string which would be legal
* either inside or outside " delimiters; any character which isn't
* legal in a hostname (ie alphanumeric or hyphen) or one of _ / +
* (the three other punctuation characters commonly abused in domain
* names) will be quoted, as \X if it is a printing ASCII character or
* \DDD otherwise.
*
* If the query goes via a CNAME then the canonical name (ie, the
* thing that the CNAME record refers to) is usually allowed to
* contain any characters, which will be quoted as above. With
* adns_qf_quotefail_cname you get adns_s_answerdomaininvalid when
* this happens. (This is a change from version 0.4 and earlier, in
* which failing the query was the default, and you had to say
* adns_qf_quoteok_cname to avoid this; that flag is now deprecated.)
*
* In version 0.4 and earlier, asking for _raw records containing
* mailboxes without specifying _qf_quoteok_anshost was silly. This
* is no longer the case. In this version only parts of responses
* that are actually supposed to be hostnames will be refused by
* default if quote-requiring characters are found.
*/
/*
* If you ask for an RR which contains domains which are actually
* encoded mailboxes, and don't ask for the _raw version, then adns
* returns the mailbox formatted suitably for an RFC822 recipient
* header field. The particular format used is that if the mailbox
* requires quoting according to the rules in RFC822 then the
* local-part is quoted in double quotes, which end at the next
* unescaped double quote (\ is the escape char, and is doubled, and
* is used to escape only \ and "). If the local-part is legal
* without quoting according to RFC822, it is presented as-is. In any
* case the local-part is followed by an @ and the domain. The domain
* will not contain any characters not legal in hostnames.
*
* Unquoted local-parts may contain any printing 7-bit ASCII
* except the punctuation characters ( ) < > @ , ; : \ " [ ]
* I.e. they may contain alphanumerics, and the following
* punctuation characters: ! # % ^ & * - _ = + { } .
*
* adns will reject local parts containing control characters (byte
* values 0-31, 127-159, and 255) - these appear to be legal according
* to RFC822 (at least 0-127) but are clearly a bad idea. RFC1035
* syntax does not make any distinction between a single RFC822
* quoted-string containing full stops, and a series of quoted-strings
* separated by full stops; adns will return anything that isn't all
* valid atoms as a single quoted-string. RFC822 does not allow
* high-bit-set characters at all, but adns does allow them in
* local-parts, treating them as needing quoting.
*
* If you ask for the domain with _raw then _no_ checking is done
* (even on the host part, regardless of adns_qf_quoteok_anshost), and
* you just get the domain name in master file format.
*
* If no mailbox is supplied the returned string will be `.' in either
* case.
*/
typedef enum {
adns_s_ok,
/* locally induced errors */
adns_s_nomemory,
adns_s_unknownrrtype,
adns_s_systemfail,
adns_s_max_localfail= 29,
/* remotely induced errors, detected locally */
adns_s_timeout,
adns_s_allservfail,
adns_s_norecurse,
adns_s_invalidresponse,
adns_s_unknownformat,
adns_s_max_remotefail= 59,
/* remotely induced errors, reported by remote server to us */
adns_s_rcodeservfail,
adns_s_rcodeformaterror,
adns_s_rcodenotimplemented,
adns_s_rcoderefused,
adns_s_rcodeunknown,
adns_s_max_tempfail= 99,
/* remote configuration errors */
adns_s_inconsistent, /* PTR gives domain whose A does not exist and match */
adns_s_prohibitedcname, /* CNAME found where eg A expected (not if _qf_loosecname) */
adns_s_answerdomaininvalid,
adns_s_answerdomaintoolong,
adns_s_invaliddata,
adns_s_max_misconfig= 199,
/* permanent problems with the query */
adns_s_querydomainwrong,
adns_s_querydomaininvalid,
adns_s_querydomaintoolong,
adns_s_max_misquery= 299,
/* permanent errors */
adns_s_nxdomain,
adns_s_nodata,
adns_s_max_permfail= 499
} adns_status;
typedef struct {
int len;
union {
struct sockaddr sa;
struct sockaddr_in inet;
#ifdef IPV6
struct sockaddr_in6 inet6;
#endif
} addr;
} adns_rr_addr;
typedef struct {
char *host;
adns_status astatus;
int naddrs; /* temp fail => -1, perm fail => 0, s_ok => >0 */
adns_rr_addr *addrs;
} adns_rr_hostaddr;
typedef struct {
char *(array[2]);
} adns_rr_strpair;
typedef struct {
int i;
adns_rr_hostaddr ha;
} adns_rr_inthostaddr;
typedef struct {
/* Used both for mx_raw, in which case i is the preference and str the domain,
* and for txt, in which case each entry has i for the `text' length,
* and str for the data (which will have had an extra nul appended
* so that if it was plain text it is now a null-terminated string).
*/
int i;
char *str;
} adns_rr_intstr;
typedef struct {
adns_rr_intstr array[2];
} adns_rr_intstrpair;
typedef struct {
char *mname, *rname;
unsigned long serial, refresh, retry, expire, minimum;
} adns_rr_soa;
typedef struct {
adns_status status;
char *cname; /* always NULL if query was for CNAME records */
char *owner; /* only set if requested in query flags, and may be 0 on error anyway */
adns_rrtype type; /* guaranteed to be same as in query */
time_t expires; /* expiry time, defined only if _s_ok, nxdomain or nodata. NOT TTL! */
int nrrs, rrsz; /* nrrs is 0 if an error occurs */
union {
void *untyped;
unsigned char *bytes;
char *(*str); /* ns_raw, cname, ptr, ptr_raw */
adns_rr_intstr *(*manyistr); /* txt (list of strings ends with i=-1, str=0) */
adns_rr_addr *addr; /* addr */
struct in_addr *inaddr; /* a */
#ifdef IPV6
struct in6_addr * in6addr; /* aaaa for IPv6 */
#endif
adns_rr_hostaddr *hostaddr; /* ns */
adns_rr_intstrpair *intstrpair; /* hinfo */
adns_rr_strpair *strpair; /* rp, rp_raw */
adns_rr_inthostaddr *inthostaddr; /* mx */
adns_rr_intstr *intstr; /* mx_raw */
adns_rr_soa *soa; /* soa, soa_raw */
} rrs;
} adns_answer;
/* Memory management:
* adns_state and adns_query are actually pointers to malloc'd state;
* On submission questions are copied, including the owner domain;
* Answers are malloc'd as a single piece of memory; pointers in the
* answer struct point into further memory in the answer.
* query_io:
* Must always be non-null pointer;
* If *query_io is 0 to start with then any query may be returned;
* If *query_io is !0 adns_query then only that query may be returned.
* If the call is successful, *query_io, *answer_r, and *context_r
* will all be set.
* Errors:
* Return values are 0 or an errno value.
*
* For _init, _init_strcfg, _submit and _synchronous, system errors
* (eg, failure to create sockets, malloc failure, etc.) return errno
* values.
*
* For _wait and _check failures are reported in the answer
* structure, and only 0, ESRCH or (for _check) EAGAIN is
* returned: if no (appropriate) requests are done adns_check returns
* EAGAIN; if no (appropriate) requests are outstanding both
* adns_query and adns_wait return ESRCH.
*
* Additionally, _wait can return EINTR if you set adns_if_eintr.
*
* All other errors (nameserver failure, timed out connections, &c)
* are returned in the status field of the answer. After a
* successful _wait or _check, if status is nonzero then nrrs will be
* 0, otherwise it will be >0. type will always be the type
* requested.
*/
int adns_init(adns_state *newstate_r, adns_initflags flags,
FBFILE *diagfile /*0=>stderr*/);
int adns_init_strcfg(adns_state *newstate_r, adns_initflags flags,
FBFILE *diagfile /*0=>discard*/, const char *configtext);
/* Configuration:
* adns_init reads /etc/resolv.conf, which is expected to be (broadly
* speaking) in the format expected by libresolv, and then
* /etc/resolv-adns.conf if it exists. adns_init_strcfg is instead
* passed a string which is interpreted as if it were the contents of
* resolv.conf or resolv-adns.conf. In general, configuration which
* is set later overrides any that is set earlier.
*
* Standard directives understood in resolv[-adns].conf:
*
* nameserver <address>
* Must be followed by the IP address of a nameserver. Several
* nameservers may be specified, and they will be tried in the order
* found. There is a compiled in limit, currently 5, on the number
* of nameservers. (libresolv supports only 3 nameservers.)
*
* search <domain> ...
* Specifies the search list for queries which specify
* adns_qf_search. This is a list of domains to append to the query
* domain. The query domain will be tried as-is either before all
* of these or after them, depending on the ndots option setting
* (see below).
*
* domain <domain>
* This is present only for backward compatibility with obsolete
* versions of libresolv. It should not be used, and is interpreted
* by adns as if it were `search' - note that this is subtly
* different to libresolv's interpretation of this directive.
*
* sortlist <addr>/<mask> ...
* Should be followed by a sequence of IP-address and netmask pairs,
* separated by spaces. They may be specified as
* eg. 172.30.206.0/24 or 172.30.206.0/255.255.255.0. Currently up
* to 15 pairs may be specified (but note that libresolv only
* supports up to 10).
*
* options
* Should followed by one or more options, separated by spaces.
* Each option consists of an option name, followed by optionally
* a colon and a value. Options are listed below.
*
* Non-standard directives understood in resolv[-adns].conf:
*
* clearnameservers
* Clears the list of nameservers, so that further nameserver lines
* start again from the beginning.
*
* include <filename>
* The specified file will be read.
*
* Additionally, adns will ignore lines in resolv[-adns].conf which
* start with a #.
*
* Standard options understood:
*
* debug
* Enables debugging output from the resolver, which will be written
* to stderr.
*
* ndots:<count>
* Affects whether queries with adns_qf_search will be tried first
* without adding domains from the searchlist, or whether the bare
* query domain will be tried last. Queries which contain at least
* <count> dots will be tried bare first. The default is 1.
*
* Non-standard options understood:
*
* adns_checkc:none
* adns_checkc:entex
* adns_checkc:freq
* Changes the consistency checking frequency; this overrides the
* setting of adns_if_check_entex, adns_if_check_freq, or neither,
* in the flags passed to adns_init.
*
* There are a number of environment variables which can modify the
* behaviour of adns. They take effect only if adns_init is used, and
* the caller of adns_init can disable them using adns_if_noenv. In
* each case there is both a FOO and an ADNS_FOO; the latter is
* interpreted later so that it can override the former. Unless
* otherwise stated, environment variables are interpreted after
* resolv[-adns].conf are read, in the order they are listed here.
*
* RES_CONF, ADNS_RES_CONF
* A filename, whose contets are in the format of resolv.conf.
*
* RES_CONF_TEXT, ADNS_RES_CONF_TEXT
* A string in the format of resolv.conf.
*
* RES_OPTIONS, ADNS_RES_OPTIONS
* These are parsed as if they appeared in the `options' line of a
* resolv.conf. In addition to being parsed at this point in the
* sequence, they are also parsed at the very beginning before
* resolv.conf or any other environment variables are read, so that
* any debug option can affect the processing of the configuration.
*
* LOCALDOMAIN, ADNS_LOCALDOMAIN
* These are interpreted as if their contents appeared in a `search'
* line in resolv.conf.
*/
int adns_synchronous(adns_state ads,
const char *owner,
adns_rrtype type,
adns_queryflags flags,
adns_answer **answer_r);
/* NB: if you set adns_if_noautosys then _submit and _check do not
* make any system calls; you must use some of the asynch-io event
* processing functions to actually get things to happen.
*/
int adns_submit(adns_state ads,
const char *owner,
adns_rrtype type,
adns_queryflags flags,
void *context,
adns_query *query_r);
/* The owner should be quoted in master file format. */
int adns_check(adns_state ads,
adns_query *query_io,
adns_answer **answer_r,
void **context_r);
int adns_wait(adns_state ads,
adns_query *query_io,
adns_answer **answer_r,
void **context_r);
/* same as adns_wait but uses poll(2) internally */
int adns_wait_poll(adns_state ads,
adns_query *query_io,
adns_answer **answer_r,
void **context_r);
void adns_cancel(adns_query query);
/* The adns_query you get back from _submit is valid (ie, can be
* legitimately passed into adns functions) until it is returned by
* adns_check or adns_wait, or passed to adns_cancel. After that it
* must not be used. You can rely on it not being reused until the
* first adns_submit or _transact call using the same adns_state after
* it became invalid, so you may compare it for equality with other
* query handles until you next call _query or _transact.
*
* _submit and _synchronous return ENOSYS if they don't understand the
* query type.
*/
int adns_submit_reverse(adns_state ads,
const struct sockaddr *addr,
adns_rrtype type,
adns_queryflags flags,
void *context,
adns_query *query_r);
/* type must be _r_ptr or _r_ptr_raw. _qf_search is ignored.
* addr->sa_family must be AF_INET or AF_INET6 or you get ENOSYS.
*/
int adns_submit_reverse_ip6(adns_state ads,
const struct sockaddr *addr,
const char *rzone,
adns_rrtype type,
adns_queryflags flags,
void *context,
adns_query *query_r);
/* For ip6.int style reverse zones */
int adns_submit_reverse_any(adns_state ads,
const struct sockaddr *addr,
const char *rzone,
adns_rrtype type,
adns_queryflags flags,
void *context,
adns_query *query_r);
/* For RBL-style reverse `zone's; look up
* <reversed-address>.<zone>
* Any type is allowed. _qf_search is ignored.
* addr->sa_family must be AF_INET or you get ENOSYS.
*/
void adns_finish(adns_state ads);
/* You may call this even if you have queries outstanding;
* they will be cancelled.
*/
void adns_forallqueries_begin(adns_state ads);
adns_query adns_forallqueries_next(adns_state ads, void **context_r);
/* Iterator functions, which you can use to loop over the outstanding
* (submitted but not yet successfuly checked/waited) queries.
*
* You can only have one iteration going at once. You may call _begin
* at any time; after that, an iteration will be in progress. You may
* only call _next when an iteration is in progress - anything else
* may coredump. The iteration remains in progress until _next
* returns 0, indicating that all the queries have been walked over,
* or ANY other adns function is called with the same adns_state (or a
* query in the same adns_state). There is no need to explicitly
* finish an iteration.
*
* context_r may be 0. *context_r may not be set when _next returns 0.
*/
void adns_checkconsistency(adns_state ads, adns_query qu);
/* Checks the consistency of adns's internal data structures.
* If any error is found, the program will abort().
* You may pass 0 for qu; if you pass non-null then additional checks
* are done to make sure that qu is a valid query.
*/
/*
* Example expected/legal calling sequence for submit/check/wait:
* adns_init
* adns_submit 1
* adns_submit 2
* adns_submit 3
* adns_wait 1
* adns_check 3 -> EAGAIN
* adns_wait 2
* adns_wait 3
* ....
* adns_finish
*/
/*
* Entrypoints for generic asynch io:
* (these entrypoints are not very useful except in combination with *
* some of the other I/O model calls which can tell you which fds to
* be interested in):
*
* Note that any adns call may cause adns to open and close fds, so
* you must call beforeselect or beforepoll again just before
* blocking, or you may not have an up-to-date list of it's fds.
*/
int adns_processany(adns_state ads);
/* Gives adns flow-of-control for a bit. This will never block, and
* can be used with any threading/asynch-io model. If some error
* occurred which might cause an event loop to spin then the errno
* value is returned.
*/
int adns_processreadable(adns_state ads, int fd, const struct timeval *now);
int adns_processwriteable(adns_state ads, int fd, const struct timeval *now);
int adns_processexceptional(adns_state ads, int fd, const struct timeval *now);
/* Gives adns flow-of-control so that it can process incoming data
* from, or send outgoing data via, fd. Very like _processany. If it
* returns zero then fd will no longer be readable or writeable
* (unless of course more data has arrived since). adns will _only_
* use that fd and only in the manner specified, regardless of whether
* adns_if_noautosys was specified.
*
* adns_processexceptional should be called when select(2) reports an
* exceptional condition, or poll(2) reports POLLPRI.
*
* It is fine to call _processreabable or _processwriteable when the
* fd is not ready, or with an fd that doesn't belong to adns; it will
* then just return 0.
*
* If some error occurred which might prevent an event loop to spin
* then the errno value is returned.
*/
void adns_processtimeouts(adns_state ads, const struct timeval *now);
/* Gives adns flow-of-control so that it can process any timeouts
* which might have happened. Very like _processreadable/writeable.
*
* now may be 0; if it isn't, *now must be the current time, recently
* obtained from gettimeofday.
*/
void adns_firsttimeout(adns_state ads,
struct timeval **tv_mod, struct timeval *tv_buf,
struct timeval now);
/* Asks adns when it would first like the opportunity to time
* something out. now must be the current time, from gettimeofday.
*
* If tv_mod points to 0 then tv_buf must be non-null, and
* _firsttimeout will fill in *tv_buf with the time until the first
* timeout, and make *tv_mod point to tv_buf. If adns doesn't have
* anything that might need timing out it will leave *tv_mod as 0.
*
* If *tv_mod is not 0 then tv_buf is not used. adns will update
* *tv_mod if it has any earlier timeout, and leave it alone if it
* doesn't.
*
* This call will not actually do any I/O, or change the fds that adns
* is using. It always succeeds and never blocks.
*/
void adns_globalsystemfailure(adns_state ads);
/* If serious problem(s) happen which globally affect your ability to
* interact properly with adns, or adns's ability to function
* properly, you or adns can call this function.
*
* All currently outstanding queries will be made to fail with
* adns_s_systemfail, and adns will close any stream sockets it has
* open.
*
* This is used by adns, for example, if gettimeofday() fails.
* Without this the program's event loop might start to spin !
*
* This call will never block.
*/
/*
* Entrypoints for select-loop based asynch io:
*/
#if 0
void adns_beforeselect(adns_state ads, int *maxfd, fd_set *readfds,
fd_set *writefds, fd_set *exceptfds,
struct timeval **tv_mod, struct timeval *tv_buf,
const struct timeval *now);
/* Find out file descriptors adns is interested in, and when it would
* like the opportunity to time something out. If you do not plan to
* block then tv_mod may be 0. Otherwise, tv_mod and tv_buf are as
* for adns_firsttimeout. readfds, writefds, exceptfds and maxfd_io may
* not be 0.
*
* If now is not 0 then this will never actually do any I/O, or change
* the fds that adns is using or the timeouts it wants. In any case
* it won't block, and it will set the timeout to zero if a query
* finishes in _beforeselect.
*/
void adns_afterselect(adns_state ads, int maxfd, const fd_set *readfds,
const fd_set *writefds, const fd_set *exceptfds,
const struct timeval *now);
/* Gives adns flow-of-control for a bit; intended for use after
* select. This is just a fancy way of calling adns_processreadable/
* writeable/timeouts as appropriate, as if select had returned the
* data being passed. Always succeeds.
*/
#endif
/*
* Example calling sequence:
*
* adns_init _noautosys
* loop {
* adns_beforeselect
* select
* adns_afterselect
* ...
* adns_submit / adns_check
* ...
* }
*/
/*
* Entrypoints for poll-loop based asynch io:
*/
struct adns_pollfd;
/* In case your system doesn't have it or you forgot to include
* <sys/poll.h>, to stop the following declarations from causing
* problems. If your system doesn't have poll then the following
* entrypoints will not be defined in libadns. Sorry !
*/
int adns_beforepoll(adns_state ads, struct adns_pollfd *fds, int *nfds_io, int *timeout_io,
const struct timeval *now);
/* Finds out which fd's adns is interested in, and when it would like
* to be able to time things out. This is in a form suitable for use
* with poll(2).
*
* On entry, usually fds should point to at least *nfds_io structs.
* adns will fill up to that many structs will information for poll,
* and record in *nfds_io how many structs it filled. If it wants to
* listen for more structs then *nfds_io will be set to the number
* required and _beforepoll will return ERANGE.
*
* You may call _beforepoll with fds==0 and *nfds_io 0, in which case
* adns will fill in the number of fds that it might be interested in
* in *nfds_io, and always return either 0 (if it is not interested in
* any fds) or ERANGE (if it is).
*
* NOTE that (unless now is 0) adns may acquire additional fds
* from one call to the next, so you must put adns_beforepoll in a
* loop, rather than assuming that the second call (with the buffer
* size requested by the first) will not return ERANGE.
*
* adns only ever sets POLLIN, POLLOUT and POLLPRI in its adns_pollfd
* structs, and only ever looks at those bits. POLLPRI is required to
* detect TCP Urgent Data (which should not be used by a DNS server)
* so that adns can know that the TCP stream is now useless.
*
* In any case, *timeout_io should be a timeout value as for poll(2),
* which adns will modify downwards as required. If the caller does
* not plan to block then *timeout_io should be 0 on entry, or
* alternatively, timeout_io may be 0. (Alternatively, the caller may
* use _beforeselect with timeout_io==0 to find out about file
* descriptors, and use _firsttimeout is used to find out when adns
* might want to time something out.)
*
* adns_beforepoll will return 0 on success, and will not fail for any
* reason other than the fds buffer being too small (ERANGE).
*
* This call will never actually do any I/O. If you supply the
* current time it will not change the fds that adns is using or the
* timeouts it wants.
*
* In any case this call won't block.
*/
#define ADNS_POLLFDS_RECOMMENDED 2
/* If you allocate an fds buf with at least RECOMMENDED entries then
* you are unlikely to need to enlarge it. You are recommended to do
* so if it's convenient. However, you must be prepared for adns to
* require more space than this.
*/
void adns_afterpoll(adns_state ads, const struct adns_pollfd *fds, int nfds,
const struct timeval *now);
/* Gives adns flow-of-control for a bit; intended for use after
* poll(2). fds and nfds should be the results from poll(). pollfd
* structs mentioning fds not belonging to adns will be ignored.
*/
adns_status adns_rr_info(adns_rrtype type,
const char **rrtname_r, const char **fmtname_r,
int *len_r,
const void *datap, char **data_r);
/*
* Get information about a query type, or convert reply data to a
* textual form. type must be specified, and the official name of the
* corresponding RR type will be returned in *rrtname_r, and
* information about the processing style in *fmtname_r. The length
* of the table entry in an answer for that type will be returned in
* in *len_r. Any or all of rrtname_r, fmtname_r and len_r may be 0.
* If fmtname_r is non-null then *fmtname_r may be null on return,
* indicating that no special processing is involved.
*
* data_r be must be non-null iff datap is. In this case *data_r will
* be set to point to a string pointing to a representation of the RR
* data in master file format. (The owner name, timeout, class and
* type will not be present - only the data part of the RR.) The
* memory will have been obtained from malloc() and must be freed by
* the caller.
*
* Usually this routine will succeed. Possible errors include:
* adns_s_nomemory
* adns_s_rrtypeunknown
* adns_s_invaliddata (*datap contained garbage)
* If an error occurs then no memory has been allocated,
* and *rrtname_r, *fmtname_r, *len_r and *data_r are undefined.
*
* There are some adns-invented data formats which are not official
* master file formats. These include:
*
* Mailboxes if __qtf_mail822: these are just included as-is.
*
* Addresses (adns_rr_addr): these may be of pretty much any type.
* The representation is in two parts: first, a word for the address
* family (ie, in AF_XXX, the XXX), and then one or more items for the
* address itself, depending on the format. For an IPv4 address the
* syntax is INET followed by the dotted quad (from inet_ntoa).
* Currently only IPv4 is supported.
*
* Text strings (as in adns_rr_txt) appear inside double quotes, and
* use \" and \\ to represent " and \, and \xHH to represent
* characters not in the range 32-126.
*
* Hostname with addresses (adns_rr_hostaddr): this consists of the
* hostname, as usual, followed by the adns_status value, as an
* abbreviation, and then a descriptive string (encoded as if it were
* a piece of text), for the address lookup, followed by zero or more
* addresses enclosed in ( and ). If the result was a temporary
* failure, then a single ? appears instead of the ( ). If the
* result was a permanent failure then an empty pair of parentheses
* appears (which a space in between). For example, one of the NS
* records for greenend.org.uk comes out like
* ns.chiark.greenend.org.uk ok "OK" ( INET 195.224.76.132 )
* an MX referring to a nonexistent host might come out like:
* 50 sun2.nsfnet-relay.ac.uk nxdomain "No such domain" ( )
* and if nameserver information is not available you might get:
* dns2.spong.dyn.ml.org timeout "DNS query timed out" ?
*/
const char *adns_strerror(adns_status st);
const char *adns_errabbrev(adns_status st);
const char *adns_errtypeabbrev(adns_status st);
/* Like strerror but for adns_status values. adns_errabbrev returns
* the abbreviation of the error - eg, for adns_s_timeout it returns
* "timeout". adns_errtypeabbrev returns the abbreviation of the
* error class: ie, for values up to adns_s_max_XXX it will return the
* string XXX. You MUST NOT call these functions with status values
* not returned by the same adns library.
*/
int adns__rereadconfig(adns_state st);
#endif

220
adns/check.c Normal file
View file

@ -0,0 +1,220 @@
/*
* check.c
* - consistency checks
*/
/*
* This file is
* Copyright (C) 1997-1999 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999-2000 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
* $Id: check.c,v 1.1 2002/08/13 14:35:04 fishwaldo Exp $
*/
#include "stdinc.h"
#include "fileio.h"
#include "internal.h"
/* This crap is needed to make it compile on OS X
* Leave it to apple to take a perfectly good preprocessor and fuck it
* up.
*/
#define unused_arg /**/
void adns_checkconsistency(adns_state ads, adns_query qu) {
adns__consistency(ads,qu,cc_user);
}
#define DLIST_CHECK(list, nodevar, part, body) \
if ((list).head) { \
assert(! (list).head->part back); \
for ((nodevar)= (list).head; (nodevar); (nodevar)= (nodevar)->part next) { \
assert((nodevar)->part next \
? (nodevar) == (nodevar)->part next->part back \
: (nodevar) == (list).tail); \
body \
} \
}
#define DLIST_CHECK_PARTLESS(list, nodevar, body) \
if ((list).head) { \
assert(! (list).head->back); \
for ((nodevar)= (list).head; (nodevar); (nodevar)= (nodevar)->next) { \
assert((nodevar)->next \
? (nodevar) == (nodevar)->next->back \
: (nodevar) == (list).tail); \
body \
} \
}
#define DLIST_ASSERTON(node, nodevar, list, part) \
do { \
for ((nodevar)= (list).head; \
(nodevar) != (node); \
(nodevar)= (nodevar)->part next) { \
assert((nodevar)); \
} \
} while(0)
static void checkc_query_alloc(adns_state ads, adns_query qu) {
allocnode *an;
DLIST_CHECK_PARTLESS(qu->allocations, an, {
});
}
static void checkc_query(adns_state ads, adns_query qu) {
adns_query child;
assert(qu->udpnextserver < ads->nservers);
assert(!(qu->udpsent & (~0UL << ads->nservers)));
assert(qu->search_pos <= ads->nsearchlist);
if (qu->parent) DLIST_ASSERTON(qu, child, qu->parent->children, siblings.);
}
static void checkc_notcpbuf(adns_state ads) {
assert(!ads->tcpsend.used);
assert(!ads->tcprecv.used);
assert(!ads->tcprecv_skip);
}
static void checkc_global(adns_state ads) {
int i;
assert(ads->udpsocket >= 0);
for (i=0; i<ads->nsortlist; i++)
assert(!(ads->sortlist[i].base.s_addr & ~ads->sortlist[i].mask.s_addr));
assert(ads->tcpserver >= 0 && ads->tcpserver < ads->nservers);
switch (ads->tcpstate) {
case server_connecting:
assert(ads->tcpsocket >= 0);
checkc_notcpbuf(ads);
break;
case server_disconnected:
case server_broken:
assert(ads->tcpsocket == -1);
checkc_notcpbuf(ads);
break;
case server_ok:
assert(ads->tcpsocket >= 0);
assert(ads->tcprecv_skip <= ads->tcprecv.used);
break;
default:
assert(!"ads->tcpstate value");
}
assert(ads->searchlist || !ads->nsearchlist);
}
static void checkc_queue_udpw(adns_state ads) {
adns_query qu;
DLIST_CHECK_PARTLESS(ads->udpw, qu, {
assert(qu->state==query_tosend);
assert(qu->retries <= UDPMAXRETRIES);
assert(qu->udpsent);
assert(!qu->children.head && !qu->children.tail);
checkc_query(ads,qu);
checkc_query_alloc(ads,qu);
});
}
static void checkc_queue_tcpw(adns_state ads) {
adns_query qu;
DLIST_CHECK_PARTLESS(ads->tcpw, qu, {
assert(qu->state==query_tcpw);
assert(!qu->children.head && !qu->children.tail);
assert(qu->retries <= ads->nservers+1);
checkc_query(ads,qu);
checkc_query_alloc(ads,qu);
});
}
static void checkc_queue_childw(adns_state ads) {
adns_query parent, child;
DLIST_CHECK_PARTLESS(ads->childw, parent, {
assert(parent->state == query_childw);
assert(parent->children.head);
DLIST_CHECK(parent->children, child, siblings., {
assert(child->parent == parent);
assert(child->state != query_done);
});
checkc_query(ads,parent);
checkc_query_alloc(ads,parent);
});
}
static void checkc_queue_output(adns_state ads) {
adns_query qu;
DLIST_CHECK_PARTLESS(ads->output, qu, {
assert(qu->state == query_done);
assert(!qu->children.head && !qu->children.tail);
assert(!qu->parent);
assert(!qu->allocations.head && !qu->allocations.tail);
checkc_query(ads,qu);
});
}
void adns__consistency(adns_state ads, adns_query qu, consistency_checks cc) {
adns_query search;
switch (cc) {
case cc_user:
break;
case cc_entex:
if (!(ads->iflags & adns_if_checkc_entex)) return;
break;
case cc_freq:
if ((ads->iflags & adns_if_checkc_freq) != adns_if_checkc_freq) return;
break;
default:
abort();
}
checkc_global(ads);
checkc_queue_udpw(ads);
checkc_queue_tcpw(ads);
checkc_queue_childw(ads);
checkc_queue_output(ads);
if (qu) {
switch (qu->state) {
case query_tosend:
DLIST_ASSERTON(qu, search, ads->udpw, unused_arg);
break;
case query_tcpw:
DLIST_ASSERTON(qu, search, ads->tcpw, unused_arg);
break;
case query_childw:
DLIST_ASSERTON(qu, search, ads->childw, unused_arg);
break;
case query_done:
DLIST_ASSERTON(qu, search, ads->output, unused_arg);
break;
default:
assert(!"specific query state");
}
}
}

22
adns/descrip.mms Normal file
View file

@ -0,0 +1,22 @@
# MMS/MMK Makefile for OpenVMS
# Copyright (c) 2001 Edward Brocklesby
#
# Usage:
# $ SET DEF [.IRCD-HYBRID-7.src]
# $ EDIT [-.include]config.h
# < change settings in config.h appropriately >
# $ COPY [.include]setup.h_vms [.include]setup.h
# $ MMS IRCD.EXE
#
# $Id: descrip.mms,v 1.1 2002/08/13 14:35:04 fishwaldo Exp $
CC= CC
CFLAGS= /INCLUDE_DIRECTORY=([-.INCLUDE],[])/STANDARD=ISOC94
LDFLAGS=
OBJECTS= CHECK,GENERAL,QUERY,SETUP,TYPES,EVENT,PARSE,REPLY,TRANSMIT
ALL : ADNS.OLB($(OBJECTS))
CLEAN :
DELETE *.OLB;*

60
adns/dlist.h Normal file
View file

@ -0,0 +1,60 @@
/*
* dlist.h
* - macros for handling doubly linked lists
*/
/*
* This file is
* Copyright (C) 1997-1999 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
* $Id: dlist.h,v 1.1 2002/08/13 14:35:04 fishwaldo Exp $
*/
#ifndef ADNS_DLIST_H_INCLUDED
#define ADNS_DLIST_H_INCLUDED
/* More strange shit for OS X and its b0rked C compiler */
#define unused_arg /**/
#define ADNS_LIST_INIT(flist) ((flist).head= (flist).tail= 0)
#define LINK_INIT(flink) ((flink).next= (flink).back= 0)
#define LIST_UNLINK_PART(flist,node,part) \
do { \
if ((node)->part back) (node)->part back->part next= (node)->part next; \
else (flist).head= (node)->part next; \
if ((node)->part next) (node)->part next->part back= (node)->part back; \
else (flist).tail= (node)->part back; \
} while(0)
#define LIST_LINK_TAIL_PART(flist,node,part) \
do { \
(node)->part next= 0; \
(node)->part back= (flist).tail; \
if ((flist).tail) (flist).tail->part next= (node); else (flist).head= (node); \
(flist).tail= (node); \
} while(0)
#define LIST_UNLINK(flist,node) LIST_UNLINK_PART(flist,node,unused_arg)
#define LIST_LINK_TAIL(flist,node) LIST_LINK_TAIL_PART(flist,node, unused_arg)
#endif

723
adns/event.c Normal file
View file

@ -0,0 +1,723 @@
/*
* event.c
* - event loop core
* - TCP connection management
* - user-visible check/wait and event-loop-related functions
*/
/*
* This file is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999-2000 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
* $Id: event.c,v 1.1 2002/08/13 14:35:05 fishwaldo Exp $
*/
#include "stdinc.h"
#include "fileio.h"
#include "s_bsd.h"
#include "internal.h"
#include "memory.h"
#include "tvarith.h"
#include "irc_string.h"
#include "memory.h"
#include "adns.h"
/* TCP connection management. */
static void tcp_close(adns_state ads) {
int serv;
serv= ads->tcpserver;
fd_close(ads->tcpsocket);
ads->tcpsocket= -1;
ads->tcprecv.used= ads->tcprecv_skip= ads->tcpsend.used= 0;
}
void adns__tcp_broken(adns_state ads, const char *what, const char *why) {
int serv;
adns_query qu;
assert(ads->tcpstate == server_connecting || ads->tcpstate == server_ok);
serv= ads->tcpserver;
if (what) adns__warn(ads,serv,0,"TCP connection failed: %s: %s",what,why);
if (ads->tcpstate == server_connecting) {
/* Counts as a retry for all the queries waiting for TCP. */
for (qu= ads->tcpw.head; qu; qu= qu->next)
qu->retries++;
}
tcp_close(ads);
ads->tcpstate= server_broken;
ads->tcpserver= (serv+1)%ads->nservers;
}
static void tcp_connected(adns_state ads, struct timeval now) {
adns_query qu, nqu;
adns__debug(ads,ads->tcpserver,0,"TCP connected");
ads->tcpstate= server_ok;
for (qu= ads->tcpw.head; qu && ads->tcpstate == server_ok; qu= nqu) {
nqu= qu->next;
assert(qu->state == query_tcpw);
adns__querysend_tcp(qu,now);
}
}
void adns__tcp_tryconnect(adns_state ads, struct timeval now) {
int r, fd, tries;
struct sockaddr_in addr;
for (tries=0; tries<ads->nservers; tries++) {
switch (ads->tcpstate) {
case server_connecting:
case server_ok:
case server_broken:
return;
case server_disconnected:
break;
default:
abort();
}
assert(!ads->tcpsend.used);
assert(!ads->tcprecv.used);
assert(!ads->tcprecv_skip);
fd= comm_open(AF_INET, SOCK_STREAM, 0, "adns TCP socket");
if (fd<0) {
adns__diag(ads,-1,0,"cannot create TCP socket: %s",strerror(errno));
return;
}
r= adns__setnonblock(ads,fd);
if (r) {
adns__diag(ads,-1,0,"cannot make TCP socket nonblocking: %s",strerror(r));
fd_close(fd);
return;
}
memset(&addr,0,sizeof(addr));
addr.sin_family= AF_INET;
addr.sin_port= htons(DNS_PORT);
addr.sin_addr= ads->servers[ads->tcpserver].addr;
r= connect(fd,(const struct sockaddr*)&addr,sizeof(addr));
ads->tcpsocket= fd;
ads->tcpstate= server_connecting;
if (r==0) { tcp_connected(ads,now); return; }
if (errno == EWOULDBLOCK || errno == EINPROGRESS) {
ads->tcptimeout= now;
timevaladd(&ads->tcptimeout,TCPCONNMS);
return;
}
adns__tcp_broken(ads,"connect",strerror(errno));
ads->tcpstate= server_disconnected;
}
}
/* Timeout handling functions. */
void adns__must_gettimeofday(adns_state ads, const struct timeval **now_io,
struct timeval *tv_buf) {
const struct timeval *now;
int r;
now= *now_io;
if (now) return;
r= gettimeofday(tv_buf,0); if (!r) { *now_io= tv_buf; return; }
adns__diag(ads,-1,0,"gettimeofday failed: %s",strerror(errno));
adns_globalsystemfailure(ads);
return;
}
static void inter_immed(struct timeval **tv_io, struct timeval *tvbuf) {
struct timeval *rbuf;
if (!tv_io) return;
rbuf= *tv_io;
if (!rbuf) { *tv_io= rbuf= tvbuf; }
timerclear(rbuf);
}
static void inter_maxto(struct timeval **tv_io, struct timeval *tvbuf,
struct timeval maxto) {
struct timeval *rbuf;
if (!tv_io) return;
rbuf= *tv_io;
if (!rbuf) {
*tvbuf= maxto; *tv_io= tvbuf;
} else {
if (timercmp(rbuf,&maxto,>)) *rbuf= maxto;
}
/*fprintf(stderr,"inter_maxto maxto=%ld.%06ld result=%ld.%06ld\n",
maxto.tv_sec,maxto.tv_usec,(**tv_io).tv_sec,(**tv_io).tv_usec);*/
}
static void inter_maxtoabs(struct timeval **tv_io, struct timeval *tvbuf,
struct timeval now, struct timeval maxtime) {
/* tv_io may be 0 */
ldiv_t dr;
/*fprintf(stderr,"inter_maxtoabs now=%ld.%06ld maxtime=%ld.%06ld\n",
now.tv_sec,now.tv_usec,maxtime.tv_sec,maxtime.tv_usec);*/
if (!tv_io) return;
maxtime.tv_sec -= (now.tv_sec+2);
maxtime.tv_usec -= (now.tv_usec-2000000);
dr= ldiv(maxtime.tv_usec,1000000);
maxtime.tv_sec += dr.quot;
maxtime.tv_usec -= dr.quot*1000000;
if (maxtime.tv_sec<0) timerclear(&maxtime);
inter_maxto(tv_io,tvbuf,maxtime);
}
static void timeouts_queue(adns_state ads, int act,
struct timeval **tv_io, struct timeval *tvbuf,
struct timeval now, struct query_queue *queue) {
adns_query qu, nqu;
for (qu= queue->head; qu; qu= nqu) {
nqu= qu->next;
if (!timercmp(&now,&qu->timeout,>)) {
inter_maxtoabs(tv_io,tvbuf,now,qu->timeout);
} else {
if (!act) { inter_immed(tv_io,tvbuf); return; }
LIST_UNLINK(*queue,qu);
if (qu->state != query_tosend) {
adns__query_fail(qu,adns_s_timeout);
} else {
adns__query_send(qu,now);
}
nqu= queue->head;
}
}
}
static void tcp_events(adns_state ads, int act,
struct timeval **tv_io, struct timeval *tvbuf,
struct timeval now) {
adns_query qu, nqu;
for (;;) {
switch (ads->tcpstate) {
case server_broken:
if (!act) { inter_immed(tv_io,tvbuf); return; }
for (qu= ads->tcpw.head; qu; qu= nqu) {
nqu= qu->next;
assert(qu->state == query_tcpw);
if (qu->retries > ads->nservers) {
LIST_UNLINK(ads->tcpw,qu);
adns__query_fail(qu,adns_s_allservfail);
}
}
ads->tcpstate= server_disconnected;
case server_disconnected: /* fall through */
if (!ads->tcpw.head) return;
if (!act) { inter_immed(tv_io,tvbuf); return; }
adns__tcp_tryconnect(ads,now);
break;
case server_ok:
if (ads->tcpw.head) return;
if (!ads->tcptimeout.tv_sec) {
assert(!ads->tcptimeout.tv_usec);
ads->tcptimeout= now;
timevaladd(&ads->tcptimeout,TCPIDLEMS);
}
case server_connecting: /* fall through */
if (!act || !timercmp(&now,&ads->tcptimeout,>)) {
inter_maxtoabs(tv_io,tvbuf,now,ads->tcptimeout);
return;
} {
/* TCP timeout has happened */
switch (ads->tcpstate) {
case server_connecting: /* failed to connect */
adns__tcp_broken(ads,"unable to make connection","timed out");
break;
case server_ok: /* idle timeout */
tcp_close(ads);
ads->tcpstate= server_disconnected;
return;
default:
abort();
}
}
break;
default:
abort();
}
}
return;
}
void adns__timeouts(adns_state ads, int act,
struct timeval **tv_io, struct timeval *tvbuf,
struct timeval now) {
timeouts_queue(ads,act,tv_io,tvbuf,now, &ads->udpw);
timeouts_queue(ads,act,tv_io,tvbuf,now, &ads->tcpw);
tcp_events(ads,act,tv_io,tvbuf,now);
}
void adns_firsttimeout(adns_state ads,
struct timeval **tv_io, struct timeval *tvbuf,
struct timeval now) {
adns__consistency(ads,0,cc_entex);
adns__timeouts(ads, 0, tv_io,tvbuf, now);
adns__consistency(ads,0,cc_entex);
}
void adns_processtimeouts(adns_state ads, const struct timeval *now) {
struct timeval tv_buf;
adns__consistency(ads,0,cc_entex);
adns__must_gettimeofday(ads,&now,&tv_buf);
if (now) adns__timeouts(ads, 1, 0,0, *now);
adns__consistency(ads,0,cc_entex);
}
/* fd handling functions. These are the top-level of the real work of
* reception and often transmission.
*/
int adns__pollfds(adns_state ads, struct adns_pollfd pollfds_buf[MAX_POLLFDS]) {
/* Returns the number of entries filled in. Always zeroes revents. */
assert(MAX_POLLFDS==2);
pollfds_buf[0].fd= ads->udpsocket;
pollfds_buf[0].events= ADNS_POLLIN;
pollfds_buf[0].revents= 0;
switch (ads->tcpstate) {
case server_disconnected:
case server_broken:
return 1;
case server_connecting:
pollfds_buf[1].events= ADNS_POLLOUT;
break;
case server_ok:
#if 0
pollfds_buf[1].events= ads->tcpsend.used ? ADNS_POLLIN|ADNS_POLLOUT|ADNS_POLLPRI : ADNS_POLLIN|ADNS_POLLPRI;
#endif
pollfds_buf[1].events= ADNS_POLLIN|ADNS_POLLOUT|ADNS_POLLPRI;
break;
default:
abort();
}
pollfds_buf[1].fd= ads->tcpsocket;
return 2;
}
int adns_processreadable(adns_state ads, int fd, const struct timeval *now) {
int want, dgramlen, r, serv, old_skip;
socklen_t udpaddrlen;
byte udpbuf[DNS_MAXUDP];
struct sockaddr_in udpaddr;
adns__consistency(ads,0,cc_entex);
switch (ads->tcpstate) {
case server_disconnected:
case server_broken:
case server_connecting:
break;
case server_ok:
if (fd != ads->tcpsocket) break;
assert(!ads->tcprecv_skip);
do {
if (ads->tcprecv.used >= ads->tcprecv_skip+2) {
dgramlen= ((ads->tcprecv.buf[ads->tcprecv_skip]<<8) |
ads->tcprecv.buf[ads->tcprecv_skip+1]);
if (ads->tcprecv.used >= ads->tcprecv_skip+2+dgramlen) {
old_skip= ads->tcprecv_skip;
ads->tcprecv_skip += 2+dgramlen;
adns__procdgram(ads, ads->tcprecv.buf+old_skip+2,
dgramlen, ads->tcpserver, 1,*now);
continue;
} else {
want= 2+dgramlen;
}
} else {
want= 2;
}
ads->tcprecv.used -= ads->tcprecv_skip;
memmove(ads->tcprecv.buf,ads->tcprecv.buf+ads->tcprecv_skip,ads->tcprecv.used);
ads->tcprecv_skip= 0;
if (!adns__vbuf_ensure(&ads->tcprecv,want)) { r= ENOMEM; goto xit; }
assert(ads->tcprecv.used <= ads->tcprecv.avail);
if (ads->tcprecv.used == ads->tcprecv.avail) continue;
r= read(ads->tcpsocket,
ads->tcprecv.buf+ads->tcprecv.used,
ads->tcprecv.avail-ads->tcprecv.used);
if (r>0) {
ads->tcprecv.used+= r;
} else {
if (r) {
if (errno==EAGAIN || errno==EWOULDBLOCK) { r= 0; goto xit; }
if (errno==EINTR) continue;
if (errno_resources(errno)) { r= errno; goto xit; }
}
adns__tcp_broken(ads,"read",r?strerror(errno):"closed");
}
} while (ads->tcpstate == server_ok);
r= 0; goto xit;
default:
abort();
}
if (fd == ads->udpsocket) {
for (;;) {
udpaddrlen= sizeof(udpaddr);
r= recvfrom(ads->udpsocket,udpbuf,sizeof(udpbuf),0,
(struct sockaddr*)&udpaddr,&udpaddrlen);
if (r<0) {
if (errno == EAGAIN || errno == EWOULDBLOCK) { r= 0; goto xit; }
if (errno == EINTR) continue;
if (errno_resources(errno)) { r= errno; goto xit; }
adns__warn(ads,-1,0,"datagram receive error: %s",strerror(errno));
r= 0; goto xit;
}
if (udpaddrlen != sizeof(udpaddr)) {
adns__diag(ads,-1,0,"datagram received with wrong address length %d"
" (expected %lu)", udpaddrlen,
(unsigned long)sizeof(udpaddr));
continue;
}
if (udpaddr.sin_family != AF_INET) {
adns__diag(ads,-1,0,"datagram received with wrong protocol family"
" %u (expected %u)",udpaddr.sin_family,AF_INET);
continue;
}
if (ntohs(udpaddr.sin_port) != DNS_PORT) {
adns__diag(ads,-1,0,"datagram received from wrong port %u (expected %u)",
ntohs(udpaddr.sin_port),DNS_PORT);
continue;
}
for (serv= 0;
serv < ads->nservers &&
ads->servers[serv].addr.s_addr != udpaddr.sin_addr.s_addr;
serv++);
if (serv >= ads->nservers) {
adns__warn(ads,-1,0,"datagram received from unknown nameserver %s",
inetntoa((char *)&udpaddr.sin_addr));
continue;
}
adns__procdgram(ads,udpbuf,r,serv,0,*now);
}
}
r= 0;
xit:
adns__consistency(ads,0,cc_entex);
return r;
}
int adns_processwriteable(adns_state ads, int fd, const struct timeval *now) {
int r;
adns__consistency(ads,0,cc_entex);
switch (ads->tcpstate) {
case server_disconnected:
case server_broken:
break;
case server_connecting:
if (fd != ads->tcpsocket) break;
assert(ads->tcprecv.used==0);
assert(ads->tcprecv_skip==0);
for (;;) {
if (!adns__vbuf_ensure(&ads->tcprecv,1)) { r= ENOMEM; goto xit; }
r= read(ads->tcpsocket,&ads->tcprecv.buf,1);
if (r==0 || (r<0 && (errno==EAGAIN || errno==EWOULDBLOCK))) {
tcp_connected(ads,*now);
r= 0; goto xit;
}
if (r>0) {
adns__tcp_broken(ads,"connect/read","sent data before first request");
r= 0; goto xit;
}
if (errno==EINTR) continue;
if (errno_resources(errno)) { r= errno; goto xit; }
adns__tcp_broken(ads,"connect/read",strerror(errno));
r= 0; goto xit;
} /* not reached */
case server_ok:
if (fd != ads->tcpsocket) break;
while (ads->tcpsend.used) {
r= write(ads->tcpsocket,ads->tcpsend.buf,ads->tcpsend.used);
if (r<0) {
if (errno==EINTR) continue;
if (errno==EAGAIN || errno==EWOULDBLOCK) { r= 0; goto xit; }
if (errno_resources(errno)) { r= errno; goto xit; }
adns__tcp_broken(ads,"write",strerror(errno));
r= 0; goto xit;
} else if (r>0) {
ads->tcpsend.used -= r;
memmove(ads->tcpsend.buf,ads->tcpsend.buf+r,ads->tcpsend.used);
}
}
r= 0;
goto xit;
default:
abort();
}
r= 0;
xit:
adns__consistency(ads,0,cc_entex);
return r;
}
int adns_processexceptional(adns_state ads, int fd, const struct timeval *now) {
adns__consistency(ads,0,cc_entex);
switch (ads->tcpstate) {
case server_disconnected:
case server_broken:
break;
case server_connecting:
case server_ok:
if (fd != ads->tcpsocket) break;
adns__tcp_broken(ads,"poll/select","exceptional condition detected");
break;
default:
abort();
}
adns__consistency(ads,0,cc_entex);
return 0;
}
static void fd_event(adns_state ads, int fd,
int revent, int pollflag,
int maxfd, const fd_set *fds,
int (*func)(adns_state, int fd, const struct timeval *now),
struct timeval now, int *r_r) {
int r;
if (!(revent & pollflag)) return;
if (fds && !(fd<maxfd && FD_ISSET(fd,fds))) return;
r= func(ads,fd,&now);
if (r) {
if (r_r) {
*r_r= r;
} else {
adns__diag(ads,-1,0,"process fd failed after select: %s",strerror(errno));
adns_globalsystemfailure(ads);
}
}
}
void adns__fdevents(adns_state ads,
const struct adns_pollfd *pollfds, int npollfds,
int maxfd, const fd_set *readfds,
const fd_set *writefds, const fd_set *exceptfds,
struct timeval now, int *r_r) {
int i, fd, revents;
for (i=0; i<npollfds; i++) {
fd= pollfds[i].fd;
if (fd >= maxfd) maxfd= fd+1;
revents= pollfds[i].revents;
fd_event(ads,fd, revents,ADNS_POLLIN, maxfd,readfds, adns_processreadable,now,r_r);
fd_event(ads,fd, revents,ADNS_POLLOUT, maxfd,writefds, adns_processwriteable,now,r_r);
fd_event(ads,fd, revents,ADNS_POLLPRI, maxfd,exceptfds, adns_processexceptional,now,r_r);
}
}
/* Wrappers for select(2). */
#if 0
void adns_beforeselect(adns_state ads, int *maxfd_io, fd_set *readfds_io,
fd_set *writefds_io, fd_set *exceptfds_io,
struct timeval **tv_mod, struct timeval *tv_tobuf,
const struct timeval *now) {
struct timeval tv_nowbuf;
struct adns_pollfd pollfds[MAX_POLLFDS];
int i, fd, maxfd, npollfds;
adns__consistency(ads,0,cc_entex);
if (tv_mod && (!*tv_mod || (*tv_mod)->tv_sec || (*tv_mod)->tv_usec)) {
/* The caller is planning to sleep. */
adns__must_gettimeofday(ads,&now,&tv_nowbuf);
if (!now) { inter_immed(tv_mod,tv_tobuf); goto xit; }
adns__timeouts(ads, 0, tv_mod,tv_tobuf, *now);
}
npollfds= adns__pollfds(ads,pollfds);
maxfd= *maxfd_io;
for (i=0; i<npollfds; i++) {
fd= pollfds[i].fd;
if (fd >= maxfd) maxfd= fd+1;
if (pollfds[i].events & ADNS_POLLIN) FD_SET(fd,readfds_io);
if (pollfds[i].events & ADNS_POLLOUT) FD_SET(fd,writefds_io);
if (pollfds[i].events & ADNS_POLLPRI) FD_SET(fd,exceptfds_io);
}
*maxfd_io= maxfd;
xit:
adns__consistency(ads,0,cc_entex);
}
void adns_afterselect(adns_state ads, int maxfd, const fd_set *readfds,
const fd_set *writefds, const fd_set *exceptfds,
const struct timeval *now) {
struct timeval tv_buf;
struct adns_pollfd pollfds[MAX_POLLFDS];
int npollfds, i;
adns__consistency(ads,0,cc_entex);
adns__must_gettimeofday(ads,&now,&tv_buf);
if (!now) goto xit;
adns_processtimeouts(ads,now);
npollfds= adns__pollfds(ads,pollfds);
for (i=0; i<npollfds; i++) pollfds[i].revents= ADNS_POLLIN|ADNS_POLLOUT|ADNS_POLLPRI;
adns__fdevents(ads,
pollfds,npollfds,
maxfd,readfds,writefds,exceptfds,
*now, 0);
xit:
adns__consistency(ads,0,cc_entex);
}
#endif
/* General helpful functions. */
void adns_globalsystemfailure(adns_state ads) {
adns__consistency(ads,0,cc_entex);
while (ads->udpw.head) adns__query_fail(ads->udpw.head, adns_s_systemfail);
while (ads->tcpw.head) adns__query_fail(ads->tcpw.head, adns_s_systemfail);
switch (ads->tcpstate) {
case server_connecting:
case server_ok:
adns__tcp_broken(ads,0,0);
break;
case server_disconnected:
case server_broken:
break;
default:
abort();
}
adns__consistency(ads,0,cc_entex);
}
int adns_processany(adns_state ads) {
int r, i;
struct timeval now;
struct adns_pollfd pollfds[MAX_POLLFDS];
int npollfds;
adns__consistency(ads,0,cc_entex);
r= gettimeofday(&now,0);
if (!r) adns_processtimeouts(ads,&now);
/* We just use adns__fdevents to loop over the fd's trying them.
* This seems more sensible than calling select, since we're most
* likely just to want to do a read on one or two fds anyway.
*/
npollfds= adns__pollfds(ads,pollfds);
for (i=0; i<npollfds; i++) pollfds[i].revents= pollfds[i].events & ~ADNS_POLLPRI;
adns__fdevents(ads,
pollfds,npollfds,
0,0,0,0,
now,&r);
adns__consistency(ads,0,cc_entex);
return 0;
}
void adns__autosys(adns_state ads, struct timeval now) {
if (ads->iflags & adns_if_noautosys) return;
adns_processany(ads);
}
int adns__internal_check(adns_state ads,
adns_query *query_io,
adns_answer **answer,
void **context_r) {
adns_query qu;
qu= *query_io;
if (!qu) {
if (ads->output.head) {
qu= ads->output.head;
} else if (ads->udpw.head || ads->tcpw.head) {
return EAGAIN;
} else {
return ESRCH;
}
} else {
if (qu->id>=0) return EAGAIN;
}
LIST_UNLINK(ads->output,qu);
*answer= qu->answer;
if (context_r) *context_r= qu->ctx.ext;
*query_io= qu;
MyFree(qu);
return 0;
}
#if 0
int adns_wait(adns_state ads,
adns_query *query_io,
adns_answer **answer_r,
void **context_r) {
int r, maxfd, rsel;
fd_set readfds, writefds, exceptfds;
struct timeval tvbuf, *tvp;
adns__consistency(ads,*query_io,cc_entex);
for (;;) {
r= adns__internal_check(ads,query_io,answer_r,context_r);
if (r != EAGAIN) break;
maxfd= 0; tvp= 0;
FD_ZERO(&readfds); FD_ZERO(&writefds); FD_ZERO(&exceptfds);
adns_beforeselect(ads,&maxfd,&readfds,&writefds,&exceptfds,&tvp,&tvbuf,0);
assert(tvp);
rsel= select(maxfd,&readfds,&writefds,&exceptfds,tvp);
if (rsel==-1) {
if (errno == EINTR) {
if (ads->iflags & adns_if_eintr) { r= EINTR; break; }
} else {
adns__diag(ads,-1,0,"select failed in wait: %s",strerror(errno));
adns_globalsystemfailure(ads);
}
} else {
assert(rsel >= 0);
adns_afterselect(ads,maxfd,&readfds,&writefds,&exceptfds,0);
}
}
adns__consistency(ads,0,cc_entex);
return r;
}
#endif
int adns_check(adns_state ads,
adns_query *query_io,
adns_answer **answer_r,
void **context_r) {
struct timeval now;
int r;
adns__consistency(ads,*query_io,cc_entex);
r= gettimeofday(&now,0);
if (!r) adns__autosys(ads,now);
r= adns__internal_check(ads,query_io,answer_r,context_r);
adns__consistency(ads,0,cc_entex);
return r;
}

352
adns/general.c Normal file
View file

@ -0,0 +1,352 @@
/*
* general.c
* - diagnostic functions
* - vbuf handling
*/
/*
* This file is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999-2000 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
* $Id: general.c,v 1.1 2002/08/13 14:35:05 fishwaldo Exp $
*/
#include "stdinc.h"
#include "fileio.h"
#include "s_log.h"
#include "memory.h"
#include "internal.h"
/* Core diagnostic functions */
#define LOG_BUFSIZE 2000
#if 0
void adns__vdiag(adns_state ads, const char *pfx, adns_initflags prevent,
int serv, adns_query qu, const char *fmt, va_list al)
{
/* Fix this to log to the ircd log interface */
#if 0
const char *bef, *aft;
vbuf vb;
vfprintf(ads->diagfile,fmt,al);
bef= " (";
aft= "\n";
if (qu && qu->query_dgram) {
adns__vbuf_init(&vb);
fprintf(ads->diagfile,"%sQNAME=%s, QTYPE=%s",
bef,
adns__diag_domain(qu->ads,-1,0, &vb,
qu->query_dgram,qu->query_dglen,DNS_HDRSIZE),
qu->typei ? qu->typei->rrtname : "<unknown>");
if (qu->typei && qu->typei->fmtname)
fprintf(ads->diagfile,"(%s)",qu->typei->fmtname);
bef=", "; aft=")\n";
adns__vbuf_free(&vb);
}
if (serv>=0) {
fprintf(ads->diagfile,"%sNS=%s",bef,inetntoa((unsigned char *)&ads->servers[serv].addr));
bef=", "; aft=")\n";
}
fputs(aft,ads->diagfile);
#endif
}
#endif
void adns__debug(adns_state ads, int serv, adns_query qu, const char *fmt, ...) {
char buf[LOG_BUFSIZE];
va_list al;
va_start(al,fmt);
vsprintf(buf, fmt, al);
#if 0
adns__vdiag(ads," debug",0,serv,qu,fmt,al);
#endif
va_end(al);
/* redundant calls to vsprintf() but what can you do,
* when you live in a shoe?
*/
ilog(L_DEBUG, "%s", buf);
}
void adns__warn(adns_state ads, int serv, adns_query qu, const char *fmt, ...) {
char buf[LOG_BUFSIZE];
va_list al;
va_start(al,fmt);
vsprintf(buf, fmt, al);
#if 0
adns__vdiag(ads," warning",adns_if_noerrprint|adns_if_noserverwarn,serv,qu,fmt,al);
#endif
va_end(al);
ilog(L_WARN, "%s", buf);
}
void adns__diag(adns_state ads, int serv, adns_query qu, const char *fmt, ...) {
char buf[LOG_BUFSIZE];
va_list al;
va_start(al,fmt);
vsprintf(buf, fmt, al);
#if 0
adns__vdiag(ads,"",adns_if_noerrprint,serv,qu,fmt,al);
#endif
va_end(al);
ilog(L_DEBUG, "%s", buf);
}
/* vbuf functions */
void adns__vbuf_init(vbuf *vb) {
vb->used= vb->avail= 0; vb->buf= 0;
}
int adns__vbuf_ensure(vbuf *vb, int want) {
void *nb;
if (vb->avail >= want) return 1;
nb= MyRealloc(vb->buf,want); if (!nb) return 0;
vb->buf= nb;
vb->avail= want;
return 1;
}
void adns__vbuf_appendq(vbuf *vb, const byte *ddata, int len) {
memcpy(vb->buf+vb->used,ddata,len);
vb->used+= len;
}
int adns__vbuf_append(vbuf *vb, const byte *ddata, int len) {
int newlen;
void *nb;
newlen= vb->used+len;
if (vb->avail < newlen) {
if (newlen<20) newlen= 20;
newlen <<= 1;
nb= MyRealloc(vb->buf,newlen);
if (!nb) { newlen= vb->used+len; nb= MyRealloc(vb->buf,newlen); }
if (!nb) return 0;
vb->buf= nb;
vb->avail= newlen;
}
adns__vbuf_appendq(vb,ddata,len);
return 1;
}
int adns__vbuf_appendstr(vbuf *vb, const char *ddata) {
int l;
l= strlen(ddata);
return adns__vbuf_append(vb,(const byte *)ddata,l);
}
void adns__vbuf_free(vbuf *vb) {
MyFree(vb->buf);
adns__vbuf_init(vb);
}
/* Additional diagnostic functions */
const char *adns__diag_domain(adns_state ads, int serv, adns_query qu,
vbuf *vb, const byte *dgram, int dglen, int cbyte) {
adns_status st;
st= adns__parse_domain(ads,serv,qu,vb, pdf_quoteok, dgram,dglen,&cbyte,dglen);
if (st == adns_s_nomemory) {
return "<cannot report domain... out of memory>";
}
if (st) {
vb->used= 0;
if (!(adns__vbuf_appendstr(vb,"<bad format... ") &&
adns__vbuf_appendstr(vb,adns_strerror(st)) &&
adns__vbuf_appendstr(vb,">") &&
adns__vbuf_append(vb,(const byte *)"",1))) {
return "<cannot report bad format... out of memory>";
}
}
if (!vb->used) {
adns__vbuf_appendstr(vb,"<truncated ...>");
adns__vbuf_append(vb,(const byte *)"",1);
}
return (const char *)vb->buf;
}
adns_status adns_rr_info(adns_rrtype type,
const char **rrtname_r, const char **fmtname_r,
int *len_r,
const void *datap, char **data_r) {
const typeinfo *typei;
vbuf vb;
adns_status st;
typei= adns__findtype(type);
if (!typei) return adns_s_unknownrrtype;
if (rrtname_r) *rrtname_r= typei->rrtname;
if (fmtname_r) *fmtname_r= typei->fmtname;
if (len_r) *len_r= typei->rrsz;
if (!datap) return adns_s_ok;
adns__vbuf_init(&vb);
st= typei->convstring(&vb,datap);
if (st) goto x_freevb;
if (!adns__vbuf_append(&vb,(const byte *)"",1)) { st= adns_s_nomemory; goto x_freevb; }
assert(strlen((const char *)vb.buf) == vb.used-1);
*data_r= MyRealloc(vb.buf,vb.used);
if (!*data_r) *data_r= (char *)vb.buf;
return adns_s_ok;
x_freevb:
adns__vbuf_free(&vb);
return st;
}
#define SINFO(n,s) { adns_s_##n, #n, s }
static const struct sinfo {
adns_status st;
const char *abbrev;
const char *string;
} sinfos[]= {
SINFO( ok, "OK" ),
SINFO( nomemory, "Out of memory" ),
SINFO( unknownrrtype, "Query not implemented in DNS library" ),
SINFO( systemfail, "General resolver or system failure" ),
SINFO( timeout, "DNS query timed out" ),
SINFO( allservfail, "All nameservers failed" ),
SINFO( norecurse, "Recursion denied by nameserver" ),
SINFO( invalidresponse, "Nameserver sent bad response" ),
SINFO( unknownformat, "Nameserver used unknown format" ),
SINFO( rcodeservfail, "Nameserver reports failure" ),
SINFO( rcodeformaterror, "Query not understood by nameserver" ),
SINFO( rcodenotimplemented, "Query not implemented by nameserver" ),
SINFO( rcoderefused, "Query refused by nameserver" ),
SINFO( rcodeunknown, "Nameserver sent unknown response code" ),
SINFO( inconsistent, "Inconsistent resource records in DNS" ),
SINFO( prohibitedcname, "DNS alias found where canonical name wanted" ),
SINFO( answerdomaininvalid, "Found syntactically invalid domain name" ),
SINFO( answerdomaintoolong, "Found overly-long domain name" ),
SINFO( invaliddata, "Found invalid DNS data" ),
SINFO( querydomainwrong, "Domain invalid for particular DNS query type" ),
SINFO( querydomaininvalid, "Domain name is syntactically invalid" ),
SINFO( querydomaintoolong, "Domain name or component is too long" ),
SINFO( nxdomain, "No such domain" ),
SINFO( nodata, "No such data" )
};
static int si_compar(const void *key, const void *elem) {
const adns_status *st= key;
const struct sinfo *si= elem;
return *st < si->st ? -1 : *st > si->st ? 1 : 0;
}
static const struct sinfo *findsinfo(adns_status st) {
return bsearch(&st,sinfos,sizeof(sinfos)/sizeof(*sinfos),sizeof(*sinfos),si_compar);
}
const char *adns_strerror(adns_status st) {
const struct sinfo *si;
si= findsinfo(st);
return si->string;
}
const char *adns_errabbrev(adns_status st) {
const struct sinfo *si;
si= findsinfo(st);
return si->abbrev;
}
#define STINFO(max) { adns_s_max_##max, #max }
static const struct stinfo {
adns_status stmax;
const char *abbrev;
} stinfos[]= {
{ adns_s_ok, "ok" },
STINFO( localfail ),
STINFO( remotefail ),
STINFO( tempfail ),
STINFO( misconfig ),
STINFO( misquery ),
STINFO( permfail )
};
static int sti_compar(const void *key, const void *elem) {
const adns_status *st= key;
const struct stinfo *sti= elem;
adns_status here, min, max;
here= *st;
min= (sti==stinfos) ? 0 : sti[-1].stmax+1;
max= sti->stmax;
return here < min ? -1 : here > max ? 1 : 0;
}
const char *adns_errtypeabbrev(adns_status st) {
const struct stinfo *sti;
sti= bsearch(&st,stinfos,sizeof(stinfos)/sizeof(*stinfos),sizeof(*stinfos),sti_compar);
return sti->abbrev;
}
void adns__isort(void *array, int nobjs, int sz, void *tempbuf,
int (*needswap)(void *context, const void *a, const void *b),
void *context) {
byte *ddata= array;
int i, place;
for (i=0; i<nobjs; i++) {
for (place= i;
place>0 && needswap(context, ddata + (place-1)*sz, ddata + i*sz);
place--);
if (place != i) {
memcpy(tempbuf, ddata + i*sz, sz);
memmove(ddata + (place+1)*sz, ddata + place*sz, (i-place)*sz);
memcpy(ddata + place*sz, tempbuf, sz);
}
}
}

716
adns/internal.h Normal file
View file

@ -0,0 +1,716 @@
/*
* internal.h
* - declarations of private objects with external linkage (adns__*)
* - definitons of internal macros
* - comments regarding library data structures
*/
/*
* This file is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999-2000 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
* $Id: internal.h,v 1.1 2002/08/13 14:35:06 fishwaldo Exp $
*/
#ifndef ADNS_INTERNAL_H_INCLUDED
#define ADNS_INTERNAL_H_INCLUDED
#include "config.h"
#ifdef __GNUC__
#define INLINE __inline__
#else
#define INLINE
#endif
typedef unsigned char byte;
#include <stdarg.h>
#include <assert.h>
#include <unistd.h>
#include <signal.h>
#include <errno.h>
#include <string.h>
#include <sys/time.h>
#include "adns.h"
#include "dlist.h"
#ifdef ADNS_REGRESS_TEST
# include "hredirect.h"
#endif
/* Configuration and constants */
#define MAXSERVERS 5
#define MAXSORTLIST 15
#define UDPMAXRETRIES 5
#define UDPRETRYMS 1500
#define TCPWAITMS 30000
#define TCPCONNMS 14000
#define TCPIDLEMS 30000
#define MAXTTLBELIEVE (7*86400) /* any TTL > 7 days is capped */
#define DNS_PORT 53
#define DNS_MAXUDP 512
#define DNS_MAXLABEL 63
#define DNS_MAXDOMAIN 255
#define DNS_HDRSIZE 12
#define DNS_IDOFFSET 0
#define DNS_CLASS_IN 1
#define IP6STRLEN 47
#define DNS_INADDR_ARPA "in-addr", "arpa"
#define DNS_IP6_INT "ip6", "int"
#define MAX_POLLFDS ADNS_POLLFDS_RECOMMENDED
typedef enum {
cc_user,
cc_entex,
cc_freq
} consistency_checks;
typedef enum {
rcode_noerror,
rcode_formaterror,
rcode_servfail,
rcode_nxdomain,
rcode_notimp,
rcode_refused
} dns_rcode;
/* Shared data structures */
typedef union {
adns_status status;
char *cp;
adns_rrtype type;
int i;
struct in_addr ia;
unsigned long ul;
} rr_align;
typedef struct {
int used, avail;
byte *buf;
} vbuf;
typedef struct {
adns_state ads;
adns_query qu;
int serv;
const byte *dgram;
int dglen, nsstart, nscount, arcount;
struct timeval now;
} parseinfo;
typedef struct {
adns_rrtype type;
const char *rrtname;
const char *fmtname;
int rrsz;
void (*makefinal)(adns_query qu, void *);
/* Change memory management of *data.
* Previously, used alloc_interim, now use alloc_final.
*/
adns_status (*convstring)(vbuf *vb, const void *);
/* Converts the RR data to a string representation in vbuf.
* vbuf will be appended to (it must have been initialised),
* and will not be null-terminated by convstring.
*/
adns_status (*parse)(const parseinfo *pai, int cbyte, int max, void *store_r);
/* Parse one RR, in dgram of length dglen, starting at cbyte and
* extending until at most max.
*
* The RR should be stored at *store_r, of length qu->typei->rrsz.
*
* If there is an overrun which might indicate truncation, it should set
* *rdstart to -1; otherwise it may set it to anything else positive.
*
* nsstart is the offset of the authority section.
*/
int (*diff_needswap)(adns_state ads, const void *datap_a, const void *datap_b);
/* Returns !0 if RR a should be strictly after RR b in the sort order,
* 0 otherwise. Must not fail.
*/
} typeinfo;
typedef struct allocnode {
struct allocnode *next, *back;
} allocnode;
union maxalign {
byte d[1];
struct in_addr ia;
long l;
void *p;
void (*fp)(void);
union maxalign *up;
} data;
typedef struct {
void *ext;
void (*callback)(adns_query parent, adns_query child);
union {
adns_rr_addr ptr_parent_addr;
adns_rr_hostaddr *hostaddr;
} info;
} qcontext;
struct adns__query {
adns_state ads;
enum { query_tosend, query_tcpw, query_childw, query_done } state;
adns_query back, next, parent;
struct { adns_query head, tail; } children;
struct { adns_query back, next; } siblings;
struct { allocnode *head, *tail; } allocations;
int interim_allocd, preserved_allocd;
void *final_allocspace;
const typeinfo *typei;
byte *query_dgram;
int query_dglen;
vbuf vb;
/* General-purpose messing-about buffer.
* Wherever a `big' interface is crossed, this may be corrupted/changed
* unless otherwise specified.
*/
adns_answer *answer;
/* This is allocated when a query is submitted, to avoid being unable
* to relate errors to queries if we run out of memory. During
* query processing status, rrs is 0. cname is set if
* we found a cname (this corresponds to cname_dgram in the query
* structure). type is set from the word go. nrrs and rrs
* are set together, when we find how many rrs there are.
* owner is set during querying unless we're doing searchlist,
* in which case it is set only when we find an answer.
*/
byte *cname_dgram;
int cname_dglen, cname_begin;
/* If non-0, has been allocated using . */
int cname_count;
vbuf search_vb;
int search_origlen, search_pos, search_doneabs;
/* Used by the searching algorithm. The query domain in textual form
* is copied into the vbuf, and _origlen set to its length. Then
* we walk the searchlist, if we want to. _pos says where we are
* (next entry to try), and _doneabs says whether we've done the
* absolute query yet (0=not yet, 1=done, -1=must do straight away,
* but not done yet). If flags doesn't have adns_qf_search then
* the vbuf is initialised but empty and everything else is zero.
*/
int id, flags, retries;
int udpnextserver;
unsigned long udpsent; /* bitmap indexed by server */
struct timeval timeout;
time_t expires; /* Earliest expiry time of any record we used. */
qcontext ctx;
/* Possible states:
*
* state Queue child id nextudpserver udpsent tcpfailed
*
* tosend NONE null >=0 0 zero zero
* tosend udpw null >=0 any nonzero zero
* tosend NONE null >=0 any nonzero zero
*
* tcpw tcpw null >=0 irrelevant any any
*
* child childw set >=0 irrelevant irrelevant irrelevant
* child NONE null >=0 irrelevant irrelevant irrelevant
* done output null -1 irrelevant irrelevant irrelevant
*
* Queries are only not on a queue when they are actually being processed.
* Queries in state tcpw/tcpw have been sent (or are in the to-send buffer)
* iff the tcp connection is in state server_ok.
*
* +------------------------+
* START -----> | tosend/NONE |
* +------------------------+
* / |\ \
* too big for UDP / UDP timeout \ \ send via UDP
* send via TCP / more retries \ \
* when conn'd / desired \ \
* | | |
* v | v
* +-----------+ +-------------+
* | tcpw/tcpw | ________ | tosend/udpw |
* +-----------+ \ +-------------+
* | | | UDP timeout | |
* | | | no more | |
* | | | retries | |
* \ | TCP died | desired | |
* \ \ no more | | |
* \ \ servers | TCP / |
* \ \ to try | timeout / |
* got \ \ v |_ | got
* reply \ _| +------------------+ / reply
* \ | done/output FAIL | /
* \ +------------------+ /
* \ /
* _| |_
* (..... got reply ....)
* / \
* need child query/ies / \ no child query
* / \
* |_ _|
* +---------------+ +----------------+
* | childw/childw | ----------------> | done/output OK |
* +---------------+ children done +----------------+
*/
};
struct query_queue { adns_query head, tail; };
struct adns__state {
adns_initflags iflags;
FBFILE *diagfile;
int configerrno;
struct query_queue udpw, tcpw, childw, output;
adns_query forallnext;
int nextid, udpsocket, tcpsocket;
vbuf tcpsend, tcprecv;
int nservers, nsortlist, nsearchlist, searchndots, tcpserver, tcprecv_skip;
enum adns__tcpstate {
server_disconnected, server_connecting,
server_ok, server_broken
} tcpstate;
struct timeval tcptimeout;
/* This will have tv_sec==0 if it is not valid. It will always be
* valid if tcpstate _connecting. When _ok, it will be nonzero if
* we are idle (ie, tcpw queue is empty), in which case it is the
* absolute time when we will close the connection.
*/
struct adns_pollfd pollfds_buf[MAX_POLLFDS];
struct server {
struct in_addr addr;
} servers[MAXSERVERS];
struct sortlist {
struct in_addr base, mask;
} sortlist[MAXSORTLIST];
char **searchlist;
};
/* From setup.c: */
int adns__setnonblock(adns_state ads, int fd); /* => errno value */
/* From general.c: */
void adns__vdiag(adns_state ads, const char *pfx, adns_initflags prevent,
int serv, adns_query qu, const char *fmt, va_list al);
void adns__debug(adns_state ads, int serv, adns_query qu,
const char *fmt, ...);
void adns__warn(adns_state ads, int serv, adns_query qu,
const char *fmt, ...);
void adns__diag(adns_state ads, int serv, adns_query qu,
const char *fmt, ...);
int adns__vbuf_ensure(vbuf *vb, int want);
int adns__vbuf_appendstr(vbuf *vb, const char *); /* does not include nul */
int adns__vbuf_append(vbuf *vb, const byte *, int len);
/* 1=>success, 0=>realloc failed */
void adns__vbuf_appendq(vbuf *vb, const byte *, int len);
void adns__vbuf_init(vbuf *vb);
void adns__vbuf_free(vbuf *vb);
const char *adns__diag_domain(adns_state ads, int serv, adns_query qu,
vbuf *vb, const byte *dgram, int dglen, int cbyte);
/* Unpicks a domain in a datagram and returns a string suitable for
* printing it as. Never fails - if an error occurs, it will
* return some kind of string describing the error.
*
* serv may be -1 and qu may be 0. vb must have been initialised,
* and will be left in an arbitrary consistent state.
*
* Returns either vb->buf, or a pointer to a string literal. Do not modify
* vb before using the return value.
*/
void adns__isort(void *array, int nobjs, int sz, void *tempbuf,
int (*needswap)(void *context, const void *a, const void *b),
void *context);
/* Does an insertion sort of array which must contain nobjs objects
* each sz bytes long. tempbuf must point to a buffer at least
* sz bytes long. needswap should return !0 if a>b (strictly, ie
* wrong order) 0 if a<=b (ie, order is fine).
*/
void adns__sigpipe_protect(adns_state);
void adns__sigpipe_unprotect(adns_state);
/* If SIGPIPE protection is not disabled, will block all signals except
* SIGPIPE, and set SIGPIPE's disposition to SIG_IGN. (And then restore.)
* Each call to _protect must be followed by a call to _unprotect before
* any significant amount of code gets to run, since the old signal mask
* is stored in the adns structure.
*/
/* From transmit.c: */
adns_status adns__mkquery(adns_state ads, vbuf *vb, int *id_r,
const char *owner, int ol,
const typeinfo *typei, adns_queryflags flags);
/* Assembles a query packet in vb. A new id is allocated and returned.
*/
adns_status adns__mkquery_frdgram(adns_state ads, vbuf *vb, int *id_r,
const byte *qd_dgram, int qd_dglen, int qd_begin,
adns_rrtype type, adns_queryflags flags);
/* Same as adns__mkquery, but takes the owner domain from an existing datagram.
* That domain must be correct and untruncated.
*/
void adns__querysend_tcp(adns_query qu, struct timeval now);
/* Query must be in state tcpw/tcpw; it will be sent if possible and
* no further processing can be done on it for now. The connection
* might be broken, but no reconnect will be attempted.
*/
void adns__query_send(adns_query qu, struct timeval now);
/* Query must be in state tosend/NONE; it will be moved to a new state,
* and no further processing can be done on it for now.
* (Resulting state is one of udp/timew, tcpwait/timew (if server not connected),
* tcpsent/timew, child/childw or done/output.)
* __query_send may decide to use either UDP or TCP depending whether
* _qf_usevc is set (or has become set) and whether the query is too
* large.
*/
/* From query.c: */
adns_status adns__internal_submit(adns_state ads, adns_query *query_r,
const typeinfo *typei, vbuf *qumsg_vb, int id,
adns_queryflags flags, struct timeval now,
const qcontext *ctx);
/* Submits a query (for internal use, called during external submits).
*
* The new query is returned in *query_r, or we return adns_s_nomemory.
*
* The query datagram should already have been assembled in qumsg_vb;
* the memory for it is _taken over_ by this routine whether it
* succeeds or fails (if it succeeds, the vbuf is reused for qu->vb).
*
* *ctx is copied byte-for-byte into the query.
*
* When the child query is done, ctx->callback will be called. The
* child will already have been taken off both the global list of
* queries in ads and the list of children in the parent. The child
* will be freed when the callback returns. The parent will have been
* taken off the global childw queue.
*
* The callback should either call adns__query_done, if it is
* complete, or adns__query_fail, if an error has occurred, in which
* case the other children (if any) will be cancelled. If the parent
* has more unfinished children (or has just submitted more) then the
* callback may choose to wait for them - it must then put the parent
* back on the childw queue.
*/
void adns__search_next(adns_state ads, adns_query qu, struct timeval now);
/* Walks down the searchlist for a query with adns_qf_search.
* The query should have just had a negative response, or not had
* any queries sent yet, and should not be on any queue.
* The query_dgram if any will be freed and forgotten and a new
* one constructed from the search_* members of the query.
*
* Cannot fail (in case of error, calls adns__query_fail).
*/
void *adns__alloc_interim(adns_query qu, size_t sz);
void *adns__alloc_preserved(adns_query qu, size_t sz);
/* Allocates some memory, and records which query it came from
* and how much there was.
*
* If an error occurs in the query, all the memory from _interim is
* simply freed. If the query succeeds, one large buffer will be made
* which is big enough for all these allocations, and then
* adns__alloc_final will get memory from this buffer.
*
* _alloc_interim can fail (and return 0).
* The caller must ensure that the query is failed.
*
* The memory from _preserved is is kept and transferred into the
* larger buffer - unless we run out of memory, in which case it too
* is freed. When you use _preserved you have to add code to the
* x_nomem error exit case in adns__makefinal_query to clear out the
* pointers you made to those allocations, because that's when they're
* thrown away; you should also make a note in the declaration of
* those pointer variables, to note that they are _preserved rather
* than _interim. If they're in the answer, note it here:
* answer->cname and answer->owner are _preserved.
*/
void adns__transfer_interim(adns_query from, adns_query to, void *block, size_t sz);
/* Transfers an interim allocation from one query to another, so that
* the `to' query will have room for the data when we get to makefinal
* and so that the free will happen when the `to' query is freed
* rather than the `from' query.
*
* It is legal to call adns__transfer_interim with a null pointer; this
* has no effect.
*
* _transfer_interim also ensures that the expiry time of the `to' query
* is no later than that of the `from' query, so that child queries'
* TTLs get inherited by their parents.
*/
void *adns__alloc_mine(adns_query qu, size_t sz);
/* Like _interim, but does not record the length for later
* copying into the answer. This just ensures that the memory
* will be freed when we're done with the query.
*/
void *adns__alloc_final(adns_query qu, size_t sz);
/* Cannot fail, and cannot return 0.
*/
void adns__makefinal_block(adns_query qu, void **blpp, size_t sz);
void adns__makefinal_str(adns_query qu, char **strp);
void adns__reset_preserved(adns_query qu);
/* Resets all of the memory management stuff etc. to take account of
* only the _preserved stuff from _alloc_preserved. Used when we find
* an error somewhere and want to just report the error (with perhaps
* CNAME, owner, etc. info), and also when we're halfway through RRs
* in a datagram and discover that we need to retry the query.
*/
void adns__query_done(adns_query qu);
void adns__query_fail(adns_query qu, adns_status);
/* From reply.c: */
void adns__procdgram(adns_state ads, const byte *dgram, int len,
int serv, int viatcp, struct timeval now);
/* This function is allowed to cause new datagrams to be constructed
* and sent, or even new queries to be started. However,
* query-sending functions are not allowed to call any general event
* loop functions in case they accidentally call this.
*
* Ie, receiving functions may call sending functions.
* Sending functions may NOT call receiving functions.
*/
/* From types.c: */
const typeinfo *adns__findtype(adns_rrtype type);
/* From parse.c: */
typedef struct {
adns_state ads;
adns_query qu;
int serv;
const byte *dgram;
int dglen, max, cbyte, namelen;
int *dmend_r;
} findlabel_state;
void adns__findlabel_start(findlabel_state *fls, adns_state ads,
int serv, adns_query qu,
const byte *dgram, int dglen, int max,
int dmbegin, int *dmend_rlater);
/* Finds labels in a domain in a datagram.
*
* Call this routine first.
* dmend_rlater may be null. ads (and of course fls) may not be.
* serv may be -1, qu may be null - they are for error reporting.
*/
adns_status adns__findlabel_next(findlabel_state *fls, int *lablen_r, int *labstart_r);
/* Then, call this one repeatedly.
*
* It will return adns_s_ok if all is well, and tell you the length
* and start of successive labels. labstart_r may be null, but
* lablen_r must not be.
*
* After the last label, it will return with *lablen_r zero.
* Do not then call it again; instead, just throw away the findlabel_state.
*
* *dmend_rlater will have been set to point to the next part of
* the datagram after the label (or after the uncompressed part,
* if compression was used). *namelen_rlater will have been set
* to the length of the domain name (total length of labels plus
* 1 for each intervening dot).
*
* If the datagram appears to be truncated, *lablen_r will be -1.
* *dmend_rlater, *labstart_r and *namelen_r may contain garbage.
* Do not call _next again.
*
* There may also be errors, in which case *dmend_rlater,
* *namelen_rlater, *lablen_r and *labstart_r may contain garbage.
* Do not then call findlabel_next again.
*/
typedef enum {
pdf_quoteok= 0x001
} parsedomain_flags;
adns_status adns__parse_domain(adns_state ads, int serv, adns_query qu, vbuf *vb, parsedomain_flags flags, const byte *dgram, int dglen, int *cbyte_io, int max);
/* vb must already have been initialised; it will be reset if necessary.
* If there is truncation, vb->used will be set to 0; otherwise
* (if there is no error) vb will be null-terminated.
* If there is an error vb and *cbyte_io may be left indeterminate.
*
* serv may be -1 and qu may be 0 - they are used for error reporting only.
*/
adns_status adns__parse_domain_more(findlabel_state *fls, adns_state ads,
adns_query qu, vbuf *vb, parsedomain_flags flags,
const byte *dgram);
/* Like adns__parse_domain, but you pass it a pre-initialised findlabel_state,
* for continuing an existing domain or some such of some kind. Also, unlike
* _parse_domain, the domain data will be appended to vb, rather than replacing
* the existing contents.
*/
adns_status adns__findrr(adns_query qu, int serv,
const byte *dgram, int dglen, int *cbyte_io,
int *type_r, int *class_r, unsigned long *ttl_r,
int *rdlen_r, int *rdstart_r,
int *ownermatchedquery_r);
/* Finds the extent and some of the contents of an RR in a datagram
* and does some checks. The datagram is *dgram, length dglen, and
* the RR starts at *cbyte_io (which is updated afterwards to point
* to the end of the RR).
*
* The type, class, TTL and RRdata length and start are returned iff
* the corresponding pointer variables are not null. type_r, class_r
* and ttl_r may not be null. The TTL will be capped.
*
* If ownermatchedquery_r != 0 then the owner domain of this
* RR will be compared with that in the query (or, if the query
* has gone to a CNAME lookup, with the canonical name).
* In this case, *ownermatchedquery_r will be set to 0 or 1.
* The query datagram (or CNAME datagram) MUST be valid and not truncated.
*
* If there is truncation then *type_r will be set to -1 and
* *cbyte_io, *class_r, *rdlen_r, *rdstart_r and *eo_matched_r will be
* undefined.
*
* qu must obviously be non-null.
*
* If an error is returned then *type_r will be undefined too.
*/
adns_status adns__findrr_anychk(adns_query qu, int serv,
const byte *dgram, int dglen, int *cbyte_io,
int *type_r, int *class_r, unsigned long *ttl_r,
int *rdlen_r, int *rdstart_r,
const byte *eo_dgram, int eo_dglen, int eo_cbyte,
int *eo_matched_r);
/* Like adns__findrr_checked, except that the datagram and
* owner to compare with can be specified explicitly.
*
* If the caller thinks they know what the owner of the RR ought to
* be they can pass in details in eo_*: this is another (or perhaps
* the same datagram), and a pointer to where the putative owner
* starts in that datagram. In this case *eo_matched_r will be set
* to 1 if the datagram matched or 0 if it did not. Either
* both eo_dgram and eo_matched_r must both be non-null, or they
* must both be null (in which case eo_dglen and eo_cbyte will be ignored).
* The eo datagram and contained owner domain MUST be valid and
* untruncated.
*/
void adns__update_expires(adns_query qu, unsigned long ttl, struct timeval now);
/* Updates the `expires' field in the query, so that it doesn't exceed
* now + ttl.
*/
int vbuf__append_quoted1035(vbuf *vb, const byte *buf, int len);
/* From event.c: */
void adns__tcp_broken(adns_state ads, const char *what, const char *why);
/* what and why may be both 0, or both non-0. */
void adns__tcp_tryconnect(adns_state ads, struct timeval now);
void adns__autosys(adns_state ads, struct timeval now);
/* Make all the system calls we want to if the application wants us to.
* Must not be called from within adns internal processing functions,
* lest we end up in recursive descent !
*/
void adns__must_gettimeofday(adns_state ads, const struct timeval **now_io,
struct timeval *tv_buf);
int adns__pollfds(adns_state ads, struct adns_pollfd pollfds_buf[MAX_POLLFDS]);
void adns__fdevents(adns_state ads,
const struct adns_pollfd *pollfds, int npollfds,
int maxfd, const fd_set *readfds,
const fd_set *writefds, const fd_set *exceptfds,
struct timeval now, int *r_r);
int adns__internal_check(adns_state ads,
adns_query *query_io,
adns_answer **answer,
void **context_r);
void adns__timeouts(adns_state ads, int act,
struct timeval **tv_io, struct timeval *tvbuf,
struct timeval now);
/* If act is !0, then this will also deal with the TCP connection
* if previous events broke it or require it to be connected.
*/
/* From check.c: */
void adns__consistency(adns_state ads, adns_query qu, consistency_checks cc);
/* Useful static inline functions: */
static INLINE int ctype_whitespace(int c) { return c==' ' || c=='\n' || c=='\t'; }
static INLINE int ctype_digit(int c) { return c>='0' && c<='9'; }
static INLINE int ctype_alpha(int c) {
return (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z');
}
static INLINE int ctype_822special(int c) { return strchr("()<>@,;:\\\".[]",c) != 0; }
static INLINE int ctype_domainunquoted(int c) {
return ctype_alpha(c) || ctype_digit(c) || (strchr("-_/+",c) != 0);
}
static INLINE int errno_resources(int e) { return e==ENOMEM || e==ENOBUFS; }
/* Useful macros */
#define MEM_ROUND(sz) \
(( ((sz)+sizeof(union maxalign)-1) / sizeof(union maxalign) ) \
* sizeof(union maxalign) )
#define GETIL_B(cb) (((dgram)[(cb)++]) & 0x0ff)
#define GET_B(cb,tv) ((tv)= GETIL_B((cb)))
#define GET_W(cb,tv) ((tv)=0, (tv)|=(GETIL_B((cb))<<8), (tv)|=GETIL_B(cb), (tv))
#define GET_L(cb,tv) ( (tv)=0, \
(tv)|=(GETIL_B((cb))<<24), \
(tv)|=(GETIL_B((cb))<<16), \
(tv)|=(GETIL_B((cb))<<8), \
(tv)|=GETIL_B(cb), \
(tv) )
#endif

250
adns/parse.c Normal file
View file

@ -0,0 +1,250 @@
/*
* parse.c
* - parsing assistance functions (mainly for domains inside datagrams)
*/
/*
* This file is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999-2000 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
* $Id: parse.c,v 1.1 2002/08/13 14:35:06 fishwaldo Exp $
*/
#include "stdinc.h"
#include "fileio.h"
#include "internal.h"
int vbuf__append_quoted1035(vbuf *vb, const byte *buf, int len) {
byte qbuf[10];
int i, ch;
while (len) {
qbuf[0]= 0;
for (i=0; i<len; i++) {
ch= buf[i];
if (ch <= ' ' || ch >= 127) {
ircsprintf((char *)qbuf,"\\%03o",ch);
break;
} else if (!ctype_domainunquoted(ch)) {
ircsprintf((char *)qbuf,"\\%c",ch);
break;
}
}
if (!adns__vbuf_append(vb,buf,i) || !adns__vbuf_append(vb,qbuf,strlen((const char *)qbuf)))
return 0;
if (i<len) i++;
buf+= i;
len-= i;
}
return 1;
}
void adns__findlabel_start(findlabel_state *fls, adns_state ads,
int serv, adns_query qu,
const byte *dgram, int dglen, int max,
int dmbegin, int *dmend_rlater) {
fls->ads= ads;
fls->qu= qu;
fls->serv= serv;
fls->dgram= dgram;
fls->dglen= dglen;
fls->max= max;
fls->cbyte= dmbegin;
fls->namelen= 0;
fls->dmend_r= dmend_rlater;
}
adns_status adns__findlabel_next(findlabel_state *fls,
int *lablen_r, int *labstart_r) {
int lablen, jumpto;
const char *dgram;
dgram= (const char *)fls->dgram;
for (;;) {
if (fls->cbyte >= fls->dglen) goto x_truncated;
if (fls->cbyte >= fls->max) goto x_badresponse;
GET_B(fls->cbyte,lablen);
if (!(lablen & 0x0c0)) break;
if ((lablen & 0x0c0) != 0x0c0) return adns_s_unknownformat;
if (fls->cbyte >= fls->dglen) goto x_truncated;
if (fls->cbyte >= fls->max) goto x_badresponse;
GET_B(fls->cbyte,jumpto);
jumpto |= (lablen&0x3f)<<8;
if (fls->dmend_r) *(fls->dmend_r)= fls->cbyte;
fls->cbyte= jumpto;
fls->dmend_r= 0; fls->max= fls->dglen+1;
}
if (labstart_r) *labstart_r= fls->cbyte;
if (lablen) {
if (fls->namelen) fls->namelen++;
fls->namelen+= lablen;
if (fls->namelen > DNS_MAXDOMAIN) return adns_s_answerdomaintoolong;
fls->cbyte+= lablen;
if (fls->cbyte > fls->dglen) goto x_truncated;
if (fls->cbyte > fls->max) goto x_badresponse;
} else {
if (fls->dmend_r) *(fls->dmend_r)= fls->cbyte;
}
*lablen_r= lablen;
return adns_s_ok;
x_truncated:
*lablen_r= -1;
return adns_s_ok;
x_badresponse:
adns__diag(fls->ads,fls->serv,fls->qu,"label in domain runs beyond end of domain");
return adns_s_invalidresponse;
}
adns_status adns__parse_domain(adns_state ads, int serv, adns_query qu,
vbuf *vb, parsedomain_flags flags,
const byte *dgram, int dglen, int *cbyte_io, int max) {
findlabel_state fls;
adns__findlabel_start(&fls,ads, serv,qu, dgram,dglen,max, *cbyte_io,cbyte_io);
vb->used= 0;
return adns__parse_domain_more(&fls,ads,qu, vb,flags,dgram);
}
adns_status adns__parse_domain_more(findlabel_state *fls, adns_state ads,
adns_query qu, vbuf *vb, parsedomain_flags flags,
const byte *dgram) {
int lablen, labstart, i, ch, first;
adns_status st;
first= 1;
for (;;) {
st= adns__findlabel_next(fls,&lablen,&labstart);
if (st) return st;
if (lablen<0) { vb->used=0; return adns_s_ok; }
if (!lablen) break;
if (first) {
first= 0;
} else {
if (!adns__vbuf_append(vb,(const byte *)".",1)) return adns_s_nomemory;
}
if (flags & pdf_quoteok) {
if (!vbuf__append_quoted1035(vb,dgram+labstart,lablen))
return adns_s_nomemory;
} else {
ch= dgram[labstart];
if (!ctype_alpha(ch) && !ctype_digit(ch)) return adns_s_answerdomaininvalid;
for (i= labstart+1; i<labstart+lablen; i++) {
ch= dgram[i];
if (ch != '-' && !ctype_alpha(ch) && !ctype_digit(ch))
return adns_s_answerdomaininvalid;
}
if (!adns__vbuf_append(vb,dgram+labstart,lablen))
return adns_s_nomemory;
}
}
if (!adns__vbuf_append(vb,(const byte *)"",1)) return adns_s_nomemory;
return adns_s_ok;
}
adns_status adns__findrr_anychk(adns_query qu, int serv,
const byte *dgram, int dglen, int *cbyte_io,
int *type_r, int *class_r, unsigned long *ttl_r,
int *rdlen_r, int *rdstart_r,
const byte *eo_dgram, int eo_dglen, int eo_cbyte,
int *eo_matched_r) {
findlabel_state fls, eo_fls;
int cbyte;
int tmp, rdlen, mismatch;
unsigned long ttl;
int lablen, labstart, ch;
int eo_lablen, eo_labstart, eo_ch;
adns_status st;
cbyte= *cbyte_io;
adns__findlabel_start(&fls,qu->ads, serv,qu, dgram,dglen,dglen,cbyte,&cbyte);
if (eo_dgram) {
adns__findlabel_start(&eo_fls,qu->ads, -1,0, eo_dgram,eo_dglen,eo_dglen,eo_cbyte,0);
mismatch= 0;
} else {
mismatch= 1;
}
for (;;) {
st= adns__findlabel_next(&fls,&lablen,&labstart);
if (st) return st;
if (lablen<0) goto x_truncated;
if (!mismatch) {
st= adns__findlabel_next(&eo_fls,&eo_lablen,&eo_labstart);
assert(!st); assert(eo_lablen>=0);
if (lablen != eo_lablen) mismatch= 1;
while (!mismatch && eo_lablen-- > 0) {
ch= dgram[labstart++]; if (ctype_alpha(ch)) ch &= ~32;
eo_ch= eo_dgram[eo_labstart++]; if (ctype_alpha(eo_ch)) eo_ch &= ~32;
if (ch != eo_ch) mismatch= 1;
}
}
if (!lablen) break;
}
if (eo_matched_r) *eo_matched_r= !mismatch;
if (cbyte+10>dglen) goto x_truncated;
GET_W(cbyte,tmp); *type_r= tmp;
GET_W(cbyte,tmp); *class_r= tmp;
GET_L(cbyte,ttl);
if (ttl > MAXTTLBELIEVE) ttl= MAXTTLBELIEVE;
*ttl_r= ttl;
GET_W(cbyte,rdlen); if (rdlen_r) *rdlen_r= rdlen;
if (rdstart_r) *rdstart_r= cbyte;
cbyte+= rdlen;
if (cbyte>dglen) goto x_truncated;
*cbyte_io= cbyte;
return adns_s_ok;
x_truncated:
*type_r= -1;
return 0;
}
adns_status adns__findrr(adns_query qu, int serv,
const byte *dgram, int dglen, int *cbyte_io,
int *type_r, int *class_r, unsigned long *ttl_r,
int *rdlen_r, int *rdstart_r,
int *ownermatchedquery_r) {
if (!ownermatchedquery_r) {
return adns__findrr_anychk(qu,serv,
dgram,dglen,cbyte_io,
type_r,class_r,ttl_r,rdlen_r,rdstart_r,
0,0,0, 0);
} else if (!qu->cname_dgram) {
return adns__findrr_anychk(qu,serv,
dgram,dglen,cbyte_io,
type_r,class_r,ttl_r,rdlen_r,rdstart_r,
qu->query_dgram,qu->query_dglen,DNS_HDRSIZE,
ownermatchedquery_r);
} else {
return adns__findrr_anychk(qu,serv,
dgram,dglen,cbyte_io,
type_r,class_r,ttl_r,rdlen_r,rdstart_r,
qu->cname_dgram,qu->cname_dglen,qu->cname_begin,
ownermatchedquery_r);
}
}

620
adns/query.c Normal file
View file

@ -0,0 +1,620 @@
/*
* query.c
* - overall query management (allocation, completion)
* - per-query memory management
* - query submission and cancellation (user-visible and internal)
*/
/*
* This file is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999-2000 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
* $Id: query.c,v 1.1 2002/08/13 14:35:07 fishwaldo Exp $
*/
#include "stdinc.h"
#include "memory.h"
#include "fileio.h"
#include "internal.h"
static adns_query query_alloc(adns_state ads, const typeinfo *typei,
adns_queryflags flags, struct timeval now) {
/* Allocate a virgin query and return it. */
adns_query qu;
qu= MyMalloc(sizeof(*qu));
qu->answer= MyMalloc(sizeof(*qu->answer));
qu->ads= ads;
qu->state= query_tosend;
qu->back= qu->next= qu->parent= 0;
ADNS_LIST_INIT(qu->children);
LINK_INIT(qu->siblings);
ADNS_LIST_INIT(qu->allocations);
qu->interim_allocd= 0;
qu->preserved_allocd= 0;
qu->final_allocspace= 0;
qu->typei= typei;
qu->query_dgram= 0;
qu->query_dglen= 0;
adns__vbuf_init(&qu->vb);
qu->cname_dgram= 0;
qu->cname_dglen= qu->cname_begin= 0;
adns__vbuf_init(&qu->search_vb);
qu->search_origlen= qu->search_pos= qu->search_doneabs= 0;
qu->id= -2; /* will be overwritten with real id before we leave adns */
qu->flags= flags;
qu->retries= 0;
qu->udpnextserver= 0;
qu->udpsent= 0;
timerclear(&qu->timeout);
qu->expires= now.tv_sec + MAXTTLBELIEVE;
memset(&qu->ctx,0,sizeof(qu->ctx));
qu->answer->status= adns_s_ok;
qu->answer->cname= qu->answer->owner= 0;
qu->answer->type= typei->type;
qu->answer->expires= -1;
qu->answer->nrrs= 0;
qu->answer->rrs.untyped= 0;
qu->answer->rrsz= typei->rrsz;
return qu;
}
static void query_submit(adns_state ads, adns_query qu,
const typeinfo *typei, vbuf *qumsg_vb, int id,
adns_queryflags flags, struct timeval now) {
/* Fills in the query message in for a previously-allocated query,
* and submits it. Cannot fail. Takes over the memory for qumsg_vb.
*/
qu->vb= *qumsg_vb;
adns__vbuf_init(qumsg_vb);
qu->query_dgram= MyMalloc(qu->vb.used);
qu->id= id;
qu->query_dglen= qu->vb.used;
memcpy(qu->query_dgram,qu->vb.buf,qu->vb.used);
adns__query_send(qu,now);
}
adns_status adns__internal_submit(adns_state ads, adns_query *query_r,
const typeinfo *typei, vbuf *qumsg_vb, int id,
adns_queryflags flags, struct timeval now,
const qcontext *ctx) {
adns_query qu;
qu= query_alloc(ads,typei,flags,now);
if (!qu) { adns__vbuf_free(qumsg_vb); return adns_s_nomemory; }
*query_r= qu;
memcpy(&qu->ctx,ctx,sizeof(qu->ctx));
query_submit(ads,qu, typei,qumsg_vb,id,flags,now);
return adns_s_ok;
}
static void query_simple(adns_state ads, adns_query qu,
const byte *owner, int ol,
const typeinfo *typei, adns_queryflags flags,
struct timeval now) {
vbuf vb_new;
int id;
adns_status status;
status= adns__mkquery(ads,&qu->vb,&id, (const char *)owner,ol, typei,flags);
if (status) {
if (status == adns_s_querydomaintoolong && (flags & adns_qf_search)) {
adns__search_next(ads,qu,now);
return;
} else {
adns__query_fail(qu,status);
return;
}
}
vb_new= qu->vb;
adns__vbuf_init(&qu->vb);
query_submit(ads,qu, typei,&vb_new,id, flags,now);
}
void adns__search_next(adns_state ads, adns_query qu, struct timeval now) {
const char *nextentry;
adns_status status;
if (qu->search_doneabs<0) {
nextentry= 0;
qu->search_doneabs= 1;
} else {
if (qu->search_pos >= ads->nsearchlist) {
if (qu->search_doneabs) {
status= adns_s_nxdomain;
goto x_fail;
} else {
nextentry= 0;
qu->search_doneabs= 1;
}
} else {
nextentry= ads->searchlist[qu->search_pos++];
}
}
qu->search_vb.used= qu->search_origlen;
if (nextentry) {
if (!adns__vbuf_append(&qu->search_vb,(const byte *)".",1) ||
!adns__vbuf_appendstr(&qu->search_vb,nextentry)) {
status= adns_s_nomemory; goto x_fail;
}
}
MyFree(qu->query_dgram);
qu->query_dgram= 0; qu->query_dglen= 0;
query_simple(ads,qu, qu->search_vb.buf, qu->search_vb.used, qu->typei, qu->flags, now);
return;
x_fail:
adns__query_fail(qu,status);
}
static int save_owner(adns_query qu, const char *owner, int ol) {
/* Returns 1 if OK, otherwise there was no memory. */
adns_answer *ans;
ans= qu->answer;
assert(!ans->owner);
ans->owner= adns__alloc_preserved(qu,ol+1); if (!ans->owner) return 0;
memcpy(ans->owner,owner,ol);
ans->owner[ol]= 0;
return 1;
}
int adns_submit(adns_state ads,
const char *owner,
adns_rrtype type,
adns_queryflags flags,
void *context,
adns_query *query_r) {
int r, ol, ndots;
adns_status status;
const typeinfo *typei;
struct timeval now;
adns_query qu;
const char *p;
adns__consistency(ads,0,cc_entex);
typei= adns__findtype(type);
if (!typei) return ENOSYS;
r= gettimeofday(&now,0); if (r) goto x_errno;
qu= query_alloc(ads,typei,flags,now); if (!qu) goto x_errno;
qu->ctx.ext= context;
qu->ctx.callback= 0;
memset(&qu->ctx.info,0,sizeof(qu->ctx.info));
*query_r= qu;
ol= strlen(owner);
if (!ol) { status= adns_s_querydomaininvalid; goto x_adnsfail; }
if (ol>DNS_MAXDOMAIN+1) { status= adns_s_querydomaintoolong; goto x_adnsfail; }
if (ol>=1 && owner[ol-1]=='.' && (ol<2 || owner[ol-2]!='\\')) {
flags &= ~adns_qf_search;
qu->flags= flags;
ol--;
}
if (flags & adns_qf_search) {
r= adns__vbuf_append(&qu->search_vb,(const byte *)owner,ol);
if (!r) { status= adns_s_nomemory; goto x_adnsfail; }
for (ndots=0, p=owner; (p= strchr(p,'.')); p++, ndots++);
qu->search_doneabs= (ndots >= ads->searchndots) ? -1 : 0;
qu->search_origlen= ol;
adns__search_next(ads,qu,now);
} else {
if (flags & adns_qf_owner) {
if (!save_owner(qu,owner,ol)) { status= adns_s_nomemory; goto x_adnsfail; }
}
query_simple(ads,qu, (const byte *)owner,ol, typei,flags, now);
}
adns__autosys(ads,now);
adns__consistency(ads,qu,cc_entex);
return 0;
x_adnsfail:
adns__query_fail(qu,status);
adns__consistency(ads,qu,cc_entex);
return 0;
x_errno:
r= errno;
assert(r);
adns__consistency(ads,0,cc_entex);
return r;
}
#ifdef IPV6
int adns_submit_reverse_ip6(adns_state ads,
const struct sockaddr *addr,
const char *zone,
adns_rrtype type,
adns_queryflags flags,
void *context,
adns_query *query_r) {
char shortbuf[100];
char *buf, *buf_free;
const unsigned char *cp;
char *qp;
int n, c, lreq, r;
if(addr->sa_family != AF_INET6) return ENOSYS;
cp = (const unsigned char *)&(((const struct sockaddr_in6*)addr) -> sin6_addr.s6_addr);
lreq = 71 + strlen(zone) + 1;
if (lreq > sizeof(shortbuf)) {
buf= MyMalloc(strlen(zone) + 4*4 + 1);
#if 0
if (!buf) return errno;
#endif
buf_free= buf;
} else {
buf= shortbuf;
buf_free= 0;
}
qp = buf;
for (n = 15; n >= 0; n--)
{
c = ircsprintf(qp, "%x.%x.", cp[n] & 0xf, (cp[n] >> 4) & 0xf);
qp += c;
}
strcpy(qp, zone);
r= adns_submit(ads,buf,type,flags,context,query_r);
if(buf_free) MyFree(buf_free);
return r;
}
#endif
int adns_submit_reverse_any(adns_state ads,
const struct sockaddr *addr,
const char *zone,
adns_rrtype type,
adns_queryflags flags,
void *context,
adns_query *query_r) {
const unsigned char *iaddr;
char *buf, *buf_free;
char shortbuf[100];
int r, lreq;
flags &= ~adns_qf_search;
if (addr->sa_family != AF_INET) return ENOSYS;
iaddr= (const unsigned char*) &(((const struct sockaddr_in*)addr) -> sin_addr);
lreq= strlen(zone) + 4*4 + 1;
if (lreq > sizeof(shortbuf)) {
buf= MyMalloc(strlen(zone) + 4*4 + 1);
#if 0
if (!buf) return errno;
#endif
buf_free= buf;
} else {
buf= shortbuf;
buf_free= 0;
}
ircsprintf(buf, "%d.%d.%d.%d.%s", iaddr[3], iaddr[2], iaddr[1], iaddr[0], zone);
r= adns_submit(ads,buf,type,flags,context,query_r);
MyFree(buf_free);
return r;
}
int adns_submit_reverse(adns_state ads,
const struct sockaddr *addr,
adns_rrtype type,
adns_queryflags flags,
void *context,
adns_query *query_r) {
if (type != adns_r_ptr && type != adns_r_ptr_raw && type != adns_r_ptr_ip6 ) return EINVAL;
#ifdef IPV6
if(addr->sa_family == AF_INET6)
return adns_submit_reverse_ip6(ads,addr,"ip6.int", type,flags,context,query_r);
else
#endif
return adns_submit_reverse_any(ads,addr,"in-addr.arpa",type,flags,context,query_r);
}
#if 0
int adns_synchronous(adns_state ads,
const char *owner,
adns_rrtype type,
adns_queryflags flags,
adns_answer **answer_r) {
adns_query qu;
int r;
r= adns_submit(ads,owner,type,flags,0,&qu);
if (r) return r;
r= adns_wait(ads,&qu,answer_r,0);
if (r) adns_cancel(qu);
return r;
}
#endif
static void *alloc_common(adns_query qu, size_t sz) {
allocnode *an;
if (!sz) return qu; /* Any old pointer will do */
assert(!qu->final_allocspace);
an= MyMalloc(MEM_ROUND(MEM_ROUND(sizeof(*an)) + sz));
#if 0
if (!an) return 0;
#endif
LIST_LINK_TAIL(qu->allocations,an);
return (byte*)an + MEM_ROUND(sizeof(*an));
}
void *adns__alloc_interim(adns_query qu, size_t sz) {
void *rv;
sz= MEM_ROUND(sz);
rv= alloc_common(qu,sz);
if (!rv) return 0;
qu->interim_allocd += sz;
return rv;
}
void *adns__alloc_preserved(adns_query qu, size_t sz) {
void *rv;
sz= MEM_ROUND(sz);
rv= adns__alloc_interim(qu,sz);
if (!rv) return 0;
qu->preserved_allocd += sz;
return rv;
}
void *adns__alloc_mine(adns_query qu, size_t sz) {
return alloc_common(qu,MEM_ROUND(sz));
}
void adns__transfer_interim(adns_query from, adns_query to, void *block, size_t sz) {
allocnode *an;
if (!block) return;
an= (void*)((byte*)block - MEM_ROUND(sizeof(*an)));
assert(!to->final_allocspace);
assert(!from->final_allocspace);
LIST_UNLINK(from->allocations,an);
LIST_LINK_TAIL(to->allocations,an);
sz= MEM_ROUND(sz);
from->interim_allocd -= sz;
to->interim_allocd += sz;
if (to->expires > from->expires) to->expires= from->expires;
}
void *adns__alloc_final(adns_query qu, size_t sz) {
/* When we're in the _final stage, we _subtract_ from interim_alloc'd
* each allocation, and use final_allocspace to point to the next free
* bit.
*/
void *rp;
sz= MEM_ROUND(sz);
rp= qu->final_allocspace;
assert(rp);
qu->interim_allocd -= sz;
assert(qu->interim_allocd>=0);
qu->final_allocspace= (byte*)rp + sz;
return rp;
}
static void cancel_children(adns_query qu) {
adns_query cqu, ncqu;
for (cqu= qu->children.head; cqu; cqu= ncqu) {
ncqu= cqu->siblings.next;
adns_cancel(cqu);
}
}
void adns__reset_preserved(adns_query qu) {
assert(!qu->final_allocspace);
cancel_children(qu);
qu->answer->nrrs= 0;
qu->answer->rrs.untyped= 0;
qu->interim_allocd= qu->preserved_allocd;
}
static void free_query_allocs(adns_query qu) {
allocnode *an, *ann;
cancel_children(qu);
for (an= qu->allocations.head; an; an= ann) { ann= an->next; MyFree(an);}
ADNS_LIST_INIT(qu->allocations);
adns__vbuf_free(&qu->vb);
adns__vbuf_free(&qu->search_vb);
MyFree(qu->query_dgram);
qu->query_dgram= 0;
}
void adns_cancel(adns_query qu) {
adns_state ads;
assert(qu != NULL);
ads= qu->ads;
adns__consistency(ads,qu,cc_entex);
if (qu->parent) LIST_UNLINK_PART(qu->parent->children,qu,siblings.);
switch (qu->state) {
case query_tosend:
LIST_UNLINK(ads->udpw,qu);
break;
case query_tcpw:
LIST_UNLINK(ads->tcpw,qu);
break;
case query_childw:
LIST_UNLINK(ads->childw,qu);
break;
case query_done:
LIST_UNLINK(ads->output,qu);
break;
default:
break;
#if 0
abort();
#endif
}
free_query_allocs(qu);
MyFree(qu->answer);
MyFree(qu);
adns__consistency(ads,0,cc_entex);
}
void adns__update_expires(adns_query qu, unsigned long ttl, struct timeval now) {
time_t max;
assert(ttl <= MAXTTLBELIEVE);
max= now.tv_sec + ttl;
if (qu->expires < max) return;
qu->expires= max;
}
static void makefinal_query(adns_query qu) {
adns_answer *ans;
int rrn;
ans= qu->answer;
if (qu->interim_allocd) {
ans= MyRealloc(qu->answer, MEM_ROUND(MEM_ROUND(sizeof(*ans)) + qu->interim_allocd));
if (!ans) goto x_nomem;
qu->answer= ans;
}
qu->final_allocspace= (byte*)ans + MEM_ROUND(sizeof(*ans));
adns__makefinal_str(qu,&ans->cname);
adns__makefinal_str(qu,&ans->owner);
if (ans->nrrs) {
adns__makefinal_block(qu, &ans->rrs.untyped, ans->nrrs*ans->rrsz);
for (rrn=0; rrn<ans->nrrs; rrn++)
qu->typei->makefinal(qu, ans->rrs.bytes + rrn*ans->rrsz);
}
free_query_allocs(qu);
return;
x_nomem:
qu->preserved_allocd= 0;
qu->answer->cname= 0;
qu->answer->owner= 0;
adns__reset_preserved(qu); /* (but we just threw away the preserved stuff) */
qu->answer->status= adns_s_nomemory;
free_query_allocs(qu);
}
void adns__query_done(adns_query qu) {
adns_answer *ans;
adns_query parent;
cancel_children(qu);
qu->id= -1;
ans= qu->answer;
if (qu->flags & adns_qf_owner && qu->flags & adns_qf_search &&
ans->status != adns_s_nomemory) {
if (!save_owner(qu, (const char *)qu->search_vb.buf, qu->search_vb.used)) {
adns__query_fail(qu,adns_s_nomemory);
return;
}
}
if (ans->nrrs && qu->typei->diff_needswap) {
if (!adns__vbuf_ensure(&qu->vb,qu->typei->rrsz)) {
adns__query_fail(qu,adns_s_nomemory);
return;
}
adns__isort(ans->rrs.bytes, ans->nrrs, ans->rrsz,
qu->vb.buf,
(int(*)(void*, const void*, const void*))qu->typei->diff_needswap,
qu->ads);
}
ans->expires= qu->expires;
parent= qu->parent;
if (parent) {
LIST_UNLINK_PART(parent->children,qu,siblings.);
LIST_UNLINK(qu->ads->childw,parent);
qu->ctx.callback(parent,qu);
free_query_allocs(qu);
MyFree(qu->answer);
MyFree(qu);
} else {
makefinal_query(qu);
LIST_LINK_TAIL(qu->ads->output,qu);
qu->state= query_done;
}
}
void adns__query_fail(adns_query qu, adns_status status) {
adns__reset_preserved(qu);
qu->answer->status= status;
adns__query_done(qu);
}
void adns__makefinal_str(adns_query qu, char **strp) {
int l;
char *before, *after;
before= *strp;
if (!before) return;
l= strlen(before)+1;
after= adns__alloc_final(qu,l);
memcpy(after,before,l);
*strp= after;
}
void adns__makefinal_block(adns_query qu, void **blpp, size_t sz) {
void *before, *after;
before= *blpp;
if (!before) return;
after= adns__alloc_final(qu,sz);
memcpy(after,before,sz);
*blpp= after;
}

373
adns/reply.c Normal file
View file

@ -0,0 +1,373 @@
/*
* reply.c
* - main handling and parsing routine for received datagrams
*/
/*
* This file is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999-2000 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
* $Id: reply.c,v 1.1 2002/08/13 14:35:07 fishwaldo Exp $
*/
#include "stdinc.h"
#include "memory.h"
#include "fileio.h"
#include "internal.h"
void adns__procdgram(adns_state ads, const byte *dgram, int dglen,
int serv, int viatcp, struct timeval now) {
int cbyte, rrstart, wantedrrs, rri, foundsoa, foundns, cname_here;
int id, f1, f2, qdcount, ancount, nscount, arcount;
int flg_ra, flg_rd, flg_tc, flg_qr, opcode;
int rrtype, rrclass, rdlength, rdstart;
int anstart, nsstart, arstart;
int ownermatched, l, nrrs;
unsigned long ttl, soattl;
const typeinfo *typei;
adns_query qu, nqu;
dns_rcode rcode;
adns_status st;
vbuf tempvb;
byte *newquery, *rrsdata;
parseinfo pai;
if (dglen<DNS_HDRSIZE) {
adns__diag(ads,serv,0,"received datagram too short for message header (%d)",dglen);
return;
}
cbyte= 0;
GET_W(cbyte,id);
GET_B(cbyte,f1);
GET_B(cbyte,f2);
GET_W(cbyte,qdcount);
GET_W(cbyte,ancount);
GET_W(cbyte,nscount);
GET_W(cbyte,arcount);
assert(cbyte == DNS_HDRSIZE);
flg_qr= f1&0x80;
opcode= (f1&0x78)>>3;
flg_tc= f1&0x02;
flg_rd= f1&0x01;
flg_ra= f2&0x80;
rcode= (f2&0x0f);
cname_here= 0;
if (!flg_qr) {
adns__diag(ads,serv,0,"server sent us a query, not a response");
return;
}
if (opcode) {
adns__diag(ads,serv,0,"server sent us unknown opcode %d (wanted 0=QUERY)",opcode);
return;
}
qu= 0;
/* See if we can find the relevant query, or leave qu=0 otherwise ... */
if (qdcount == 1) {
for (qu= viatcp ? ads->tcpw.head : ads->udpw.head; qu; qu= nqu) {
nqu= qu->next;
if (qu->id != id) continue;
if (dglen < qu->query_dglen) continue;
if (memcmp(qu->query_dgram+DNS_HDRSIZE,
dgram+DNS_HDRSIZE,
qu->query_dglen-DNS_HDRSIZE))
continue;
if (viatcp) {
assert(qu->state == query_tcpw);
} else {
assert(qu->state == query_tosend);
if (!(qu->udpsent & (1<<serv))) continue;
}
break;
}
if (qu) {
/* We're definitely going to do something with this query now */
if (viatcp) LIST_UNLINK(ads->tcpw,qu);
else LIST_UNLINK(ads->udpw,qu);
}
}
/* If we're going to ignore the packet, we return as soon as we have
* failed the query (if any) and printed the warning message (if
* any).
*/
switch (rcode) {
case rcode_noerror:
case rcode_nxdomain:
break;
case rcode_formaterror:
adns__warn(ads,serv,qu,"server cannot understand our query (Format Error)");
if (qu) adns__query_fail(qu,adns_s_rcodeformaterror);
return;
case rcode_servfail:
if (qu) adns__query_fail(qu,adns_s_rcodeservfail);
else adns__debug(ads,serv,qu,"server failure on unidentifiable query");
return;
case rcode_notimp:
adns__warn(ads,serv,qu,"server claims not to implement our query");
if (qu) adns__query_fail(qu,adns_s_rcodenotimplemented);
return;
case rcode_refused:
adns__debug(ads,serv,qu,"server refused our query");
if (qu) adns__query_fail(qu,adns_s_rcoderefused);
return;
default:
adns__warn(ads,serv,qu,"server gave unknown response code %d",rcode);
if (qu) adns__query_fail(qu,adns_s_rcodeunknown);
return;
}
if (!qu) {
if (!qdcount) {
adns__diag(ads,serv,0,"server sent reply without quoting our question");
} else if (qdcount>1) {
adns__diag(ads,serv,0,"server claimed to answer %d questions with one message",
qdcount);
} else if (ads->iflags & adns_if_debug) {
adns__vbuf_init(&tempvb);
adns__debug(ads,serv,0,"reply not found, id %02x, query owner %s",
id, adns__diag_domain(ads,serv,0,&tempvb,dgram,dglen,DNS_HDRSIZE));
adns__vbuf_free(&tempvb);
}
return;
}
/* We're definitely going to do something with this packet and this query now. */
anstart= qu->query_dglen;
arstart= -1;
/* Now, take a look at the answer section, and see if it is complete.
* If it has any CNAMEs we stuff them in the answer.
*/
wantedrrs= 0;
cbyte= anstart;
for (rri= 0; rri<ancount; rri++) {
rrstart= cbyte;
st= adns__findrr(qu,serv, dgram,dglen,&cbyte,
&rrtype,&rrclass,&ttl, &rdlength,&rdstart,
&ownermatched);
if (st) { adns__query_fail(qu,st); return; }
if (rrtype == -1) goto x_truncated;
if (rrclass != DNS_CLASS_IN) {
adns__diag(ads,serv,qu,"ignoring answer RR with wrong class %d (expected IN=%d)",
rrclass,DNS_CLASS_IN);
continue;
}
if (!ownermatched) {
if (ads->iflags & adns_if_debug) {
adns__debug(ads,serv,qu,"ignoring RR with an unexpected owner %s",
adns__diag_domain(ads,serv,qu, &qu->vb, dgram,dglen,rrstart));
}
continue;
}
if (rrtype == adns_r_cname &&
(qu->typei->type & adns__rrt_typemask) != adns_r_cname) {
if (qu->flags & adns_qf_cname_forbid) {
adns__query_fail(qu,adns_s_prohibitedcname);
return;
} else if (qu->cname_dgram && ++qu->cname_count >= 2) {
adns__debug(ads,serv,qu,"allegedly canonical name %s is actually alias for %s",
qu->answer->cname,
adns__diag_domain(ads,serv,qu, &qu->vb, dgram,dglen,rdstart));
adns__query_fail(qu,adns_s_prohibitedcname);
return;
} else if (wantedrrs) { /* Ignore CNAME(s) after RR(s). */
adns__debug(ads,serv,qu,"ignoring CNAME (to %s) coexisting with RR",
adns__diag_domain(ads,serv,qu, &qu->vb, dgram,dglen,rdstart));
} else {
qu->cname_begin= rdstart;
qu->cname_dglen= dglen;
st= adns__parse_domain(ads,serv,qu, &qu->vb,
qu->flags & adns_qf_quotefail_cname ? 0 : pdf_quoteok,
dgram,dglen, &rdstart,rdstart+rdlength);
if (!qu->vb.used) goto x_truncated;
if (st) { adns__query_fail(qu,st); return; }
l= strlen((char*)qu->vb.buf)+1;
qu->answer->cname= adns__alloc_preserved(qu,l);
if (!qu->answer->cname) { adns__query_fail(qu,adns_s_nomemory); return; }
qu->cname_dgram= adns__alloc_mine(qu,dglen);
memcpy(qu->cname_dgram,dgram,dglen);
memcpy(qu->answer->cname,qu->vb.buf,l);
cname_here= 1;
adns__update_expires(qu,ttl,now);
/* If we find the answer section truncated after this point we restart
* the query at the CNAME; if beforehand then we obviously have to use
* TCP. If there is no truncation we can use the whole answer if
* it contains the relevant info.
*/
}
} else if (rrtype == (qu->typei->type & adns__rrt_typemask)) {
wantedrrs++;
} else {
adns__debug(ads,serv,qu,"ignoring answer RR with irrelevant type %d",rrtype);
}
}
/* We defer handling truncated responses here, in case there was a CNAME
* which we could use.
*/
if (flg_tc) goto x_truncated;
nsstart= cbyte;
if (!wantedrrs) {
/* Oops, NODATA or NXDOMAIN or perhaps a referral (which would be a problem) */
/* RFC2308: NODATA has _either_ a SOA _or_ _no_ NS records in authority section */
foundsoa= 0; soattl= 0; foundns= 0;
for (rri= 0; rri<nscount; rri++) {
rrstart= cbyte;
st= adns__findrr(qu,serv, dgram,dglen,&cbyte,
&rrtype,&rrclass,&ttl, &rdlength,&rdstart, 0);
if (st) { adns__query_fail(qu,st); return; }
if (rrtype==-1) goto x_truncated;
if (rrclass != DNS_CLASS_IN) {
adns__diag(ads,serv,qu,
"ignoring authority RR with wrong class %d (expected IN=%d)",
rrclass,DNS_CLASS_IN);
continue;
}
if (rrtype == adns_r_soa_raw) { foundsoa= 1; soattl= ttl; break; }
else if (rrtype == adns_r_ns_raw) { foundns= 1; }
}
if (rcode == rcode_nxdomain) {
/* We still wanted to look for the SOA so we could find the TTL. */
adns__update_expires(qu,soattl,now);
if (qu->flags & adns_qf_search) {
adns__search_next(ads,qu,now);
} else {
adns__query_fail(qu,adns_s_nxdomain);
}
return;
}
if (foundsoa || !foundns) {
/* Aha ! A NODATA response, good. */
adns__update_expires(qu,soattl,now);
adns__query_fail(qu,adns_s_nodata);
return;
}
/* Now what ? No relevant answers, no SOA, and at least some NS's.
* Looks like a referral. Just one last chance ... if we came across
* a CNAME in this datagram then we should probably do our own CNAME
* lookup now in the hope that we won't get a referral again.
*/
if (cname_here) goto x_restartquery;
/* Bloody hell, I thought we asked for recursion ? */
if (!flg_ra) {
adns__diag(ads,serv,qu,"server is not willing to do recursive lookups for us");
adns__query_fail(qu,adns_s_norecurse);
} else {
if (!flg_rd)
adns__diag(ads,serv,qu,"server thinks we didn't ask for recursive lookup");
else
adns__debug(ads,serv,qu,"server claims to do recursion, but gave us a referral");
adns__query_fail(qu,adns_s_invalidresponse);
}
return;
}
/* Now, we have some RRs which we wanted. */
qu->answer->rrs.untyped= adns__alloc_interim(qu,qu->typei->rrsz*wantedrrs);
if (!qu->answer->rrs.untyped) { adns__query_fail(qu,adns_s_nomemory); return; }
typei= qu->typei;
cbyte= anstart;
rrsdata= qu->answer->rrs.bytes;
pai.ads= qu->ads;
pai.qu= qu;
pai.serv= serv;
pai.dgram= dgram;
pai.dglen= dglen;
pai.nsstart= nsstart;
pai.nscount= nscount;
pai.arcount= arcount;
pai.now= now;
for (rri=0, nrrs=0; rri<ancount; rri++) {
st= adns__findrr(qu,serv, dgram,dglen,&cbyte,
&rrtype,&rrclass,&ttl, &rdlength,&rdstart,
&ownermatched);
assert(!st); assert(rrtype != -1);
if (rrclass != DNS_CLASS_IN ||
rrtype != (qu->typei->type & adns__rrt_typemask) ||
!ownermatched)
continue;
adns__update_expires(qu,ttl,now);
st= typei->parse(&pai, rdstart,rdstart+rdlength, rrsdata+nrrs*typei->rrsz);
if (st) { adns__query_fail(qu,st); return; }
if (rdstart==-1) goto x_truncated;
nrrs++;
}
assert(nrrs==wantedrrs);
qu->answer->nrrs= nrrs;
/* This may have generated some child queries ... */
if (qu->children.head) {
qu->state= query_childw;
LIST_LINK_TAIL(ads->childw,qu);
return;
}
adns__query_done(qu);
return;
x_truncated:
if (!flg_tc) {
adns__diag(ads,serv,qu,"server sent datagram which points outside itself");
adns__query_fail(qu,adns_s_invalidresponse);
return;
}
qu->flags |= adns_qf_usevc;
x_restartquery:
if (qu->cname_dgram) {
st= adns__mkquery_frdgram(qu->ads,&qu->vb,&qu->id,
qu->cname_dgram, qu->cname_dglen, qu->cname_begin,
qu->typei->type, qu->flags);
if (st) { adns__query_fail(qu,st); return; }
newquery= MyRealloc(qu->query_dgram,qu->vb.used);
if (!newquery) { adns__query_fail(qu,adns_s_nomemory); return; }
qu->query_dgram= newquery;
qu->query_dglen= qu->vb.used;
memcpy(newquery,qu->vb.buf,qu->vb.used);
}
if (qu->state == query_tcpw) qu->state= query_tosend;
qu->retries= 0;
adns__reset_preserved(qu);
adns__query_send(qu,now);
}

697
adns/setup.c Normal file
View file

@ -0,0 +1,697 @@
/*
* setup.c
* - configuration file parsing
* - management of global state
*/
/*
* This file is
* Copyright (C) 1997-1999 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999-2000 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
* $Id: setup.c,v 1.1 2002/08/13 14:35:07 fishwaldo Exp $
*/
#include "stdinc.h"
#include "memory.h"
#include "fileio.h"
#include "s_bsd.h"
#include "internal.h"
#include "s_log.h"
/* For some reason BSD/OS doesn't define INADDR_LOOPBACK */
#ifndef INADDR_LOOPBACK
#define INADDR_LOOPBACK 0x7f000001
#endif
static void readconfig(adns_state ads, const char *filename, int warnmissing);
static void addserver(adns_state ads, struct in_addr addr)
{
int i;
struct server *ss;
if(addr.s_addr == 0)
addr.s_addr = htonl(INADDR_LOOPBACK);
for (i=0; i<ads->nservers; i++)
{
if (ads->servers[i].addr.s_addr == addr.s_addr)
{
adns__debug(ads,-1,0,
"duplicate nameserver %s ignored",inetntoa((char *)&addr));
return;
}
}
if (ads->nservers>=MAXSERVERS)
{
adns__diag(ads,-1,0,"too many nameservers, ignoring %s",inetntoa((char *)&addr));
return;
}
ss= ads->servers+ads->nservers;
ss->addr= addr;
ads->nservers++;
}
static void freesearchlist(adns_state ads)
{
if (ads->nsearchlist) MyFree(*ads->searchlist);
MyFree(ads->searchlist);
}
static void saveerr(adns_state ads, int en)
{
if (!ads->configerrno) ads->configerrno= en;
}
static void configparseerr(adns_state ads, const char *fn, int lno,
const char *fmt, ...)
{
#if 0
va_list al;
#endif
saveerr(ads,EINVAL);
if (!ads->diagfile || (ads->iflags & adns_if_noerrprint)) return;
#if 0
if (lno==-1) fprintf(ads->diagfile,"adns: %s: ",fn);
else fprintf(ads->diagfile,"adns: %s:%d: ",fn,lno);
va_start(al,fmt);
vfprintf(ads->diagfile,fmt,al);
va_end(al);
fputc('\n',ads->diagfile);
#endif
}
static int nextword(const char **bufp_io, const char **word_r, int *l_r) {
const char *p, *q;
p= *bufp_io;
while (ctype_whitespace(*p)) p++;
if (!*p) return 0;
q= p;
while (*q && !ctype_whitespace(*q)) q++;
*l_r= q-p;
*word_r= p;
*bufp_io= q;
return 1;
}
static void ccf_nameserver(adns_state ads, const char *fn, int lno, const char *buf) {
struct in_addr ia;
if (inetpton(AF_INET, buf,&ia) <=0) {
configparseerr(ads,fn,lno,"invalid nameserver address `%s'",buf);
return;
}
adns__debug(ads,-1,0,"using nameserver %s",inetntoa((char *)&ia));
addserver(ads,ia);
}
static void ccf_search(adns_state ads, const char *fn, int lno, const char *buf) {
const char *bufp, *word;
char *newchars, **newptrs, **pp;
int count, tl, l;
if (!buf) return;
bufp= buf;
count= 0;
tl= 0;
while (nextword(&bufp,&word,&l)) { count++; tl += l+1; }
newptrs = MyMalloc(sizeof(char*)*count);
if (!newptrs)
{
saveerr(ads,errno);
return;
}
newchars= MyMalloc(tl);
if (!newchars)
{
saveerr(ads,errno);
MyFree(newptrs);
return;
}
bufp= buf;
pp= newptrs;
while (nextword(&bufp,&word,&l)) {
*pp++= newchars;
memcpy(newchars,word,l);
newchars += l;
*newchars++ = 0;
}
freesearchlist(ads);
ads->nsearchlist= count;
ads->searchlist= newptrs;
}
static void ccf_sortlist(adns_state ads, const char *fn, int lno, const char *buf) {
const char *word;
char tbuf[200], *slash, *ep;
struct in_addr base, mask;
int l;
unsigned long initial, baselocal;
if (!buf) return;
ads->nsortlist= 0;
while (nextword(&buf,&word,&l)) {
if (ads->nsortlist >= MAXSORTLIST) {
adns__diag(ads,-1,0,"too many sortlist entries, ignoring %.*s onwards",l,word);
return;
}
if (l >= sizeof(tbuf)) {
configparseerr(ads,fn,lno,"sortlist entry `%.*s' too long",l,word);
continue;
}
memcpy(tbuf,word,l); tbuf[l]= 0;
slash= strchr(tbuf,'/');
if (slash) *slash++= 0;
if (inetpton(AF_INET, tbuf,&base) <= 0) {
configparseerr(ads,fn,lno,"invalid address `%s' in sortlist",tbuf);
continue;
}
if (slash) {
if (strchr(slash,'.')) {
if (inetpton(AF_INET, slash,&mask) <= 0) {
configparseerr(ads,fn,lno,"invalid mask `%s' in sortlist",slash);
continue;
}
if (base.s_addr & ~mask.s_addr) {
configparseerr(ads,fn,lno,
"mask `%s' in sortlist overlaps address `%s'",slash,tbuf);
continue;
}
} else {
initial= strtoul(slash,&ep,10);
if (*ep || initial>32) {
configparseerr(ads,fn,lno,"mask length `%s' invalid",slash);
continue;
}
mask.s_addr= htonl((0x0ffffffffUL) << (32-initial));
}
} else {
baselocal= ntohl(base.s_addr);
if (!baselocal & 0x080000000UL) /* class A */
mask.s_addr= htonl(0x0ff000000UL);
else if ((baselocal & 0x0c0000000UL) == 0x080000000UL)
mask.s_addr= htonl(0x0ffff0000UL); /* class B */
else if ((baselocal & 0x0f0000000UL) == 0x0e0000000UL)
mask.s_addr= htonl(0x0ff000000UL); /* class C */
else {
configparseerr(ads,fn,lno,
"network address `%s' in sortlist is not in classed ranges,"
" must specify mask explicitly", tbuf);
continue;
}
}
ads->sortlist[ads->nsortlist].base= base;
ads->sortlist[ads->nsortlist].mask= mask;
ads->nsortlist++;
}
}
static void ccf_options(adns_state ads, const char *fn, int lno, const char *buf) {
const char *word;
char *ep;
unsigned long v;
int l;
if (!buf) return;
while (nextword(&buf,&word,&l)) {
if (l==5 && !memcmp(word,"debug",5)) {
ads->iflags |= adns_if_debug;
continue;
}
if (l>=6 && !memcmp(word,"ndots:",6)) {
v= strtoul(word+6,&ep,10);
if (l==6 || ep != word+l || v > INT_MAX) {
configparseerr(ads,fn,lno,"option `%.*s' malformed or has bad value",l,word);
continue;
}
ads->searchndots= v;
continue;
}
if (l>=12 && !memcmp(word,"adns_checkc:",12)) {
if (!strcmp(word+12,"none")) {
ads->iflags &= ~adns_if_checkc_freq;
ads->iflags |= adns_if_checkc_entex;
} else if (!strcmp(word+12,"entex")) {
ads->iflags &= ~adns_if_checkc_freq;
ads->iflags |= adns_if_checkc_entex;
} else if (!strcmp(word+12,"freq")) {
ads->iflags |= adns_if_checkc_freq;
} else {
configparseerr(ads,fn,lno, "option adns_checkc has bad value `%s' "
"(must be none, entex or freq", word+12);
}
continue;
}
adns__diag(ads,-1,0,"%s:%d: unknown option `%.*s'", fn,lno, l,word);
}
}
static void ccf_clearnss(adns_state ads, const char *fn, int lno, const char *buf) {
ads->nservers= 0;
}
static void ccf_include(adns_state ads, const char *fn, int lno, const char *buf) {
if (!*buf) {
configparseerr(ads,fn,lno,"`include' directive with no filename");
return;
}
readconfig(ads,buf,1);
}
static const struct configcommandinfo {
const char *name;
void (*fn)(adns_state ads, const char *fn, int lno, const char *buf);
} configcommandinfos[]= {
{ "nameserver", ccf_nameserver },
{ "domain", ccf_search },
{ "search", ccf_search },
{ "sortlist", ccf_sortlist },
{ "options", ccf_options },
{ "clearnameservers", ccf_clearnss },
{ "include", ccf_include },
{ 0 }
};
typedef union {
FBFILE *file;
const char *text;
} getline_ctx;
static int gl_file(adns_state ads, getline_ctx *src_io, const char *filename,
int lno, char *buf, int buflen) {
FBFILE *file= src_io->file;
int c, i;
char *p;
p= buf;
buflen--;
i= 0;
for (;;) { /* loop over chars */
if (i == buflen) {
adns__diag(ads,-1,0,"%s:%d: line too long, ignored",filename,lno);
goto x_badline;
}
c= fbgetc(file);
if (!c) {
adns__diag(ads,-1,0,"%s:%d: line contains nul, ignored",filename,lno);
goto x_badline;
} else if (c == '\n') {
break;
} else if (c == EOF) {
if (!i) return -1;
break;
} else {
*p++= c;
i++;
}
}
*p++= 0;
return i;
x_badline:
saveerr(ads,EINVAL);
while ((c= fbgetc(file)) != EOF && c != '\n');
return -2;
}
static int gl_text(adns_state ads, getline_ctx *src_io, const char *filename,
int lno, char *buf, int buflen)
{
const char *cp= src_io->text;
int l;
if (!cp || !*cp) return -1;
if (*cp == ';' || *cp == '\n') cp++;
l= strcspn(cp,";\n");
src_io->text = cp+l;
if (l >= buflen) {
adns__diag(ads,-1,0,"%s:%d: line too long, ignored",filename,lno);
saveerr(ads,EINVAL);
return -2;
}
memcpy(buf,cp,l);
buf[l]= 0;
return l;
}
static void readconfiggeneric(adns_state ads, const char *filename,
int (*getline)(adns_state ads, getline_ctx*,
const char *filename, int lno,
char *buf, int buflen),
/* Returns >=0 for success, -1 for EOF or error
* (error will have been reported), or -2 for
* bad line was encountered, try again.
*/
getline_ctx gl_ctx)
{
char linebuf[2000], *p, *q;
int lno, l, dirl;
const struct configcommandinfo *ccip;
for (lno=1;
(l= getline(ads,&gl_ctx, filename,lno, linebuf,sizeof(linebuf))) != -1;
lno++) {
if (l == -2) continue;
while (l>0 && ctype_whitespace(linebuf[l-1])) l--;
linebuf[l]= 0;
p= linebuf;
while (ctype_whitespace(*p)) p++;
if (*p == '#' || !*p) continue;
q= p;
while (*q && !ctype_whitespace(*q)) q++;
dirl= q-p;
for (ccip=configcommandinfos;
ccip->name && !(strlen(ccip->name)==dirl && !memcmp(ccip->name,p,q-p));
ccip++);
if (!ccip->name) {
adns__diag(ads,-1,0,"%s:%d: unknown configuration directive `%.*s'",
filename,lno,q-p,p);
continue;
}
while (ctype_whitespace(*q)) q++;
ccip->fn(ads,filename,lno,q);
}
}
static const char *instrum_getenv(adns_state ads, const char *envvar) {
const char *value;
value= getenv(envvar);
if (!value) adns__debug(ads,-1,0,"environment variable %s not set",envvar);
else adns__debug(ads,-1,0,"environment variable %s set to `%s'",envvar,value);
return value;
}
static void readconfig(adns_state ads, const char *filename, int warnmissing) {
getline_ctx gl_ctx;
gl_ctx.file= fbopen(filename,"r");
if (gl_ctx.file == NULL) {
if (errno == ENOENT) {
if (warnmissing)
adns__debug(ads,-1,0,"configuration file `%s' does not exist",filename);
return;
}
saveerr(ads,errno);
adns__diag(ads,-1,0,"cannot open configuration file `%s': %s",
filename,strerror(errno));
return;
}
readconfiggeneric(ads,filename,gl_file,gl_ctx);
fbclose(gl_ctx.file);
}
static void readconfigtext(adns_state ads, const char *text, const char *showname) {
getline_ctx gl_ctx;
gl_ctx.text= text;
readconfiggeneric(ads,showname,gl_text,gl_ctx);
}
static void readconfigenv(adns_state ads, const char *envvar) {
const char *filename;
if (ads->iflags & adns_if_noenv) {
adns__debug(ads,-1,0,"not checking environment variable `%s'",envvar);
return;
}
filename= instrum_getenv(ads,envvar);
if (filename) readconfig(ads,filename,1);
}
static void readconfigenvtext(adns_state ads, const char *envvar) {
const char *textdata;
if (ads->iflags & adns_if_noenv) {
adns__debug(ads,-1,0,"not checking environment variable `%s'",envvar);
return;
}
textdata= instrum_getenv(ads,envvar);
if (textdata) readconfigtext(ads,textdata,envvar);
}
int adns__setnonblock(adns_state ads, int fd) {
if(!set_non_blocking(fd))
return errno;
return 0;
}
static int init_begin(adns_state *ads_r, adns_initflags flags, FBFILE *diagfile)
{
adns_state ads;
ads = MyMalloc(sizeof(*ads));
/* Under hybrid, MyMalloc would have aborted already */
#if 0
if (!ads) return errno;
#endif
ads->iflags= flags;
ads->diagfile= diagfile;
ads->configerrno= 0;
ADNS_LIST_INIT(ads->udpw);
ADNS_LIST_INIT(ads->tcpw);
ADNS_LIST_INIT(ads->childw);
ADNS_LIST_INIT(ads->output);
ads->forallnext= 0;
ads->nextid= 0x311f;
ads->udpsocket= ads->tcpsocket= -1;
adns__vbuf_init(&ads->tcpsend);
adns__vbuf_init(&ads->tcprecv);
ads->tcprecv_skip= 0;
ads->nservers= ads->nsortlist= ads->nsearchlist= ads->tcpserver= 0;
ads->searchndots= 1;
ads->tcpstate= server_disconnected;
timerclear(&ads->tcptimeout);
ads->searchlist= 0;
*ads_r= ads;
return 0;
}
static int init_finish(adns_state ads) {
struct in_addr ia;
int r;
if (!ads->nservers)
{
#if 0
if (ads->diagfile && ads->iflags & adns_if_debug)
fprintf(ads->diagfile,"adns: no nameservers, using localhost\n");
#endif
ia.s_addr= htonl(INADDR_LOOPBACK);
addserver(ads,ia);
}
ads->udpsocket = comm_open(AF_INET, SOCK_DGRAM, 0, "UDP Resolver socket");
if (ads->udpsocket<0) { ilog(L_CRIT, "Failed to open socket"); r= errno; goto x_free; }
r= adns__setnonblock(ads,ads->udpsocket);
if (r) { ilog(L_CRIT, "Failed to make socket non-blocking"); r= errno; goto x_closeudp; }
return 0;
x_closeudp:
fd_close(ads->udpsocket);
x_free:
MyFree(ads);
ilog(L_CRIT, "Returning from init_finish: r = %d", r);
return r;
}
static void init_abort(adns_state ads) {
if (ads->nsearchlist) {
MyFree(ads->searchlist[0]);
MyFree(ads->searchlist);
}
MyFree(ads);
}
int adns_init(adns_state *ads_r, adns_initflags flags, FBFILE *diagfile) {
adns_state ads;
const char *res_options, *adns_res_options;
int r;
r= init_begin(&ads, flags, diagfile);
if (r) return r;
res_options= instrum_getenv(ads,"RES_OPTIONS");
adns_res_options= instrum_getenv(ads,"ADNS_RES_OPTIONS");
ccf_options(ads,"RES_OPTIONS",-1,res_options);
ccf_options(ads,"ADNS_RES_OPTIONS",-1,adns_res_options);
#ifndef VMS
readconfig(ads,"/etc/resolv.conf",0);
readconfig(ads,"/etc/resolv-adns.conf",0);
#else
ilog(L_CRIT, "Opening IRCD$CONFDIR:RESOLV.CONF (VMS)");
readconfig(ads,"IRCD$CONFDIR:RESOLV.CONF",0);
#endif
readconfigenv(ads,"RES_CONF");
readconfigenv(ads,"ADNS_RES_CONF");
readconfigenvtext(ads,"RES_CONF_TEXT");
readconfigenvtext(ads,"ADNS_RES_CONF_TEXT");
ccf_options(ads,"RES_OPTIONS",-1,res_options);
ccf_options(ads,"ADNS_RES_OPTIONS",-1,adns_res_options);
ccf_search(ads,"LOCALDOMAIN",-1,instrum_getenv(ads,"LOCALDOMAIN"));
ccf_search(ads,"ADNS_LOCALDOMAIN",-1,instrum_getenv(ads,"ADNS_LOCALDOMAIN"));
if (ads->configerrno && ads->configerrno != EINVAL) {
ilog(L_CRIT, "Failed at 1");
r= ads->configerrno;
init_abort(ads);
return r;
}
r= init_finish(ads);
if (r) return r;
adns__consistency(ads,0,cc_entex);
*ads_r= ads;
return 0;
}
int adns_init_strcfg(adns_state *ads_r, adns_initflags flags,
FBFILE *diagfile, const char *configtext) {
adns_state ads;
int r;
r= init_begin(&ads, flags, diagfile); if (r) return r;
readconfigtext(ads,configtext,"<supplied configuration text>");
if (ads->configerrno) {
r= ads->configerrno;
init_abort(ads);
return r;
}
r= init_finish(ads); if (r) return r;
adns__consistency(ads,0,cc_entex);
*ads_r= ads;
return 0;
}
void adns_finish(adns_state ads) {
adns__consistency(ads,0,cc_entex);
for (;;) {
if (ads->udpw.head) adns_cancel(ads->udpw.head);
else if (ads->tcpw.head) adns_cancel(ads->tcpw.head);
else if (ads->childw.head) adns_cancel(ads->childw.head);
else if (ads->output.head) adns_cancel(ads->output.head);
else break;
}
fd_close(ads->udpsocket);
if (ads->tcpsocket >= 0) fd_close(ads->tcpsocket);
adns__vbuf_free(&ads->tcpsend);
adns__vbuf_free(&ads->tcprecv);
freesearchlist(ads);
MyFree(ads);
}
void adns_forallqueries_begin(adns_state ads) {
adns__consistency(ads,0,cc_entex);
ads->forallnext=
ads->udpw.head ? ads->udpw.head :
ads->tcpw.head ? ads->tcpw.head :
ads->childw.head ? ads->childw.head :
ads->output.head;
}
adns_query adns_forallqueries_next(adns_state ads, void **context_r) {
adns_query qu, nqu;
adns__consistency(ads,0,cc_entex);
nqu= ads->forallnext;
for (;;) {
qu= nqu;
if (!qu) return 0;
if (qu->next) {
nqu= qu->next;
} else if (qu == ads->udpw.tail) {
nqu=
ads->tcpw.head ? ads->tcpw.head :
ads->childw.head ? ads->childw.head :
ads->output.head;
} else if (qu == ads->tcpw.tail) {
nqu=
ads->childw.head ? ads->childw.head :
ads->output.head;
} else if (qu == ads->childw.tail) {
nqu= ads->output.head;
} else {
nqu= 0;
}
if (!qu->parent) break;
}
ads->forallnext= nqu;
if (context_r) *context_r= qu->ctx.ext;
return qu;
}
int adns__rereadconfig(adns_state ads)
{
struct in_addr ia;
adns__consistency(ads,0,cc_entex);
ads->nservers = 0;
#ifndef VMS
readconfig(ads,"/etc/resolv.conf",0);
#else
readconfig(ads,"[]resolv.conf",0);
#endif
if (!ads->nservers)
{
ia.s_addr= htonl(INADDR_LOOPBACK);
addserver(ads,ia);
}
adns__consistency(ads,0,cc_entex);
return 0;
}

273
adns/transmit.c Normal file
View file

@ -0,0 +1,273 @@
/*
* transmit.c
* - construct queries
* - send queries
*/
/*
* This file is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999-2000 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
* $Id: transmit.c,v 1.1 2002/08/13 14:35:08 fishwaldo Exp $
*/
#include "stdinc.h"
#include "fileio.h"
#include "internal.h"
#include "tvarith.h"
#define MKQUERY_START(vb) (rqp= (vb)->buf+(vb)->used)
#define MKQUERY_ADDB(b) *rqp++= (b)
#define MKQUERY_ADDW(w) (MKQUERY_ADDB(((w)>>8)&0x0ff), MKQUERY_ADDB((w)&0x0ff))
#define MKQUERY_STOP(vb) ((vb)->used= rqp-(vb)->buf)
static adns_status mkquery_header(adns_state ads, vbuf *vb, int *id_r, int qdlen) {
int id;
byte *rqp;
if (!adns__vbuf_ensure(vb,DNS_HDRSIZE+qdlen+4)) return adns_s_nomemory;
vb->used= 0;
MKQUERY_START(vb);
*id_r= id= (ads->nextid++) & 0x0ffff;
MKQUERY_ADDW(id);
MKQUERY_ADDB(0x01); /* QR=Q(0), OPCODE=QUERY(0000), !AA, !TC, RD */
MKQUERY_ADDB(0x00); /* !RA, Z=000, RCODE=NOERROR(0000) */
MKQUERY_ADDW(1); /* QDCOUNT=1 */
MKQUERY_ADDW(0); /* ANCOUNT=0 */
MKQUERY_ADDW(0); /* NSCOUNT=0 */
MKQUERY_ADDW(0); /* ARCOUNT=0 */
MKQUERY_STOP(vb);
return adns_s_ok;
}
static adns_status mkquery_footer(vbuf *vb, adns_rrtype type) {
byte *rqp;
MKQUERY_START(vb);
MKQUERY_ADDW(type & adns__rrt_typemask); /* QTYPE */
MKQUERY_ADDW(DNS_CLASS_IN); /* QCLASS=IN */
MKQUERY_STOP(vb);
assert(vb->used <= vb->avail);
return adns_s_ok;
}
adns_status adns__mkquery(adns_state ads, vbuf *vb, int *id_r,
const char *owner, int ol,
const typeinfo *typei, adns_queryflags flags) {
int ll, c, nbytes;
byte label[255], *rqp;
const char *p, *pe;
adns_status st;
st= mkquery_header(ads,vb,id_r,ol+2); if (st) return st;
MKQUERY_START(vb);
p= owner; pe= owner+ol;
nbytes= 0;
while (p!=pe) {
ll= 0;
while (p!=pe && (c= *p++)!='.') {
if (c=='\\') {
if (!(flags & adns_qf_quoteok_query)) return adns_s_querydomaininvalid;
if (ctype_digit(p[0])) {
if (ctype_digit(p[1]) && ctype_digit(p[2])) {
c = (*p++ - '0')*100;
c += (*p++ - '0')*10;
c += (*p++ - '0');
if (c >= 256) return adns_s_querydomaininvalid;
} else {
return adns_s_querydomaininvalid;
}
} else if (!(c= *p++)) {
return adns_s_querydomaininvalid;
}
}
if (!(flags & adns_qf_quoteok_query)) {
if (c == '-') {
if (!ll) return adns_s_querydomaininvalid;
} else if (!ctype_alpha(c) && !ctype_digit(c)) {
return adns_s_querydomaininvalid;
}
}
if (ll == sizeof(label)) return adns_s_querydomaininvalid;
label[ll++]= c;
}
if (!ll) return adns_s_querydomaininvalid;
if (ll > DNS_MAXLABEL) return adns_s_querydomaintoolong;
nbytes+= ll+1;
if (nbytes >= DNS_MAXDOMAIN) return adns_s_querydomaintoolong;
MKQUERY_ADDB(ll);
memcpy(rqp,label,ll); rqp+= ll;
}
MKQUERY_ADDB(0);
MKQUERY_STOP(vb);
st= mkquery_footer(vb,typei->type);
return adns_s_ok;
}
adns_status adns__mkquery_frdgram(adns_state ads, vbuf *vb, int *id_r,
const byte *qd_dgram, int qd_dglen, int qd_begin,
adns_rrtype type, adns_queryflags flags) {
byte *rqp;
findlabel_state fls;
int lablen, labstart;
adns_status st;
st= mkquery_header(ads,vb,id_r,qd_dglen); if (st) return st;
MKQUERY_START(vb);
adns__findlabel_start(&fls,ads,-1,0,qd_dgram,qd_dglen,qd_dglen,qd_begin,0);
for (;;) {
st= adns__findlabel_next(&fls,&lablen,&labstart); assert(!st);
if (!lablen) break;
assert(lablen<255);
MKQUERY_ADDB(lablen);
memcpy(rqp,qd_dgram+labstart,lablen);
rqp+= lablen;
}
MKQUERY_ADDB(0);
MKQUERY_STOP(vb);
st= mkquery_footer(vb,type);
return adns_s_ok;
}
void adns__querysend_tcp(adns_query qu, struct timeval now) {
byte length[2];
#if 0
struct iovec iov[2];
#endif
int wr, wr2 = 0, r;
adns_state ads;
if (qu->ads->tcpstate != server_ok) return;
assert(qu->state == query_tcpw);
length[0]= (qu->query_dglen&0x0ff00U) >>8;
length[1]= (qu->query_dglen&0x0ff);
ads= qu->ads;
if (!adns__vbuf_ensure(&ads->tcpsend,ads->tcpsend.used+qu->query_dglen+2)) return;
qu->retries++;
/* Reset idle timeout. */
ads->tcptimeout.tv_sec= ads->tcptimeout.tv_usec= 0;
if (ads->tcpsend.used) {
wr= 0;
} else {
#if 0
iov[0].iov_base= (char *)length;
iov[0].iov_len= 2;
iov[1].iov_base= (char *)qu->query_dgram;
iov[1].iov_len= qu->query_dglen;
wr= writev(qu->ads->tcpsocket,iov,2);
#endif
wr = write(qu->ads->tcpsocket, (char *)length, 2);
if (wr > 0)
wr2 = write(qu->ads->tcpsocket, (char *)qu->query_dgram, qu->query_dglen);
if (wr < 0 || wr2 < 0) {
if (!(errno == EAGAIN || errno == EINTR || errno == ENOSPC ||
errno == ENOBUFS || errno == ENOMEM)) {
adns__tcp_broken(ads,"write",strerror(errno));
return;
}
wr= 0;
}
}
if (wr<2) {
r= adns__vbuf_append(&ads->tcpsend,length,2-wr); assert(r);
wr= 0;
} else {
wr-= 2;
}
if (wr<qu->query_dglen) {
r= adns__vbuf_append(&ads->tcpsend,qu->query_dgram+wr,qu->query_dglen-wr); assert(r);
}
}
static void query_usetcp(adns_query qu, struct timeval now) {
qu->state= query_tcpw;
qu->timeout= now;
timevaladd(&qu->timeout,TCPWAITMS);
LIST_LINK_TAIL(qu->ads->tcpw,qu);
adns__querysend_tcp(qu,now);
adns__tcp_tryconnect(qu->ads,now);
}
void adns__query_send(adns_query qu, struct timeval now) {
struct sockaddr_in servaddr;
int serv, r;
adns_state ads;
assert(qu->ads->nservers > 0);
assert(qu->state == query_tosend);
if ((qu->flags & adns_qf_usevc) || (qu->query_dglen > DNS_MAXUDP)) {
query_usetcp(qu,now);
return;
}
if(qu->query_dglen > DNS_MAXUDP) {
adns__query_fail(qu, adns_s_systemfail);
return;
}
if (qu->retries >= UDPMAXRETRIES) {
adns__query_fail(qu,adns_s_timeout);
return;
}
serv= qu->udpnextserver;
memset(&servaddr,0,sizeof(servaddr));
ads= qu->ads;
servaddr.sin_family= AF_INET;
servaddr.sin_addr= ads->servers[serv].addr;
servaddr.sin_port= htons(DNS_PORT);
r= sendto(ads->udpsocket,qu->query_dgram,qu->query_dglen,0,
(const struct sockaddr*)&servaddr,sizeof(servaddr));
if (r<0 && errno == EMSGSIZE) { qu->retries= 0; query_usetcp(qu,now); return; }
if (r<0 && errno != EAGAIN) adns__warn(ads,serv,0,"sendto failed: %s",strerror(errno));
qu->timeout= now;
timevaladd(&qu->timeout,UDPRETRYMS);
qu->udpsent |= (1<<serv);
qu->udpnextserver= (serv+1)%ads->nservers;
qu->retries++;
LIST_LINK_TAIL(ads->udpw,qu);
}

43
adns/tvarith.h Normal file
View file

@ -0,0 +1,43 @@
/*
* tvarith.h
* - static inline functions for doing arithmetic on timevals
*/
/*
* This file is
* Copyright (C) 1997-1999 Ian Jackson <ian@davenant.greenend.org.uk>
*
* It is part of adns, which is
* Copyright (C) 1997-2000 Ian Jackson <ian@davenant.greenend.org.uk>
* Copyright (C) 1999-2000 Tony Finch <dot@dotat.at>
*
* 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, 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.
*
* $Id: tvarith.h,v 1.1 2002/08/13 14:35:08 fishwaldo Exp $
*/
#ifndef ADNS_TVARITH_H_INCLUDED
#define ADNS_TVARITH_H_INCLUDED
static INLINE void timevaladd(struct timeval *tv_io, long ms) {
struct timeval tmp;
assert(ms>=0);
tmp= *tv_io;
tmp.tv_usec += (ms%1000)*1000;
tmp.tv_sec += ms/1000;
if (tmp.tv_usec >= 1000000) { tmp.tv_sec++; tmp.tv_usec -= 1000000; }
*tv_io= tmp;
}
#endif

1166
adns/types.c Normal file

File diff suppressed because it is too large Load diff

81
autoconf/acconfig.h Normal file
View file

@ -0,0 +1,81 @@
/*
* $Id: acconfig.h,v 1.1 2002/08/13 14:35:09 fishwaldo Exp $
*/
/* Define if you have the poll() system call. */
#undef USE_POLL
/* Define with our select type */
#undef SELECT_TYPE
/* Define if we are going to use /dev/poll for network IO */
#undef HAVE_DEVPOLL
#undef USE_DEVPOLL
/* Using kqueue */
#undef USE_KQUEUE
/* Using poll */
#undef USE_POLL
/* Using select */
#undef USE_SELECT
/* Using devpoll */
#undef USE_DEVPOLL
/* Using sigio */
#undef USE_SIGIO
/* Define if we have socklen_t */
#undef HAVE_SOCKLEN_T
/* Define if we have uintptr_t */
#undef HAVE_UINTPTR_T
/* Define if we need HAVE_SHL_LOAD - HPUX */
#undef HAVE_SHL_LOAD
/* Define based upon RLIMIT value is found in sys/resource.h */
/* By default, we assume nothing is found. */
#undef RLIMIT_FD_MAX
/* Define if we can include both string.h and strings.h */
#undef STRING_WITH_STRINGS
/* This is a string containing any extra underscores that must be prepended
* to symbols loaded from modules.
*/
#undef SYMBOL_PREFIX
/* IPv6 support */
#undef IPV6
/* u_int32_t */
#undef u_int32_t
/* static modules */
#undef STATIC_MODULES
/* No block allocator */
#undef NOBALLOC
/* Gettext support */
#undef HAVE_GETTEXT
/* nanosleep */
#undef HAVE_NANOSLEEP
/* nicklen */
#undef NICKLEN
/* max_clients */
#undef MAX_CLIENTS
/* topiclen */
#undef TOPICLEN
/* EFNET */
#undef EFNET

1021
autoconf/configure.in Normal file

File diff suppressed because it is too large Load diff

250
autoconf/install-sh Executable file
View file

@ -0,0 +1,250 @@
#! /bin/sh
# $Id: install-sh,v 1.1 2002/08/13 14:35:10 fishwaldo Exp $
# install - install a program, script, or datafile
# This comes from X11R5 (mit/util/scripts/install.sh).
#
# Copyright 1991 by the Massachusetts Institute of Technology
#
# Permission to use, copy, modify, distribute, and sell this software and its
# documentation for any purpose is hereby granted without fee, 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.
#
# Calling this script install-sh is preferred over install.sh, to prevent
# `make' implicit rules from creating a file called install from it
# when there is no Makefile.
#
# This script is compatible with the BSD install script, but was written
# from scratch.
#
# set DOITPROG to echo to test this script
# Don't use :- since 4.3BSD and earlier shells don't like it.
doit="${DOITPROG-}"
# put in absolute paths if you don't have them in your path; or use env. vars.
mvprog="${MVPROG-mv}"
cpprog="${CPPROG-cp}"
chmodprog="${CHMODPROG-chmod}"
chownprog="${CHOWNPROG-chown}"
chgrpprog="${CHGRPPROG-chgrp}"
stripprog="${STRIPPROG-strip}"
rmprog="${RMPROG-rm}"
mkdirprog="${MKDIRPROG-mkdir}"
transformbasename=""
transform_arg=""
instcmd="$mvprog"
chmodcmd="$chmodprog 0755"
chowncmd=""
chgrpcmd=""
stripcmd=""
rmcmd="$rmprog -f"
mvcmd="$mvprog"
src=""
dst=""
dir_arg=""
while [ x"$1" != x ]; do
case $1 in
-c) instcmd="$cpprog"
shift
continue;;
-d) dir_arg=true
shift
continue;;
-m) chmodcmd="$chmodprog $2"
shift
shift
continue;;
-o) chowncmd="$chownprog $2"
shift
shift
continue;;
-g) chgrpcmd="$chgrpprog $2"
shift
shift
continue;;
-s) stripcmd="$stripprog"
shift
continue;;
-t=*) transformarg=`echo $1 | sed 's/-t=//'`
shift
continue;;
-b=*) transformbasename=`echo $1 | sed 's/-b=//'`
shift
continue;;
*) if [ x"$src" = x ]
then
src=$1
else
# this colon is to work around a 386BSD /bin/sh bug
:
dst=$1
fi
shift
continue;;
esac
done
if [ x"$src" = x ]
then
echo "install: no input file specified"
exit 1
else
true
fi
if [ x"$dir_arg" != x ]; then
dst=$src
src=""
if [ -d $dst ]; then
instcmd=:
else
instcmd=mkdir
fi
else
# Waiting for this to be detected by the "$instcmd $src $dsttmp" command
# might cause directories to be created, which would be especially bad
# if $src (and thus $dsttmp) contains '*'.
if [ -f $src -o -d $src ]
then
true
else
echo "install: $src does not exist"
exit 1
fi
if [ x"$dst" = x ]
then
echo "install: no destination specified"
exit 1
else
true
fi
# If destination is a directory, append the input filename; if your system
# does not like double slashes in filenames, you may need to add some logic
if [ -d $dst ]
then
dst="$dst"/`basename $src`
else
true
fi
fi
## this sed command emulates the dirname command
dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'`
# Make sure that the destination directory exists.
# this part is taken from Noah Friedman's mkinstalldirs script
# Skip lots of stat calls in the usual case.
if [ ! -d "$dstdir" ]; then
defaultIFS='
'
IFS="${IFS-${defaultIFS}}"
oIFS="${IFS}"
# Some sh's can't handle IFS=/ for some reason.
IFS='%'
set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'`
IFS="${oIFS}"
pathcomp=''
while [ $# -ne 0 ] ; do
pathcomp="${pathcomp}${1}"
shift
if [ ! -d "${pathcomp}" ] ;
then
$mkdirprog "${pathcomp}"
else
true
fi
pathcomp="${pathcomp}/"
done
fi
if [ x"$dir_arg" != x ]
then
$doit $instcmd $dst &&
if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi &&
if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi &&
if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi &&
if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi
else
# If we're going to rename the final executable, determine the name now.
if [ x"$transformarg" = x ]
then
dstfile=`basename $dst`
else
dstfile=`basename $dst $transformbasename |
sed $transformarg`$transformbasename
fi
# don't allow the sed command to completely eliminate the filename
if [ x"$dstfile" = x ]
then
dstfile=`basename $dst`
else
true
fi
# Make a temp file name in the proper directory.
dsttmp=$dstdir/#inst.$$#
# Move or copy the file name to the temp name
$doit $instcmd $src $dsttmp &&
trap "rm -f ${dsttmp}" 0 &&
# and set any options; do chmod last to preserve setuid bits
# If any of these fail, we abort the whole thing. If we want to
# ignore errors from any of these, just make sure not to ignore
# errors from the above "$doit $instcmd $src $dsttmp" command.
if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi &&
if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi &&
if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi &&
if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi &&
# Now rename the file to the real destination.
$doit $rmcmd -f $dstdir/$dstfile &&
$doit $mvcmd $dsttmp $dstdir/$dstfile
fi &&
exit 0

10
clean.com Normal file
View file

@ -0,0 +1,10 @@
$! $Id: clean.com,v 1.1 2002/08/13 14:34:56 fishwaldo Exp $
$! yes, its a hack. this needs to be merged into make.com.
$! (well, really, into a top-level descrip.mms.. one day).
$
$ WRITE SYS$OUTPUT "Cleaning tree from all compiled objects..."
$ DELETE [...]*.EXE;*
$ DELETE [...]*.OLB;*
$ DELETE [...]*.OBJ;*
$ WRITE SYS$OUTPUT "All done."

5330
configure vendored Executable file

File diff suppressed because it is too large Load diff

1
contrib/.cvsignore Normal file
View file

@ -0,0 +1 @@
Makefile

83
contrib/Makefile.in Normal file
View file

@ -0,0 +1,83 @@
#
# Makefile.in for ircd/contrib
#
# $Id: Makefile.in,v 1.1 2002/08/13 14:35:10 fishwaldo Exp $
#
CC = @CC@
RM = @RM@
SED = @SED@
LEX = @LEX@
LEXLIB = @LEXLIB@
CFLAGS = @IRC_CFLAGS@ -DIRCD_PREFIX=\"@prefix@\"
PICFLAGS = @PICFLAGS@
MKDEP = @MKDEP@
INSTALL = @INSTALL@
INSTALL_PROGRAM = @INSTALL_PROGRAM@
INSTALL_DATA = @INSTALL_DATA@
INSTALL_SUID = @INSTALL_PROGRAM@ -o root -m 4755
SHELL = /bin/sh
AUTOMODULEDIR = @prefix@/modules
SSL_LIBS = @SSL_LIBS@
SSL_INCLUDES = @SSL_INCLUDES@
IRCDLIBS = @LIBS@ $(SSL_LIBS)
INCLUDES = -I../include -I../adns $(SSL_INCLUDES)
CPPFLAGS = ${INCLUDES} @CPPFLAGS@
SRCS = \
m_clearchan.c \
m_flags.c \
m_force.c \
m_jupe.c \
m_ltrace.c \
m_map.c \
m_mkpasswd.c \
m_ojoin.c \
m_opme.c \
m_tburst.c \
spy_admin_notice.c \
spy_info_notice.c \
spy_links_notice.c \
spy_motd_notice.c \
spy_stats_notice.c \
spy_stats_p_notice.c \
spy_trace_notice.c \
spy_whois_notice.c \
example_module.c
OBJS = ${SRCS:.c=.so}
default: build
build: all
all: $(OBJS)
install: all
@echo "Installing modules into $(AUTOMODULEDIR) .."
@for file in $(OBJS); do \
$(INSTALL_DATA) $$file $(AUTOMODULEDIR); \
done
.SUFFIXES: .so
.c.so:
${CC} ${PICFLAGS} ${CPPFLAGS} ${CFLAGS} $< -o $@
.PHONY: depend clean distclean
depend:
@${MKDEP} ${CPPFLAGS} ${SRCS} > .depend
@sed s/\\\.o/\\\.so/ < .depend > .depend.tmp
@sed -e '/^# DO NOT DELETE THIS LINE/,$$d' <Makefile >Makefile.depend
@echo '# DO NOT DELETE THIS LINE!!!' >>Makefile.depend
@echo '# make depend needs it.' >>Makefile.depend
@cat .depend.tmp >>Makefile.depend
@mv Makefile.depend Makefile
@rm -f .depend.tmp .depend
clean:
${RM} -f *.so *~
distclean: clean
${RM} -f Makefile

100
contrib/README Normal file
View file

@ -0,0 +1,100 @@
$Id: README,v 1.1 2002/08/13 14:35:10 fishwaldo Exp $
This directory contains modules and patches that have been contributed
by other people, or aren't suitable for including into the
hybrid tree. The coding team do not officially support the contrib/
modules, or guarantee any of them will actually work.
Modules
-------
m_clearchan.c - CLEARCHAN - clears all users out of a channel and joins person
issuing command
Syntax: CLEARCHAN <channel> [vchanid]
m_flags.c - FLAGS - csircd like support of changing usermodes
Syntax: FLAGS :+OWALLOPS -SWALLOPS
m_force.c - FORCE - forces a user to either part or join a channel with
an optional status (@%+)
Syntax: FORCEJOIN <nick> [status]<channel>
FORCEPART <nick> <channel>
m_jupe.c - JUPE - Server juping command
Syntax: JUPE juped.server.name :Reason
m_ltrace.c - LTRACE - Limited trace. Similar to TRACE except only reports
current opers and servers.
Syntax: LTRACE [nick|mask [server]]
m_map.c - MAP - Display the server routing graph in a visually pleasing
format
Syntax: MAP
m_mkpasswd.c - MKPASSWD - generate a DES or MD5 encryption of a password
Syntax: MKPASSWD <plaintext> [MD5|DES]
m_ojoin.c - OJOIN - Join a channel through any modes or limits with
an optional status (@%+)
Syntax: OJOIN [status]<channel>
m_opme.c - OPME - Allows an admin to op themselves in an opless channel
Syntax: OPME <channel>
m_tburst.c - TBURST - module that will make servers send channel topics
to each other after a netsplit/restart.
example_module.c - An example module to be used for creating your own.
Syntax: TEST
Spy Modules
-----------
The following are the 'spy' parts, accessible via the +y usermode
spy_admin_notice.c - Spy on clients doing ADMIN
spy_info_notice.c - Spy on clients doing INFO
spy_links_notice.c - Spy on clients doing LINKS
spy_motd_notice.c - Spy on clients doing MOTD
spy_stats_notice.c - Spy on clients doing all STATS
spy_stats_p_notice.c - Spy on clients doing STATS p only
spy_trace_notice.c - Spy on clients doing TRACE/LTRACE
spy_whois_notice.c - Spy on local clients who WHOIS you.
Note: if you have both spy_stats_notice.c and spy_stats_p_notice.c loaded
you will get two messages.
VMS Files
---------
vms_*.c - Misc files needed for VMS support.
Patches
-------
The following are the patches contained in contrib. A short description
of the patch is contained here, along with any notes.
To apply a patch, first change to the ircd-hybrid-7 root directory,
the directory one level above contrib/. If you have already compiled
the ircd, run 'make clean'. Then for example to patch
remote-unkline.diff type:
patch -p0 < contrib/remote-unkline.diff
You must then run 'make' and 'make install' again, and restart your ircd.
The following patches are included:
lmh.diff - This patch adds remote unkline support, temp dline support,
better temp klines, /quote xline and global user@host
limits.
Please read README.LMH for more information as this patch
requires different methods to be applied and adds multiple
config options.
disable_identd.diff - This patch adds support for disabling identd queries.
See README.disable_identd for more information.

168
contrib/README.LMH Normal file
View file

@ -0,0 +1,168 @@
+lmh patches by fl_
The +lmh patch exists to add some functionality and features that I find
useful and that people have requested. This patch will not modify the
example configs to show the new options, they are only contained in this
readme. I know its quite long, but..
This patch is unofficial and is used at your own risk.
To patch your ircd with this diff:
Change to your ircd-hybrid-7 directory.
If you have already compiled the ircd, run 'make clean' then:
patch -p1 < contrib/lmh.diff
Then run 'make' and 'make install'.
The following features have been added:
i) Temp dline support and temp kline extensions.
Normal dlines may still be placed as normal via:
/quote dline <nick|ip> :reason
However they can be made temporary by adding a duration:
/quote dline [duration] <nick|ip> :reason
The duration is in minutes. Temp klines/dlines will now both have a
maximum length of 4 weeks (40320 minutes). This is because the ircd
now handles them more efficiently by grouping them and checking their
expiry as infrequently as possible.
ii) Oper flood exemption
This is the equivalent of hybrid6's TRUE_NO_OPER_FLOOD, and will
remove all flood limits for opers. Note this is dangerous as an oper
will not get rate limited no matter how many lines they send to the
server. Use with great precaution. Unlike hybrid6 however this
is configured per oper and defaults to disabled.
To grant an oper this exemption add to their oper {} block:
flood_exempt = yes;
Note the exemption only takes effect whilst opered, but once a user
has opered with the flood exemption, the exemption will remain until
that user is disconnected from the ircd, even if the exemption is
removed from their oper block and they reoper.
Note that opers without this exemption still have increased flood limits
of about 20 lines per second which is controlled by no_oper_flood
in the general {} block.
iii) Remote unkline support.
This extends hybrid7s remote kline support to also allow unklines to
be done on remote servers by authorised users.
To facilitate this, the shared {}; block has been modified to give
remote opers specific permissions (similar to an oper {}). By default
the permissions of a shared block are that an oper may remotely kline
but not unkline.
The two options added to the shared block are:
kline = <yes|no>;
unkline = <yes|no>;
To issue a remote unkline:
/quote unkline <user@host> on <server>
If you do not wish this to be supported, simply dont add any shared
blocks with 'unkline = yes'.
iv) /quote XLINE support
This gives opers who do not have ircd.conf access the ability to set
XLINE's, or gecos bans. These ban a user based on their realname, or
gecos field. They will be added to an xline.conf file in the etc/
directory of your ircd.
To add an xline:
/quote xline <gecos> [type] :<reason>
The gecos field is the gecos that should be banned and may not contain
spaces. If you need to add something that has a space you must use
'?' instead of spaces, ie:
/quote xline eggdrop?bot 2 :no bots
The type field denotes how the xline works and may be:
2 - Reject the user silently.
1 - Reject the user and send a warning to +r opers.
0 - Send a warning to +r opers but allow user to connect.
To allow an oper to use the xline command the following option has been
added to the oper {} block:
xline = <yes|no>;
The ability for a user to xline is marked by the 'X' priv. Note that
xlines are not checked for dupes and config access is required to
remove a placed xline.
v) Global user@host limits.
Taken from ircnets ircd. Currently you may limit a certain host to n
number of connections to the ircd, however these do not stop a user
loading large amounts of clones on multiple servers. The global limits
extend the host limits so you can set network-wide host limits.
Thus you could allow 2 local users from 'vanity.host.com' and 3 users
network wide from 'vanity.host.com'. The network wide limit includes
the local server. Thus if a user had three connections to the network
on another server, they would not be allowed to connect locally. If
a user had two connections on another server and one connection locally,
they would not be allowed to connect another client locally either.
You may also limit the amount of connections from a specific user@host,
ie: 'abuser@vanity.host.com'. Unidented connections will be counted
as having the same ident. Ident limits are global only (thus they
include the local server in their limits).
Thus a global host limit of 3, local host limit of 2 and an ident limit
of 1 would allow one connection from 'abuser@vanity.host.com' no matter
where on the network the connection was. However
'realuser@vanity.host.com' would be allowed to connect as the idents
are different, providing the host limits are not exceeded.
Users set 'exceed_limit = yes;' may exceed any limits.
The following option is added to the general {} block:
use_global_limits = <yes|no>;
This option is enabled by default and controls whether the global
user@host limits are used. This option may not be changed once the
server is running and requires a restart to be modified.
The following options are added to the class {} block:
number_per_ident = <number>;
number_per_ip = <number>; -- not really added, just noted here.
number_per_ip_global = <number>;
- number_per_ip will do the same function as in vanilla hybrid7, limiting
local connections per host.
- number_per_ident controls the user@ portion of the limits.
- number_per_ip_global controls how many connections a host may have
network wide.
All three options default to 0 (unlimited).
The behaviour of class blocks are modified slightly and as a result you
*MUST* use 'connectfreq = <duration>;' in server class blocks, not
number_per_ip.
vi) ASCII casemapping support (by AndroSyn)
IRCs scandinavian origins mean the characters are {}|~ are treated as
the lowercase of []\^. Thus as the nicks "a" and "A" would be the same,
the nicks "[" and "{" would be.
If this is defined they are treated as individual characters, so the
nicks [foo] and {foo} would be two seperate clients. If this is
enabled it MUST be done network wide or you will experience problems
with non-compatible servers. Your locale(1) must also be set to "C"
or the system itself may treat the characters differently.
The following option is added to config.h that can be defined:
USE_ASCII_CASEMAP
If you have any problems, questions or find any bugs, find me on irc
(ircnet/efnet) or email me. Have fun. :)
--
Lee H <lee@leeh.co.uk>
$Id: README.LMH,v 1.1 2002/08/13 14:35:11 fishwaldo Exp $

View file

@ -0,0 +1,17 @@
# $Id: README.disable_identd,v 1.1 2002/08/13 14:35:11 fishwaldo Exp $
#
This diff adds a config option to the general {} block called disable_auth
to hybrid 7. To disable identd requests add something like this to your
config file:
general {
disable_auth = yes;
}
You should note that this does not effect other identd related settings with
regard to stripping tildes or the requirement of identd checking in auth {}
blocks.
Aaron Sethman <androsyn@ratbox.org>
July 07, 2002

View file

@ -0,0 +1,87 @@
Index: include/s_conf.h
===================================================================
RCS file: /cvsroot/ircd-hybrid-7/include/s_conf.h,v
retrieving revision 7.180
diff -u -r7.180 s_conf.h
--- include/s_conf.h 24 May 2002 23:34:08 -0000 7.180
+++ include/s_conf.h 8 Jul 2002 00:06:17 -0000
@@ -231,6 +231,7 @@
int throttle_time;
int use_egd;
int ping_cookie;
+ int disable_auth;
#ifdef HAVE_LIBCRYPTO
struct EncCapability *default_cipher_preference;
#endif
Index: src/ircd_lexer.l
===================================================================
RCS file: /cvsroot/ircd-hybrid-7/src/ircd_lexer.l,v
retrieving revision 1.139
diff -u -r1.139 ircd_lexer.l
--- src/ircd_lexer.l 25 May 2002 01:55:20 -0000 1.139
+++ src/ircd_lexer.l 8 Jul 2002 00:06:17 -0000
@@ -115,6 +115,7 @@
deny { return DENY; }
description { return DESCRIPTION; }
die { return DIE; }
+disable_auth { return DISABLE_AUTH; }
disable_hidden { return DISABLE_HIDDEN; }
disable_local_channels { return DISABLE_LOCAL_CHANNELS; }
disable_remote_commands { return DISABLE_REMOTE_COMMANDS; }
Index: src/ircd_parser.y
===================================================================
RCS file: /cvsroot/ircd-hybrid-7/src/ircd_parser.y,v
retrieving revision 1.252
diff -u -r1.252 ircd_parser.y
--- src/ircd_parser.y 12 Jun 2002 19:29:36 -0000 1.252
+++ src/ircd_parser.y 8 Jul 2002 00:06:17 -0000
@@ -117,6 +117,7 @@
%token DENY
%token DESCRIPTION
%token DIE
+%token DISABLE_AUTH
%token DISABLE_HIDDEN
%token DISABLE_LOCAL_CHANNELS
%token DISABLE_REMOTE_COMMANDS
@@ -1974,6 +1975,7 @@
general_compression_level | general_client_flood |
general_throttle_time | general_havent_read_conf |
general_dot_in_ip6_addr | general_ping_cookie |
+ general_disable_auth |
error;
general_failed_oper_notice: FAILED_OPER_NOTICE '=' TYES ';'
@@ -2330,6 +2332,15 @@
PING_COOKIE '=' TNO ';'
{
ConfigFileEntry.ping_cookie = 0;
+ } ;
+
+general_disable_auth: DISABLE_AUTH '=' TYES ';'
+ {
+ ConfigFileEntry.disable_auth = 1;
+ } |
+ DISABLE_AUTH '=' TNO ';'
+ {
+ ConfigFileEntry.disable_auth = 0;
} ;
general_throttle_time: THROTTLE_TIME '=' timespec ';'
Index: src/s_auth.c
===================================================================
RCS file: /cvsroot/ircd-hybrid-7/src/s_auth.c,v
retrieving revision 7.97
diff -u -r7.97 s_auth.c
--- src/s_auth.c 11 Jun 2002 20:29:06 -0000 7.97
+++ src/s_auth.c 8 Jul 2002 00:06:17 -0000
@@ -423,7 +423,9 @@
adns_getaddr(&client->localClient->ip, client->localClient->aftype, client->localClient->dns_query);
SetDNSPending(auth);
- start_auth_query(auth);
+ if(ConfigFileEntry.disable_auth == 0)
+ start_auth_query(auth);
+
link_auth_request(auth, &auth_poll_list);
}

207
contrib/example_module.c Normal file
View file

@ -0,0 +1,207 @@
/************************************************************************
* IRC - Internet Relay Chat, doc/example_module.c
* Copyright (C) 2001 Hybrid 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 1, or (at your option)
* any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id: example_module.c,v 1.1 2002/08/13 14:35:11 fishwaldo Exp $
*/
/* List of ircd includes from ../include/ */
#include "stdinc.h"
#include "handlers.h"
#include "client.h"
#include "common.h" /* FALSE bleah */
#include "ircd.h"
#include "irc_string.h"
#include "numeric.h"
#include "fdlist.h"
#include "s_bsd.h"
#include "s_conf.h"
#include "s_log.h"
#include "s_serv.h"
#include "send.h"
#include "msg.h"
#include "parse.h"
#include "modules.h"
/* Declare the void's initially up here, as modules dont have an
* include file, we will normally have client_p, source_p, parc
* and parv[] where:
*
* client_p == client issuing command
* source_p == where the command came from
* parc == the number of parameters
* parv == an array of the parameters
*/
static void mr_test(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static void m_test(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static void ms_test(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static void mo_test(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
/* Show the commands this module can handle in a msgtab
* and give the msgtab a name, here its test_msgtab
*/
struct Message test_msgtab = {
/* Fields are in order:
*-> "COMMAND", 0, 0, parc_count, maxparc, MFLG_SLOW, 0,
*
* where:
* COMMAND == the /command you want
* parc_count == the number of parameters needed
* (the clients name is one param, parv[0])
* maxparc == the maximum parameters we allow
* the 0's and MFLG_SLOW should not be changed..
*/
/* This would add the command "TEST" which requires no additional
* parameters
*/
"TEST", 0, 0, 1, 0, MFLG_SLOW, 0,
/* Fields are in order:
*-> {unregged, regged, remote, oper}
*
* where:
* unregged == function to call for unregistered clients
* regged == function to call for normal users
* remote == function to call for servers/remote users
* oper == function to call for operators
*
* There are also some pre-coded functions for use:
* m_unregistered: prevent the client using this if unregistered
* m_not_oper: tell the client it requires being an operator
* m_ignore: ignore the command when it comes from certain types
* m_error: give an error when the command comes from certain types
*/
{mr_test, m_test, ms_test, mo_test}
/* It is normal for unregistered functions to be prefixed with mr_
* " " normal users to be prefixed with m_
* " " remote clients to be prefixed with ms_
* " " operators to be prefixed with mo_
*/
};
/* Thats the msgtab finished */
#ifndef STATIC_MODULES
/* Here we tell it what to do when the module is loaded */
void
_modinit(void)
{
/* This will add the commands in test_msgtab (which is above) */
mod_add_cmd(&test_msgtab);
}
/* here we tell it what to do when the module is unloaded */
void
_moddeinit(void)
{
/* This will remove the commands in test_msgtab (which is above) */
mod_del_cmd(&test_msgtab);
}
/* When we last modified the file (shown in /modlist), this is usually:
*/
const char *_version = "$Revision: 1.1 $";
#endif
/*
* mr_test
* parv[0] = sender prefix
* parv[1] = parameter
*/
/* Here we have the functions themselves that we declared above,
* and the fairly normal C coding
*/
static void mr_test(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
if(parc == 1)
sendto_one(source_p, ":%s NOTICE %s :You are unregistered and sent no parameters",
me.name, source_p->name);
else
sendto_one(source_p, ":%s NOTICE %s :You are unregistered and sent parameter: %s",
me.name, source_p->name, parv[1]);
}
/*
* m_test
* parv[0] = sender prefix
* parv[1] = parameter
*/
static void m_test(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
if(parc == 1)
sendto_one(source_p, ":%s NOTICE %s :You are a normal user, and sent no parameters",
me.name, source_p->name);
else
sendto_one(source_p, ":%s NOTICE %s :You are a normal user, and send parameters: %s",
me.name, source_p->name, parv[1]);
}
/*
* ms_test
* parv[0] = sender prefix
* parv[1] = parameter
*/
static void ms_test(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
if(parc == 1)
{
if(IsServer(source_p))
sendto_one(source_p, ":%s NOTICE %s :You are a server, and sent no parameters",
me.name, source_p->name);
else
sendto_one(source_p, ":%s NOTICE %s :You are a remote client, and sent no parameters",
me.name, source_p->name);
}
else
{
if(IsServer(source_p))
sendto_one(source_p, ":%s NOTICE %s :You are a server, and sent parameters: %s",
me.name, source_p->name, parv[1]);
else
sendto_one(source_p, ":%s NOTICE %s :You are a remote client, and sent parameters: %s",
me.name, source_p->name, parv[1]);
}
}
/*
* mo_test
* parv[0] = sender prefix
* parv[1] = parameter
*/
static void mo_test(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
if(parc == 1)
sendto_one(source_p, ":%s NOTICE %s :You are an operator, and sent no parameters",
me.name, source_p->name);
else
sendto_one(source_p, ":%s NOTICE %s :You are an operator, and sent parameters: %s",
me.name, source_p->name, parv[1]);
}
/* END OF EXAMPLE MODULE */

2588
contrib/lmh.diff Normal file

File diff suppressed because it is too large Load diff

370
contrib/m_clearchan.c Normal file
View file

@ -0,0 +1,370 @@
/*
* IRC - Internet Relay Chat, contrib/m_clearchan.c
* Copyright (C) 2002 Hybrid 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 1, or (at your option)
* any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id: m_clearchan.c,v 1.1 2002/08/13 14:35:14 fishwaldo Exp $
*/
#include "stdinc.h"
#include "tools.h"
#include "handlers.h"
#include "channel.h"
#include "channel_mode.h"
#include "client.h"
#include "ircd.h"
#include "numeric.h"
#include "s_log.h"
#include "s_serv.h"
#include "send.h"
#include "whowas.h"
#include "irc_string.h"
#include "hash.h"
#include "msg.h"
#include "parse.h"
#include "modules.h"
#include "vchannel.h"
#include "list.h"
#define MSG_CLEARCHAN "CLEARCHAN"
extern BlockHeap *ban_heap;
static void mo_clearchan(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static void kick_list(struct Client *client_p, struct Client *source_p, struct Channel *chptr,
dlink_list *list,char *chname);
static void remove_our_modes(int type,
struct Channel *chptr, struct Channel *top_chptr,
struct Client *source_p);
static void remove_a_mode(int hide_or_not,
struct Channel *chptr, struct Channel *top_chptr,
struct Client *source_p, dlink_list *list, char flag);
static void free_channel_list(dlink_list *list);
static char *mbuf;
struct Message clearchan_msgtab = {
MSG_CLEARCHAN, 0, 0, 2, 0, MFLG_SLOW, 0,
{m_unregistered, m_not_oper, m_ignore, mo_clearchan}
};
void
_modinit(void)
{
mod_add_cmd(&clearchan_msgtab);
}
void
_moddeinit(void)
{
mod_del_cmd(&clearchan_msgtab);
}
char *_version = "$Revision: 1.1 $";
/*
** mo_clearchan
** parv[0] = sender prefix
** parv[1] = channel
*/
static void mo_clearchan(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
struct Channel *chptr, *root_chptr;
int on_vchan = 0;
/* admins only */
if (!IsOperAdmin(source_p))
{
sendto_one(source_p, ":%s NOTICE %s :You have no A flag", me.name, parv[0]);
return;
}
/* XXX - we might not have CBURSTed this channel if we are a lazylink
* yet. */
chptr= hash_find_channel(parv[1]);
root_chptr = chptr;
#ifdef VCHANS
if (chptr && parc > 2 && parv[2][0] == '!')
{
chptr = find_vchan(chptr, parv[2]);
if (root_chptr != chptr)
on_vchan++;
}
#endif
if( chptr == NULL )
{
sendto_one(source_p, form_str(ERR_NOSUCHCHANNEL),
me.name, parv[0], parv[1]);
return;
}
if(IsMember(source_p, chptr))
{
sendto_one(source_p, ":%s NOTICE %s :*** Please part %s before using CLEARCHAN",
me.name, source_p->name, parv[1]);
return;
}
if (!on_vchan)
{
sendto_wallops_flags(FLAGS_WALLOP, &me,
"CLEARCHAN called for [%s] by %s!%s@%s",
parv[1], source_p->name, source_p->username, source_p->host);
sendto_server(NULL, source_p, NULL, NOCAPS, NOCAPS, LL_ICLIENT,
":%s WALLOPS :CLEARCHAN called for [%s] by %s!%s@%s",
me.name, parv[1], source_p->name, source_p->username,
source_p->host);
ilog(L_NOTICE, "CLEARCHAN called for [%s] by %s!%s@%s",
parv[1], source_p->name, source_p->username, source_p->host);
}
else
{
sendto_wallops_flags(FLAGS_WALLOP, &me,
"CLEARCHAN called for [%s %s] by %s!%s@%s",
parv[1], parv[2], source_p->name, source_p->username,
source_p->host);
sendto_server(NULL, source_p, NULL, NOCAPS, NOCAPS, LL_ICLIENT,
":%s WALLOPS :CLEARCHAN called for [%s %s] by %s!%s@%s",
me.name, parv[1], parv[2], source_p->name,
source_p->username, source_p->host);
ilog(L_NOTICE, "CLEARCHAN called for [%s %s] by %s!%s@%s",
parv[1], parv[2], source_p->name, source_p->username, source_p->host);
}
/* Kill all the modes we have about the channel.. making everyone a peon */
remove_our_modes(0, chptr, root_chptr, source_p);
/* SJOIN the user to give them ops, and lock the channel */
sendto_server(client_p, source_p, chptr, NOCAPS, NOCAPS,
LL_ICLIENT, ":%s SJOIN %lu %s +ntsi :@%s",
me.name, (unsigned long) (chptr->channelts - 1),
chptr->chname, source_p->name);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s!%s@%s JOIN %s",
source_p->name,
source_p->username,
source_p->host,
root_chptr->chname);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +o %s",
me.name, chptr->chname, source_p->name);
add_user_to_channel(chptr, source_p, CHFL_CHANOP);
/* Take the TS down by 1, so we don't see the channel taken over
* again. */
if (chptr->channelts)
chptr->channelts--;
#ifdef VCHANS
if (on_vchan)
add_vchan_to_client_cache(source_p,root_chptr,chptr);
#endif
chptr->mode.mode =
MODE_SECRET | MODE_TOPICLIMIT | MODE_INVITEONLY | MODE_NOPRIVMSGS;
free_topic(chptr);
chptr->mode.key[0] = 0;
/* Kick the users out and join the oper */
kick_list(client_p, source_p, chptr, &chptr->peons, chptr->chname);
}
void kick_list(struct Client *client_p, struct Client *source_p, struct Channel *chptr,
dlink_list *list,char *chname)
{
struct Client *who;
dlink_node *m;
dlink_node *next_m;
for (m = list->head; m; m = next_m)
{
next_m = m->next;
who = m->data;
sendto_channel_local(ALL_MEMBERS, chptr,
":%s KICK %s %s :CLEARCHAN",
source_p->name, chname, who->name);
sendto_server(NULL, source_p, chptr, NOCAPS, NOCAPS, LL_ICLIENT,
":%s KICK %s %s :CLEARCHAN", source_p->name,
chname, who->name);
remove_user_from_channel(chptr, who);
}
/* Join the user themselves to the channel down here, so they dont see a nicklist
* or people being kicked */
sendto_one(source_p, ":%s!%s@%s JOIN %s",
source_p->name,
source_p->username,
source_p->host,
chname);
channel_member_names(source_p, chptr, chname, 1);
}
/*
* remove_our_modes
*
* inputs - hide from ops or not int flag
* - pointer to channel to remove modes from
* - if vchan basechannel pointer
* - client pointer
* output - NONE
* side effects - Go through the local members, remove all their
* chanop modes etc., this side lost the TS.
*/
static void remove_our_modes( int hide_or_not,
struct Channel *chptr, struct Channel *top_chptr,
struct Client *source_p)
{
remove_a_mode(hide_or_not, chptr, top_chptr, source_p, &chptr->chanops, 'o');
#ifdef REQUIRE_OANDV
remove_a_mode(hide_or_not, chptr, top_chptr, source_p, &chptr->chanops_voiced, 'o');
#endif
#ifdef HALFOPS
remove_a_mode(hide_or_not, chptr, top_chptr, source_p, &chptr->halfops, 'h');
#endif
remove_a_mode(hide_or_not, chptr, top_chptr, source_p, &chptr->voiced, 'v');
#ifdef REQUIRE_OANDV
remove_a_mode(hide_or_not, chptr, top_chptr, source_p, &chptr->chanops_voiced, 'v');
#endif
/* Move all voice/ops etc. to non opped list */
dlinkMoveList(&chptr->chanops, &chptr->peons);
#ifdef HALFOPS
dlinkMoveList(&chptr->halfops, &chptr->peons);
#endif
dlinkMoveList(&chptr->voiced, &chptr->peons);
#ifdef REQUIRE_OANDV
dlinkMoveList(&chptr->chanops_voiced, &chptr->peons);
#endif
dlinkMoveList(&chptr->locchanops, &chptr->locpeons);
#ifdef HALFOPS
dlinkMoveList(&chptr->lochalfops, &chptr->locpeons);
#endif
dlinkMoveList(&chptr->locvoiced, &chptr->locpeons);
#ifdef REQUIRE_OANDV
dlinkMoveList(&chptr->locchanops_voiced, &chptr->locpeons);
#endif
/* Clear all +beI modes */
free_channel_list(&chptr->banlist);
free_channel_list(&chptr->exceptlist);
free_channel_list(&chptr->invexlist);
chptr->banlist.head = chptr->exceptlist.head = chptr->invexlist.head = NULL;
chptr->banlist.tail = chptr->exceptlist.tail = chptr->invexlist.tail = NULL;
}
/*
* remove_a_mode
*
* inputs -
* output - NONE
* side effects - remove ONE mode from a channel
*/
static void remove_a_mode( int hide_or_not,
struct Channel *chptr, struct Channel *top_chptr,
struct Client *source_p, dlink_list *list, char flag)
{
dlink_node *ptr;
struct Client *target_p;
char buf[BUFSIZE];
char lmodebuf[MODEBUFLEN];
char *lpara[MAXMODEPARAMS];
char *chname;
int count = 0;
mbuf = lmodebuf;
*mbuf++ = '-';
lpara[0] = lpara[1] = lpara[2] = lpara[3] = "";
chname = chptr->chname;
ircsprintf(buf,":%s MODE %s ", me.name, chname);
for (ptr = list->head; ptr && ptr->data; ptr = ptr->next)
{
target_p = ptr->data;
lpara[count++] = target_p->name;
*mbuf++ = flag;
if (count >= MAXMODEPARAMS)
{
*mbuf = '\0';
sendto_channel_local(hide_or_not, chptr,
":%s MODE %s %s %s %s %s %s",
me.name,
chname,
lmodebuf,
lpara[0], lpara[1], lpara[2], lpara[3] );
mbuf = lmodebuf;
*mbuf++ = '-';
count = 0;
lpara[0] = lpara[1] = lpara[2] = lpara[3] = "";
}
}
if(count != 0)
{
*mbuf = '\0';
sendto_channel_local(hide_or_not, chptr,
":%s MODE %s %s %s %s %s %s",
me.name,
chname,
lmodebuf,
lpara[0], lpara[1], lpara[2], lpara[3] );
}
}
/*
* free_channel_list
*
* inputs - pointer to dlink_list
* output - NONE
* side effects -
*/
static void free_channel_list(dlink_list *list)
{
dlink_node *ptr;
dlink_node *next_ptr;
struct Ban *actualBan;
for (ptr = list->head; ptr; ptr = next_ptr)
{
next_ptr = ptr->next;
actualBan = ptr->data;
MyFree(actualBan->banstr);
MyFree(actualBan->who);
BlockHeapFree(ban_heap, actualBan);
free_dlink_node(ptr);
}
}

435
contrib/m_flags.c Normal file
View file

@ -0,0 +1,435 @@
/*
* m_flags.c: Implements comstud-style mode flags.
*
* Copyright 2002 by W. Campbell and the ircd-hybrid 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.
*
* $Id: m_flags.c,v 1.1 2002/08/13 14:35:15 fishwaldo Exp $
*/
/* List of ircd includes from ../include/ */
#include "stdinc.h"
#include "handlers.h"
#include "client.h"
#include "common.h" /* FALSE bleah */
#include "ircd.h"
#include "irc_string.h"
#include "numeric.h"
#include "fdlist.h"
#include "s_bsd.h"
#include "s_conf.h"
#include "s_log.h"
#include "s_serv.h"
#include "send.h"
#include "msg.h"
#include "parse.h"
#include "modules.h"
#include "s_user.h" /* send_umode_out() */
static void m_flags(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static void mo_flags(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static char *set_flags_to_string(struct Client *client_p);
static char *unset_flags_to_string(struct Client *client_p);
struct Message test_msgtab = {
"FLAGS", 0, 0, 0, 0, MFLG_SLOW, 0,
{m_unregistered, m_flags, m_ignore, mo_flags}
};
#ifndef STATIC_MODULES
void
_modinit(void)
{
mod_add_cmd(&test_msgtab);
}
void
_moddeinit(void)
{
mod_del_cmd(&test_msgtab);
}
const char *_version = "$Revision: 1.1 $";
#endif
/* FLAGS requires it's own mini parser, since the last parameter in it can
** contain a number of FLAGS. CS handles FLAGS mode1 mode2 OR
** FLAGS :mode1 mode2, but not both mixed.
**
** The best way to match a flag to a mode is with a simple table
*/
struct FlagTable
{
char *name;
int mode;
int oper;
};
static struct FlagTable flag_table[] =
{
/* name mode it represents oper only? */
{ "OWALLOPS", FLAGS_OPERWALL, 1 },
{ "SWALLOPS", FLAGS_WALLOP, 0 },
{ "STATSNOTICES", FLAGS_SPY, 1 },
/* We don't have a separate OKILL and SKILL modes */
{ "OKILLS", FLAGS_SKILL, 0 },
{ "SKILLS", FLAGS_SKILL, 0 },
{ "SNOTICES", FLAGS_SERVNOTICE, 0 },
/* We don't have separate client connect and disconnect modes */
{ "CLICONNECTS", FLAGS_CCONN, 1 },
{ "CLIDISCONNECTS", FLAGS_CCONN, 1 },
/* I'm taking a wild guess here... */
{ "THROTTLES", FLAGS_REJ, 1 },
#if 0
/* This one is special...controlled via an oper block option */
{ "NICKCHANGES", FLAGS_NCHANGE, 1 },
/* NICKCHANGES must be checked for separately */
#endif
/* I'm assuming this is correct... */
{ "IPMISMATCHES", FLAGS_UNAUTH, 1 },
{ "LWALLOPS", FLAGS_LOCOPS, 1 },
/* These aren't separate on Hybrid */
{ "CONNECTS", FLAGS_EXTERNAL, 1 },
{ "SQUITS", FLAGS_EXTERNAL, 1 },
/* Now we have our Hybrid specific flags */
{ "FULL", FLAGS_FULL, 1 },
/* Not in CS, but we might as well put it here */
{ "INVISIBLE", FLAGS_INVISIBLE, 0 },
{ "BOTS", FLAGS_BOTS, 1 },
{ "CALLERID", FLAGS_CALLERID, 0 },
{ "UNAUTH", FLAGS_UNAUTH, 1 },
{ "DEBUG", FLAGS_DEBUG, 1 },
{ NULL, 0, 0 }
};
/* We won't control CALLERID or INVISIBLE in here */
#define FL_ALL_USER_FLAGS (FLAGS_WALLOP | FLAGS_SKILL | FLAGS_SERVNOTICE )
/* and we don't control NCHANGES here either */
#define FL_ALL_OPER_FLAGS (FL_ALL_USER_FLAGS | FLAGS_CCONN | FLAGS_REJ |\
FLAGS_FULL | FLAGS_SPY | FLAGS_DEBUG |\
FLAGS_OPERWALL | FLAGS_BOTS | FLAGS_EXTERNAL |\
FLAGS_UNAUTH | FLAGS_LOCOPS )
/*
** m_flags
** parv[0] = sender prefix
** parv[1] = parameter
*/
static void m_flags(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
int i,j;
int isadd;
int setflags;
int isgood;
char *p;
char *flag;
if (parc < 2)
{
/* Generate a list of what flags you have and what you are missing,
** and send it to the user
*/
sendto_one(source_p, ":%s NOTICE %s :Current flags:%s",
me.name, parv[0], set_flags_to_string(source_p));
sendto_one(source_p, ":%s NOTICE %s :Current missing flags:%s",
me.name, parv[0], unset_flags_to_string(source_p));
return;
}
/* Preserve the current flags */
setflags = source_p->umodes;
/* XXX - change this to support a multiple last parameter like ISON */
for (i = 1; i < parc; i++)
{
for (flag = strtoken(&p, parv[i], " "); flag;
flag = strtoken(&p, NULL, " "))
{
/* We default to being in ADD mode */
isadd = 1;
/* We default to being in BAD mode */
isgood = 0;
if (!isalpha(flag[0]))
{
if (flag[0] == '-')
isadd = 0;
else if (flag[0] == '+')
isadd = 1;
flag++;
}
/* support ALL here */
if (!irccmp(flag, "ALL"))
{
if (isadd)
source_p->umodes |= FL_ALL_USER_FLAGS;
else
source_p->umodes &= ~FL_ALL_USER_FLAGS;
sendto_one(source_p, ":%s NOTICE %s :Current flags:%s",
me.name, parv[0], set_flags_to_string(source_p));
sendto_one(source_p, ":%s NOTICE %s :Current missing flags:%s",
me.name, parv[0], unset_flags_to_string(source_p));
send_umode_out(client_p, source_p, setflags);
return;
}
for (j = 0; flag_table[j].name; j++)
{
if (!flag_table[j].oper && !irccmp(flag, flag_table[j].name))
{
if (isadd)
source_p->umodes |= flag_table[j].mode;
else
source_p->umodes &= ~ (flag_table[j].mode);
isgood = 1;
continue;
}
}
/* This for ended without matching a valid FLAG, here is where
** I want to operate differently than ircd-comstud, and just ignore
** the invalid flag, send a warning and go on.
*/
if (!isgood)
sendto_one(source_p, ":%s NOTICE %s :Invalid FLAGS: %s (IGNORING)",
me.name, parv[0], flag);
}
}
/* All done setting the flags, print the notices out to the user
** telling what flags they have and what flags they are missing
*/
sendto_one(source_p, ":%s NOTICE %s :Current flags:%s",
me.name, parv[0], set_flags_to_string(source_p));
sendto_one(source_p, ":%s NOTICE %s :Current missing flags:%s",
me.name, parv[0], unset_flags_to_string(source_p));
send_umode_out(client_p, source_p, setflags);
}
/*
** mo_flags
** parv[0] = sender prefix
** parv[1] = parameter
*/
static void mo_flags(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
int i,j;
int isadd;
int setflags;
int isgood;
char *p;
char *flag;
if (parc < 2)
{
/* Generate a list of what flags you have and what you are missing,
** and send it to the user
*/
sendto_one(source_p, ":%s NOTICE %s :Current flags:%s",
me.name, parv[0], set_flags_to_string(source_p));
sendto_one(source_p, ":%s NOTICE %s :Current missing flags:%s",
me.name, parv[0], unset_flags_to_string(source_p));
return;
}
/* Preserve the current flags */
setflags = source_p->umodes;
/* XXX - change this to support a multiple last parameter like ISON */
for (i = 1; i < parc; i++)
{
for (flag = strtoken(&p, parv[i], " "); flag;
flag = strtoken(&p, NULL, " "))
{
/* We default to being in ADD mode */
isadd = 1;
/* We default to being in BAD mode */
isgood = 0;
if (!isalpha(flag[0]))
{
if (flag[0] == '-')
isadd = 0;
else if (flag[0] == '+')
isadd = 1;
flag++;
}
/* support ALL here */
if (!irccmp(flag, "ALL"))
{
if (isadd)
source_p->umodes |= FL_ALL_OPER_FLAGS;
else
source_p->umodes &= ~FL_ALL_OPER_FLAGS;
sendto_one(source_p, ":%s NOTICE %s :Current flags:%s",
me.name, parv[0], set_flags_to_string(source_p));
sendto_one(source_p, ":%s NOTICE %s :Current missing flags:%s",
me.name, parv[0], unset_flags_to_string(source_p));
send_umode_out(client_p, source_p, setflags);
return;
}
if (!irccmp(flag, "NICKCHANGES"))
{
if (!IsOperN(source_p))
{
sendto_one(source_p,
":%s NOTICE %s :*** You need oper and N flag for +n",
me.name,parv[0]);
continue;
}
if (isadd)
source_p->umodes |= FLAGS_NCHANGE;
else
source_p->umodes &= ~FLAGS_NCHANGE;
isgood = 1;
continue;
}
for (j = 0; flag_table[j].name; j++)
{
if (!irccmp(flag, flag_table[j].name))
{
if (isadd)
source_p->umodes |= flag_table[j].mode;
else
source_p->umodes &= ~ (flag_table[j].mode);
isgood = 1;
continue;
}
}
/* This for ended without matching a valid FLAG, here is where
** I want to operate differently than ircd-comstud, and just ignore
** the invalid flag, send a warning and go on.
*/
if (!isgood)
sendto_one(source_p, ":%s NOTICE %s :Invalid FLAGS: %s (IGNORING)",
me.name, parv[0], flag);
}
}
/* All done setting the flags, print the notices out to the user
** telling what flags they have and what flags they are missing
*/
sendto_one(source_p, ":%s NOTICE %s :Current flags:%s",
me.name, parv[0], set_flags_to_string(source_p));
sendto_one(source_p, ":%s NOTICE %s :Current missing flags:%s",
me.name, parv[0], unset_flags_to_string(source_p));
send_umode_out(client_p, source_p, setflags);
}
static char *set_flags_to_string(struct Client *client_p)
{
/* XXX - list all flags that we have set on the client */
static char setflags[BUFSIZE + 1];
int i;
/* Clear it to begin with, we'll be doing a lot of ircsprintf's */
setflags[0] = '\0';
/* Unlike unset_flags_to_string(), we don't have to care about oper
** flags and not showing them
*/
for (i = 0; flag_table[i].name; i++)
{
if (client_p->umodes & flag_table[i].mode)
{
ircsprintf(setflags, "%s %s", setflags, flag_table[i].name);
}
}
#if 0
if (IsOper(client_p) && IsOperN(client_p))
{
#endif
/* You can only be set +NICKCHANGES if you are an oper and
** IsOperN(client_p) is true
*/
if (client_p->umodes & FLAGS_NCHANGE)
{
ircsprintf(setflags, "%s %s", setflags, "NICKCHANGES");
}
#if 0
}
#endif
return setflags;
}
static char *unset_flags_to_string(struct Client *client_p)
{
/* Inverse of above */
/* XXX - list all flags that we do NOT have set on the client */
static char setflags[BUFSIZE + 1];
int i,isoper;
/* Clear it to begin with, we'll be doing a lot of ircsprintf's */
setflags[0] = '\0';
if (IsOper(client_p))
isoper = 1;
else
isoper = 0;
for (i = 0; flag_table[i].name; i++)
{
if ( !(client_p->umodes & flag_table[i].mode))
{
if (!isoper && flag_table[i].oper)
continue;
ircsprintf(setflags, "%s %s", setflags, flag_table[i].name);
}
}
if (IsOper(client_p) && IsOperN(client_p))
{
if ( !(client_p->umodes & FLAGS_NCHANGE))
{
ircsprintf(setflags, "%s %s", setflags, "NICKCHANGES");
}
}
return setflags;
}

314
contrib/m_force.c Normal file
View file

@ -0,0 +1,314 @@
/* contrib/m_force.c
* Copyright (C) 2002 Hybrid 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.
*
* $Id: m_force.c,v 1.1 2002/08/13 14:35:15 fishwaldo Exp $
*/
#include "stdinc.h"
#include "handlers.h"
#include "client.h"
#include "common.h" /* FALSE bleah */
#include "ircd.h"
#include "irc_string.h"
#include "numeric.h"
#include "fdlist.h"
#include "hash.h"
#include "s_bsd.h"
#include "s_conf.h"
#include "s_log.h"
#include "s_serv.h"
#include "send.h"
#include "msg.h"
#include "parse.h"
#include "modules.h"
#include "channel.h"
#include "channel_mode.h"
static void mo_forcejoin(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static void mo_forcepart(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
struct Message forcejoin_msgtab = {
"FORCEJOIN", 0, 0, 3, 0, MFLG_SLOW, 0,
{m_ignore, m_not_oper, mo_forcejoin, mo_forcejoin}
};
struct Message forcepart_msgtab = {
"FORCEPART", 0, 0, 3, 0, MFLG_SLOW, 0,
{m_ignore, m_not_oper, mo_forcepart, mo_forcepart}
};
#ifndef STATIC_MODULES
void
_modinit(void)
{
mod_add_cmd(&forcejoin_msgtab);
mod_add_cmd(&forcepart_msgtab);
}
void
_moddeinit(void)
{
mod_del_cmd(&forcejoin_msgtab);
mod_del_cmd(&forcepart_msgtab);
}
char *_version = "$Revision: 1.1 $";
#endif
/*
* m_forcejoin
* parv[0] = sender prefix
* parv[1] = user to force
* parv[2] = channel to force them into
*/
static void mo_forcejoin(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
struct Client *target_p;
struct Channel *chptr;
int type;
char mode;
char sjmode;
char *newch;
if(!IsAdmin(source_p))
{
sendto_one(source_p, ":%s NOTICE %s :You have no A flag", me.name, parv[0]);
return;
}
if((hunt_server(client_p, source_p, ":%s FORCEJOIN %s %s", 1, parc, parv)) != HUNTED_ISME)
return;
/* if target_p is not existant, print message
* to source_p and bail - scuzzy
*/
if ((target_p = find_client(parv[1])) == NULL)
{
sendto_one(source_p, form_str(ERR_NOSUCHNICK), me.name,
source_p->name, parv[1]);
return;
}
if(!IsClient(target_p))
return;
/* select our modes from parv[2] if they exist... (chanop)*/
if(*parv[2] == '@')
{
type = CHFL_CHANOP;
mode = 'o';
sjmode = '@';
}
#ifdef HALFOPS
else if(*parv[2] == '%')
{
type = CHFL_HALFOP;
mode = 'h';
sjmode = '%';
}
#endif
else if(*parv[2] == '+')
{
type = CHFL_VOICE;
mode = 'v';
sjmode = '+';
}
else
{
type = CHFL_PEON;
mode = sjmode = '\0';
}
if(mode != '\0')
parv[2]++;
if((chptr = hash_find_channel(parv[2])) != NULL)
{
if(IsMember(target_p, chptr))
{
/* debugging is fun... */
sendto_one(source_p, ":%s NOTICE %s :*** Notice -- %s is already in %s", me.name,
source_p->name, target_p->name, chptr->chname);
return;
}
add_user_to_channel(chptr, target_p, type);
if (chptr->chname[0] != '&')
sendto_server(target_p, target_p, chptr, NOCAPS, NOCAPS, LL_ICLIENT,
":%s SJOIN %lu %s + :%c%s",
me.name, (unsigned long) chptr->channelts,
chptr->chname, type ? sjmode : ' ', target_p->name);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s!%s@%s JOIN :%s",
target_p->name, target_p->username,
target_p->host, chptr->chname);
if(type)
sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +%c %s",
me.name, chptr->chname, mode, target_p->name);
if(chptr->topic != NULL)
{
sendto_one(target_p, form_str(RPL_TOPIC), me.name,
target_p->name, chptr->chname, chptr->topic);
sendto_one(target_p, form_str(RPL_TOPICWHOTIME),
me.name, source_p->name, chptr->chname,
chptr->topic_info, chptr->topic_time);
}
channel_member_names(target_p, chptr, chptr->chname, 1);
}
else
{
newch = parv[2];
if (!check_channel_name(newch))
{
sendto_one(source_p, form_str(ERR_BADCHANNAME), me.name,
source_p->name, (unsigned char*)newch);
return;
}
/* channel name must begin with & or # */
if (!IsChannelName(newch))
{
sendto_one(source_p, form_str(ERR_BADCHANNAME), me.name,
source_p->name, (unsigned char*)newch);
return;
}
/* it would be interesting here to allow an oper
* to force target_p into a channel that doesn't exist
* even more so, into a local channel when we disable
* local channels... but...
* I don't want to break anything - scuzzy
*/
if (ConfigServerHide.disable_local_channels &&
(*newch == '&'))
{
sendto_one(source_p, ":%s NOTICE %s :No such channel (%s)", me.name,
source_p->name, newch);
return;
}
/* newch can't be longer than CHANNELLEN */
if (strlen(newch) > CHANNELLEN)
{
sendto_one(source_p, ":%s NOTICE %s :Channel name is too long", me.name,
source_p->name);
return;
}
chptr = get_or_create_channel(target_p, newch, NULL);
add_user_to_channel(chptr, target_p, CHFL_CHANOP);
/* send out a join, make target_p join chptr */
if (chptr->chname[0] != '&')
sendto_server(target_p, target_p, chptr, NOCAPS, NOCAPS, LL_ICLIENT,
":%s SJOIN %lu %s +nt :@%s", me.name,
(unsigned long) chptr->channelts, chptr->chname,
target_p->name);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s!%s@%s JOIN :%s",
target_p->name, target_p->username,
target_p->host, chptr->chname);
chptr->mode.mode |= MODE_TOPICLIMIT;
chptr->mode.mode |= MODE_NOPRIVMSGS;
sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +nt", me.name,
chptr->chname);
target_p->localClient->last_join_time = CurrentTime;
channel_member_names(target_p, chptr, chptr->chname, 1);
/* we do this to let the oper know that a channel was created, this will be
* seen from the server handling the command instead of the server that
* the oper is on.
*/
sendto_one(source_p, ":%s NOTICE %s :*** Notice -- Creating channel %s", me.name,
source_p->name, chptr->chname);
}
}
static void mo_forcepart(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
struct Client *target_p;
struct Channel *chptr;
if(!IsAdmin(source_p))
{
sendto_one(source_p, ":%s NOTICE %s :You have no A flag", me.name, parv[0]);
return;
}
if((hunt_server(client_p, source_p, ":%s FORCEPART %s %s", 1, parc, parv)) != HUNTED_ISME)
return;
/* if target_p == NULL then let the oper know */
if ((target_p = find_client(parv[1])) == NULL)
{
sendto_one(source_p, form_str(ERR_NOSUCHNICK), me.name,
source_p->name, parv[1]);
return;
}
if(!IsClient(target_p))
return;
if((chptr = hash_find_channel(parv[2])) == NULL)
{
sendto_one(source_p, form_str(ERR_NOSUCHCHANNEL),
me.name, parv[0], parv[1]);
return;
}
if (!IsMember(target_p, chptr))
{
sendto_one(source_p, form_str(ERR_USERNOTINCHANNEL),
me.name, parv[0], parv[2], parv[1]);
return;
}
if (chptr->chname[0] != '&')
sendto_server(target_p, target_p, chptr, NOCAPS, NOCAPS, LL_ICLIENT,
":%s PART %s :%s",
target_p->name, chptr->chname,
target_p->name);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s!%s@%s PART %s :%s",
target_p->name, target_p->username,
target_p->host,chptr->chname,
target_p->name);
remove_user_from_channel(chptr, target_p);
}

201
contrib/m_jupe.c Normal file
View file

@ -0,0 +1,201 @@
/*
* ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
* m_jupe.c: Jupes a server.
*
* Copyright (C) 2002 by the past and present ircd coders, and others.
*
* 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
*
* $Id: m_jupe.c,v 1.1 2002/08/13 14:35:15 fishwaldo Exp $
*/
#include "stdinc.h"
#include "tools.h"
#include "irc_string.h"
#include "handlers.h"
#include "channel.h"
#include "client.h"
#include "ircd.h"
#include "numeric.h"
#include "s_log.h"
#include "s_serv.h"
#include "send.h"
#include "whowas.h"
#include "irc_string.h"
#include "hash.h"
#include "msg.h"
#include "parse.h"
#include "modules.h"
#include "class.h"
#include "common.h"
#include "event.h"
#include "fdlist.h"
#include "list.h"
#include "s_conf.h"
#include "scache.h"
static void mo_jupe(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static int bogus_host(char *host);
struct Message jupe_msgtab = {
"JUPE", 0, 0, 3, 0, MFLG_SLOW, 0,
{m_unregistered, m_not_oper, mo_jupe, mo_jupe}
};
#ifndef STATIC_MODULES
void
_modinit(void)
{
mod_add_cmd(&jupe_msgtab);
}
void
_moddeinit(void)
{
mod_del_cmd(&jupe_msgtab);
}
const char *_version = "$Revision: 1.1 $";
#endif
/*
** mo_jupe
** parv[0] = sender prefix
** parv[1] = server we're juping
** parv[2] = reason for jupe
*/
static void mo_jupe(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
struct Client *target_p;
struct Client *ajupe;
dlink_node *m;
char reason[REALLEN+2];
if(!ServerInfo.hub)
return;
if(!IsOperAdmin(source_p))
{
sendto_one(source_p, ":%s NOTICE %s :You must be an admin to use this command",
me.name, parv[0]);
return;
}
if (bogus_host(parv[1]))
{
sendto_one(source_p, ":%s NOTICE %s :Invalid servername: %s",
me.name, parv[0], parv[1]);
return;
}
if(match(parv[1], me.name))
{
sendto_one(source_p, ":%s NOTICE %s :I cant jupe myself!",
me.name, source_p->name);
return;
}
sendto_wallops_flags(FLAGS_WALLOP, &me,
"JUPE for %s requested by %s: %s",
parv[1], get_oper_name(source_p), parv[2]);
sendto_server(NULL, source_p, NULL, NOCAPS, NOCAPS, LL_ICLIENT,
":%s WALLOPS :JUPE for %s requested by %s!%s@%s: %s",
parv[0], parv[1], source_p->name,
source_p->username, source_p->host, parv[2]);
ilog(L_NOTICE, "JUPE for %s requested by %s: %s",
parv[1], get_oper_name(source_p), parv[2]);
target_p= find_server(parv[1]);
if(target_p)
exit_client(client_p, target_p, &me, parv[2]);
sendto_server(NULL, NULL, NULL, NOCAPS, NOCAPS, NOFLAGS,
":%s SERVER %s 1 :JUPED: %s",
me.name, parv[1], parv[2]);
sendto_realops_flags(FLAGS_ALL, L_ALL,
"Link with %s established: (JUPED) link",
parv[1]);
ajupe = make_client(NULL);
/* make_client() adds client to unknown_list */
m = dlinkFind(&unknown_list, ajupe);
if(m != NULL)
dlinkDelete(m, &unknown_list);
free_dlink_node(m);
make_server(ajupe);
ajupe->hopcount = 1;
strlcpy(ajupe->name,parv[1],HOSTLEN);
/* we need to give 7 chars to prepend "JUPED: " */
if(strlen(parv[2]) > (REALLEN-7))
parv[2][REALLEN-7] = '\0';
ircsprintf(reason, "%s %s", "JUPED:", parv[2]);
strlcpy(ajupe->info,reason,REALLEN);
ajupe->serv->up = me.name;
ajupe->servptr = &me;
SetServer(ajupe);
SetDead(ajupe);
Count.server++;
Count.myserver++;
/* Some day, all these lists will be consolidated *sigh* */
add_client_to_list(ajupe);
add_to_client_hash_table(ajupe->name, ajupe);
add_client_to_llist(&(ajupe->servptr->serv->servers), ajupe);
add_server_to_list(ajupe);
}
/*
* bogus_host
*
* inputs - hostname
* output - 1 if a bogus hostname input, 0 if its valid
* side effects - none
*/
int bogus_host(char *host)
{
int bogus_server = 0;
char *s;
int dots = 0;
for( s = host; *s; s++ )
{
if (!IsServChar(*s))
{
bogus_server = 1;
break;
}
if ('.' == *s)
++dots;
}
if (!dots || bogus_server || strlen(host) > HOSTLEN)
return 1;
return 0;
}

370
contrib/m_ltrace.c Normal file
View file

@ -0,0 +1,370 @@
/*
* ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
* m_ltrace.c: Traces a path to a client/server.
*
* Copyright (C) 2002 Hybrid 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
*
* $Id: m_ltrace.c,v 1.1 2002/08/13 14:35:16 fishwaldo Exp $
*/
#include "stdinc.h"
#include "handlers.h"
#include "class.h"
#include "hook.h"
#include "client.h"
#include "hash.h"
#include "common.h"
#include "hash.h"
#include "irc_string.h"
#include "ircd.h"
#include "numeric.h"
#include "fdlist.h"
#include "s_bsd.h"
#include "s_serv.h"
#include "send.h"
#include "msg.h"
#include "parse.h"
#include "modules.h"
static void m_ltrace(struct Client *, struct Client *, int, char **);
static void mo_ltrace(struct Client*, struct Client*, int, char**);
static struct Client* next_client_double(struct Client *next, const char* ch);
static void ltrace_spy(struct Client *);
struct Message ltrace_msgtab = {
"LTRACE", 0, 0, 0, 0, MFLG_SLOW, 0,
{m_unregistered, m_ltrace, mo_ltrace, mo_ltrace}
};
#ifndef STATIC_MODULES
void
_modinit(void)
{
hook_add_event("doing_ltrace");
mod_add_cmd(&ltrace_msgtab);
}
void
_moddeinit(void)
{
hook_del_event("doing_ltrace");
mod_del_cmd(&ltrace_msgtab);
}
const char *_version = "$Revision: 1.1 $";
#endif
static int report_this_status(struct Client *source_p, struct Client *target_p,int dow,
int link_u_p, int link_u_s);
/*
* m_ltrace()
*
* parv[0] = sender prefix
* parv[1] = target client/server to trace
*/
static void m_ltrace(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
char *tname;
if (parc > 1)
tname = parv[1];
else
tname = me.name;
sendto_one(source_p, form_str(RPL_ENDOFTRACE), me.name, parv[0], tname);
}
/*
* mo_ltrace
* parv[0] = sender prefix
* parv[1] = servername
*/
static void mo_ltrace(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
struct Client *target_p = NULL;
char *tname;
int doall, link_s[MAXCONNECTIONS], link_u[MAXCONNECTIONS];
int wilds, dow;
dlink_node *ptr;
char *looking_for = parv[0];
if(!IsClient(source_p))
return;
if (parc > 1)
tname = parv[1];
else
tname = me.name;
if(!IsOper(source_p))
{
sendto_one(source_p, form_str(RPL_ENDOFTRACE), me.name, parv[0], tname);
return;
}
if (parc > 2)
if (hunt_server(client_p, source_p, ":%s LTRACE %s :%s", 2, parc, parv))
return;
switch (hunt_server(client_p, source_p, ":%s LTRACE :%s", 1, parc, parv))
{
case HUNTED_PASS: /* note: gets here only if parv[1] exists */
{
struct Client *ac2ptr;
ac2ptr = next_client_double(GlobalClientList, tname);
if (ac2ptr)
sendto_one(source_p, form_str(RPL_TRACELINK), me.name, looking_for,
ircd_version, debugmode, tname, ac2ptr->from->name);
else
sendto_one(source_p, form_str(RPL_TRACELINK), me.name, looking_for,
ircd_version, debugmode, tname, "ac2ptr_is_NULL!!");
return;
}
case HUNTED_ISME:
break;
default:
return;
}
ltrace_spy(source_p);
doall = (parv[1] && (parc > 1)) ? match(tname, me.name): TRUE;
wilds = !parv[1] || strchr(tname, '*') || strchr(tname, '?');
dow = wilds || doall;
set_time();
/* lusers cant issue ltrace.. */
if(!IsOper(source_p) || !dow)
{
const char* name;
const char* class_name;
char ipaddr[HOSTIPLEN];
target_p = find_client(tname);
if(target_p && IsPerson(target_p))
{
name = get_client_name(target_p, HIDE_IP);
inetntop(target_p->localClient->aftype, &IN_ADDR(target_p->localClient->ip), ipaddr, HOSTIPLEN);
class_name = get_client_class(target_p);
if (IsOper(target_p))
sendto_one(source_p, form_str(RPL_TRACEOPERATOR),
me.name, parv[0], class_name, name,
MyOper(source_p) ? ipaddr :
(IsIPSpoof(target_p) ? "255.255.255.255" : ipaddr),
CurrentTime - target_p->lasttime,
(target_p->user) ? (CurrentTime - target_p->user->last) : 0);
}
sendto_one(source_p, form_str(RPL_ENDOFTRACE),me.name,
parv[0], tname);
return;
}
memset((void *)link_s,0,sizeof(link_s));
memset((void *)link_u,0,sizeof(link_u));
/*
* Count up all the servers and clients in a downlink.
*/
if (doall)
{
for (target_p = GlobalClientList; target_p; target_p = target_p->next)
{
if (IsPerson(target_p))
{
link_u[target_p->from->localClient->fd]++;
}
else if (IsServer(target_p))
{
link_s[target_p->from->localClient->fd]++;
}
}
}
/* report all opers */
for (ptr = lclient_list.head; ptr; ptr = ptr->next)
{
target_p = ptr->data;
if(!IsOper(target_p))
continue;
if (!doall && wilds && !match(tname, target_p->name))
continue;
if (!dow && irccmp(tname, target_p->name))
continue;
report_this_status(source_p,target_p,dow,0,0);
}
/* report all servers */
for (ptr = serv_list.head; ptr; ptr = ptr->next)
{
target_p = ptr->data;
if (!doall && wilds && !match(tname, target_p->name))
continue;
if (!dow && irccmp(tname, target_p->name))
continue;
report_this_status(source_p, target_p, dow,
link_u[target_p->localClient->fd],
link_s[target_p->localClient->fd]);
}
sendto_one(source_p, form_str(RPL_ENDOFTRACE),me.name, parv[0],tname);
}
/*
* report_this_status
*
* inputs - pointer to client to report to
* - pointer to client to report about
* output - counter of number of hits
* side effects - NONE
*/
static int report_this_status(struct Client *source_p, struct Client *target_p,
int dow, int link_u_p, int link_s_p)
{
const char* name;
const char* class_name;
char ip[HOSTIPLEN];
inetntop(target_p->localClient->aftype, &IN_ADDR(target_p->localClient->ip), ip, HOSTIPLEN);
name = get_client_name(target_p, HIDE_IP);
class_name = get_client_class(target_p);
set_time();
switch(target_p->status)
{
case STAT_CONNECTING:
sendto_one(source_p, form_str(RPL_TRACECONNECTING), me.name,
source_p->name, class_name,
IsOperAdmin(source_p) ? name : target_p->name);
break;
case STAT_HANDSHAKE:
sendto_one(source_p, form_str(RPL_TRACEHANDSHAKE), me.name,
source_p->name, class_name,
IsOperAdmin(source_p) ? name : target_p->name);
break;
case STAT_ME:
case STAT_UNKNOWN:
break;
case STAT_CLIENT:
if (IsAdmin(target_p))
sendto_one(source_p, form_str(RPL_TRACEOPERATOR),
me.name, source_p->name, class_name, name,
IsOperAdmin(source_p) ? ip : "255.255.255.255",
CurrentTime - target_p->lasttime,
(target_p->user) ? (CurrentTime - target_p->user->last) : 0);
else if (IsOper(target_p))
sendto_one(source_p, form_str(RPL_TRACEOPERATOR),
me.name, source_p->name, class_name, name,
MyOper(source_p) ? ip :
(IsIPSpoof(target_p) ? "255.255.255.255" : ip),
CurrentTime - target_p->lasttime,
(target_p->user)?(CurrentTime - target_p->user->last):0);
break;
case STAT_SERVER:
if(!IsOperAdmin(source_p))
name = get_client_name(target_p, MASK_IP);
sendto_one(source_p, form_str(RPL_TRACESERVER),
me.name, source_p->name, class_name, link_s_p,
link_u_p, name, *(target_p->serv->by) ?
target_p->serv->by : "*", "*",
me.name, CurrentTime - target_p->lasttime);
break;
default: /* ...we actually shouldn't come here... --msa */
sendto_one(source_p, form_str(RPL_TRACENEWTYPE), me.name,
source_p->name, name);
break;
}
return 0;
}
/* ltrace_spy()
*
* input - pointer to client
* output - none
* side effects - hook event doing_trace is called
*/
static void ltrace_spy(struct Client *source_p)
{
struct hook_spy_data data;
data.source_p = source_p;
hook_call_event("doing_ltrace", &data);
}
/*
* this slow version needs to be used for hostmasks *sigh
*
* next_client_double - find the next matching client.
* The search can be continued from the specified client entry.
* Normal usage loop is:
*
* for (x = client; x = next_client_double(x,mask); x = x->next)
* HandleMatchingClient;
*
*/
static struct Client*
next_client_double(struct Client *next, /* First client to check */
const char* ch) /* search string (may include wilds) */
{
struct Client *tmp = next;
next = find_client(ch);
if (next == NULL)
next = tmp;
if (tmp && tmp->prev == next)
return NULL;
if (next != tmp)
return next;
for ( ; next; next = next->next)
{
if (match(ch,next->name) || match(next->name,ch))
break;
}
return next;
}

156
contrib/m_map.c Normal file
View file

@ -0,0 +1,156 @@
/*
* ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
* m_map.c: Sends an Undernet compatible map to a user.
*
* Copyright (C) 2002 by the past and present ircd coders, and others.
*
* 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
*
* $Id: m_map.c,v 1.1 2002/08/13 14:35:16 fishwaldo Exp $
*/
#include "stdinc.h"
#include "client.h"
#include "modules.h"
#include "handlers.h"
#include "numeric.h"
#include "send.h"
#include "s_conf.h"
#define USER_COL 50 /* display | Users: %d at col 50 */
static void m_map(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static void mo_map(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static void dump_map(struct Client *client_p,struct Client *root, char *pbuf);
struct Message map_msgtab = {
"MAP", 0, 0, 0, 0, MFLG_SLOW, 0,
{m_unregistered, m_map, m_ignore, mo_map}
};
#ifndef STATIC_MODULES
void _modinit(void)
{
mod_add_cmd(&map_msgtab);
}
void _moddeinit(void)
{
mod_del_cmd(&map_msgtab);
}
const char *_version = "$Revision: 1.1 $";
#endif
static char buf[BUFSIZE];
/* m_map
** parv[0] = sender prefix
*/
static void m_map(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
if (!ConfigServerHide.flatten_links)
{
dump_map(client_p,&me,buf);
sendto_one(client_p, form_str(RPL_MAPEND), me.name, client_p->name);
return;
}
m_not_oper(client_p,source_p,parc,parv);
return;
}
/*
** mo_map
** parv[0] = sender prefix
*/
static void mo_map(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
dump_map(client_p,&me,buf);
sendto_one(client_p, form_str(RPL_MAPEND), me.name, client_p->name);
}
/*
** dump_map
** dumps server map, called recursively.
*/
static void dump_map(struct Client *client_p,struct Client *root_p, char *pbuf)
{
int cnt = 0, i = 0, len;
int users = 0;
struct Client *server_p,*user_p;
*pbuf= '\0';
strncat(pbuf,root_p->name,BUFSIZE - ((size_t) pbuf - (size_t) buf));
len = strlen(buf);
buf[len] = ' ';
if (len < USER_COL)
{
for (i = len+1; i < USER_COL; i++)
{
buf[i] = '-';
}
}
/* FIXME: add serv->usercnt */
for( user_p = root_p->serv->users; user_p; user_p = user_p->lnext )
users++;
snprintf(buf + USER_COL, BUFSIZE - USER_COL,
" | Users: %5d (%4.1f%%)", users,
100 * (float) users / (float) Count.total);
sendto_one(client_p, form_str(RPL_MAP),me.name,client_p->name,buf);
if ((server_p = root_p->serv->servers))
{
for (; server_p; server_p = server_p->lnext)
{
cnt++;
}
if (cnt)
{
if (pbuf > buf + 3)
{
pbuf[-2] = ' ';
if (pbuf[-3] == '`')
pbuf[-3] = ' ';
}
}
}
for (i = 1,server_p = root_p->serv->servers; server_p; server_p=server_p->lnext)
{
*pbuf = ' ';
if (i < cnt)
*(pbuf + 1) = '|';
else
*(pbuf + 1) = '`';
*(pbuf + 2) = '-';
*(pbuf + 3) = ' ';
dump_map(client_p,server_p,pbuf+4);
i++;
}
}

168
contrib/m_mkpasswd.c Normal file
View file

@ -0,0 +1,168 @@
/*
* m_mkpasswd.c: Encrypts a password online, DES or MD5.
*
* Copyright 2002 W. Campbell and the ircd-hybrid development team
* Based on mkpasswd.c, originally by Nelson Minar (minar@reed.edu)
*
* You can use this code in any way as long as these names remain.
*
* $Id: m_mkpasswd.c,v 1.1 2002/08/13 14:35:16 fishwaldo Exp $
*/
/* List of ircd includes from ../include/ */
#include "stdinc.h"
#include "handlers.h"
#include "client.h"
#include "common.h" /* FALSE bleah */
#include "ircd.h"
#include "irc_string.h"
#include "numeric.h"
#include "fdlist.h"
#include "s_bsd.h"
#include "s_conf.h"
#include "s_log.h"
#include "s_serv.h"
#include "send.h"
#include "msg.h"
#include "parse.h"
#include "modules.h"
#include <string.h>
extern char *crypt();
static void m_mkpasswd(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static void mo_mkpasswd(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static char *make_salt(void);
static char *make_md5_salt(void);
static char saltChars[] = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789./";
struct Message test_msgtab = {
"MKPASSWD", 0, 0, 1, 2, MFLG_SLOW, 0,
{m_unregistered, m_mkpasswd, m_ignore, mo_mkpasswd}
};
#ifndef STATIC_MODULES
void _modinit(void)
{
mod_add_cmd(&test_msgtab);
}
void _moddeinit(void)
{
mod_del_cmd(&test_msgtab);
}
const char *_version = "$Revision: 1.1 $";
#endif
static void m_mkpasswd(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
static time_t last_used = 0;
int is_md5 = 0;
if ((last_used + ConfigFileEntry.pace_wait) > CurrentTime)
{
/* safe enough to give this on a local connect only */
sendto_one(source_p,form_str(RPL_LOAD2HI),me.name,parv[0]);
return;
}
else
{
last_used = CurrentTime;
}
if (parc == 3)
{
if (!irccmp(parv[2], "MD5"))
{
is_md5 = 1;
}
else if (!irccmp(parv[2], "DES"))
{
/* Not really needed, but we may want to have a default encryption
* setting somewhere down the road
*/
is_md5 = 0;
}
else
{
sendto_one(source_p, ":%s NOTICE %s :MKPASSWD syntax error: MKPASSWD pass [DES|MD5]", me.name, parv[0]);
return;
}
}
if(parc == 1)
sendto_one(source_p, form_str(ERR_NEEDMOREPARAMS),
me.name, parv[0], "MKPASSWD");
else
sendto_one(source_p, ":%s NOTICE %s :Encryption for [%s]: %s",
me.name, parv[0], parv[1], crypt(parv[1],
is_md5 ? make_md5_salt() : make_salt()));
}
/*
** mo_test
** parv[0] = sender prefix
** parv[1] = parameter
*/
static void mo_mkpasswd(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
int is_md5 = 0;
if (parc == 3)
{
if (!irccmp(parv[2], "MD5"))
{
is_md5 = 1;
}
else if (!irccmp(parv[2], "DES"))
{
/* Not really needed, but we may want to have a default encryption
* setting somewhere down the road
*/
is_md5 = 0;
}
else
{
sendto_one(source_p, ":%s NOTICE %s :MKPASSWD syntax error: MKPASSWD pass [DES|MD5]", me.name, parv[0]);
return;
}
}
if (parc == 1)
sendto_one(source_p, form_str(ERR_NEEDMOREPARAMS),
me.name, parv[0], "MKPASSWD");
else
sendto_one(source_p, ":%s NOTICE %s :Encryption for [%s]: %s",
me.name, parv[0], parv[1], crypt(parv[1],
is_md5 ? make_md5_salt() : make_salt()));
}
static char *make_salt(void)
{
static char salt[3];
salt[0] = saltChars[random() % 64];
salt[1] = saltChars[random() % 64];
salt[2] = '\0';
return salt;
}
static char *make_md5_salt(void)
{
static char salt[13];
int i;
salt[0] = '$';
salt[1] = '1';
salt[2] = '$';
for (i=3; i<11; i++)
salt[i] = saltChars[random() % 64];
salt[11] = '$';
salt[12] = '\0';
return salt;
}

203
contrib/m_ojoin.c Normal file
View file

@ -0,0 +1,203 @@
/* contrib/m_ojoin.c
* Copyright (C) 2002 Hybrid 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 1, or (at your option)
* any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id: m_ojoin.c,v 1.1 2002/08/13 14:35:16 fishwaldo Exp $
*/
#include "stdinc.h"
#include "tools.h"
#include "handlers.h"
#include "channel.h"
#include "client.h"
#include "ircd.h"
#include "numeric.h"
#include "s_log.h"
#include "s_serv.h"
#include "send.h"
#include "whowas.h"
#include "irc_string.h"
#include "hash.h"
#include "msg.h"
#include "parse.h"
#include "modules.h"
#include "vchannel.h"
#include "list.h"
#include "channel_mode.h"
static void mo_ojoin(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
struct Message ojoin_msgtab = {
"OJOIN", 0, 0, 2, 0, MFLG_SLOW, 0,
{m_unregistered, m_not_oper, m_ignore, mo_ojoin}
};
void
_modinit(void)
{
mod_add_cmd(&ojoin_msgtab);
}
void
_moddeinit(void)
{
mod_del_cmd(&ojoin_msgtab);
}
char *_version = "$Revision: 1.1 $";
/*
** mo_ojoin
** parv[0] = sender prefix
** parv[1] = channel
*/
static void mo_ojoin(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
struct Channel *chptr, *root_chptr;
int move_me = 0;
#ifdef VCHANS
int on_vchan = 0;
#endif
/* admins only */
if (!IsOperAdmin(source_p))
{
sendto_one(source_p, ":%s NOTICE %s :You have no A flag", me.name, parv[0]);
return;
}
/* XXX - we might not have CBURSTed this channel if we are a lazylink
* yet. */
if (*parv[1] == '@' || *parv[1] == '%' || *parv[1] == '+')
{
parv[1]++;
move_me = 1;
}
chptr= hash_find_channel(parv[1]);
root_chptr = chptr;
#ifdef VCHANS
if (chptr && parc > 2 && parv[2][0] == '!')
{
chptr = find_vchan(chptr, parv[2]);
if (root_chptr != chptr)
on_vchan++;
}
#endif
if( chptr == NULL )
{
sendto_one(source_p, form_str(ERR_NOSUCHCHANNEL),
me.name, parv[0], parv[1]);
return;
}
if(IsMember(source_p, chptr))
{
sendto_one(source_p, ":%s NOTICE %s :Please part %s before using OJOIN",
me.name, source_p->name, parv[1]);
return;
}
if (move_me == 1)
parv[1]--;
if (*parv[1] == '@')
{
add_user_to_channel(chptr, source_p, CHFL_CHANOP);
if (chptr->chname[0] != '&')
sendto_server(client_p, source_p, chptr, NOCAPS, NOCAPS, LL_ICLIENT,
":%s SJOIN %lu %s + :@%s", me.name, chptr->channelts,
chptr->chname, source_p->name);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s!%s@%s JOIN %s",
source_p->name,
source_p->username,
source_p->host,
root_chptr->chname);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +o %s",
me.name, chptr->chname, source_p->name);
}
#ifdef HALFOPS
else if (*parv[1] == '%')
{
add_user_to_channel(chptr, source_p, CHFL_HALFOP);
if (chptr->chname[0] != '&')
sendto_server(client_p, source_p, chptr, NOCAPS, NOCAPS, LL_ICLIENT,
":%s SJOIN %lu %s + :%%%s", me.name, chptr->channelts,
chptr->chname, source_p->name);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s!%s@%s JOIN %s",
source_p->name,
source_p->username,
source_p->host,
root_chptr->chname);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +h %s",
me.name, chptr->chname, source_p->name);
}
#endif
else if (*parv[1] == '+')
{
add_user_to_channel(chptr, source_p, CHFL_VOICE);
if (chptr->chname[0] != '&')
sendto_server(client_p, source_p, chptr, NOCAPS, NOCAPS, LL_ICLIENT,
":%s SJOIN %lu %s + :+%s", me.name, chptr->channelts,
chptr->chname, source_p->name);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s!%s@%s JOIN %s",
source_p->name,
source_p->username,
source_p->host,
root_chptr->chname);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s MODE %s +v %s",
me.name, chptr->chname, source_p->name);
}
else
{
add_user_to_channel(chptr, source_p, CHFL_PEON);
if (chptr->chname[0] != '&')
sendto_server(client_p, source_p, chptr, NOCAPS, NOCAPS, LL_ICLIENT,
":%s SJOIN %lu %s + :%s",
me.name, chptr->channelts,
chptr->chname, source_p->name);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s!%s@%s JOIN %s",
source_p->name,
source_p->username,
source_p->host,
root_chptr->chname);
}
/* send the topic... */
if (chptr->topic != NULL)
{
sendto_one(source_p, form_str(RPL_TOPIC), me.name,
source_p->name, chptr->chname, chptr->topic);
sendto_one(source_p, form_str(RPL_TOPICWHOTIME), me.name,
source_p->name, chptr->chname, chptr->topic_info,
chptr->topic_time);
}
/* XXX - check this isn't too big above... */
#ifdef VCHANS
if (on_vchan)
add_vchan_to_client_cache(source_p,root_chptr,chptr);
#endif
source_p->localClient->last_join_time = CurrentTime;
channel_member_names(source_p, chptr, chptr->chname, 1);
}

206
contrib/m_opme.c Normal file
View file

@ -0,0 +1,206 @@
/* contrib/m_opme.c
* Copyright (C) 2002 Hybrid 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 1, or (at your option)
* any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id: m_opme.c,v 1.1 2002/08/13 14:35:16 fishwaldo Exp $
*/
#include "stdinc.h"
#include "tools.h"
#include "handlers.h"
#include "channel.h"
#include "client.h"
#include "ircd.h"
#include "numeric.h"
#include "s_log.h"
#include "s_serv.h"
#include "send.h"
#include "whowas.h"
#include "irc_string.h"
#include "hash.h"
#include "msg.h"
#include "parse.h"
#include "modules.h"
#include "vchannel.h"
static void mo_opme(struct Client *client_p, struct Client *source_p,
int parc, char *parv[]);
static int chan_is_opless(struct Channel *chptr);
struct Message opme_msgtab = {
"OPME", 0, 0, 2, 0, MFLG_SLOW, 0,
{m_unregistered, m_not_oper, m_ignore, mo_opme}
};
void
_modinit(void)
{
mod_add_cmd(&opme_msgtab);
}
void
_moddeinit(void)
{
mod_del_cmd(&opme_msgtab);
}
char *_version = "$Revision: 1.1 $";
static int chan_is_opless(struct Channel *chptr)
{
if (chptr->chanops.head)
return 0;
else
return 1;
}
/*
** mo_opme
** parv[0] = sender prefix
** parv[1] = channel
*/
static void mo_opme(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
struct Channel *chptr, *root_chptr;
int on_vchan = 0;
dlink_node *ptr;
dlink_node *locptr;
/* admins only */
if (!IsAdmin(source_p))
{
sendto_one(source_p, ":%s NOTICE %s :You have no A flag", me.name,
parv[0]);
return;
}
/* XXX - we might not have CBURSTed this channel if we are a lazylink
* yet. */
chptr= hash_find_channel(parv[1]);
root_chptr = chptr;
#ifdef VCHANS
if (chptr && parc > 2 && parv[2][0] == '!')
{
chptr = find_vchan(chptr, parv[2]);
if (root_chptr != chptr)
on_vchan++;
}
#endif
if( chptr == NULL )
{
sendto_one(source_p, form_str(ERR_NOSUCHCHANNEL),
me.name, parv[0], parv[1]);
return;
}
if (!chan_is_opless(chptr))
{
sendto_one(source_p, ":%s NOTICE %s :%s Channel is not opless",
me.name, parv[0], parv[1]);
return;
}
if ((ptr = find_user_link(&chptr->peons, source_p)))
dlinkDelete(ptr, &chptr->peons);
else if ((ptr = find_user_link(&chptr->voiced, source_p)))
dlinkDelete(ptr, &chptr->voiced);
#ifdef HALFOPS
else if ((ptr = find_user_link(&chptr->halfops, source_p)))
dlinkDelete(ptr, &chptr->halfops);
#endif
else if ((ptr = find_user_link(&chptr->chanops, source_p)))
dlinkDelete(ptr, &chptr->chanops);
#ifdef REQUIRE_OANDV
else if((ptr = find_user_link(&chptr->chanops_voiced, source_p)))
dlinkDelete(ptr, &chptr->chanops_voiced);
#endif
else
{
/* Theyre not even on the channel, bail. */
return;
}
if((locptr = find_user_link(&chptr->locpeons, source_p)))
dlinkDelete(locptr, &chptr->locpeons);
else if((locptr = find_user_link(&chptr->locvoiced, source_p)))
dlinkDelete(locptr, &chptr->locvoiced);
#ifdef HALFOPS
else if((locptr = find_user_link(&chptr->lochalfops, source_p)))
dlinkDelete(locptr, &chptr->lochalfops);
#endif
else if((locptr = find_user_link(&chptr->locchanops, source_p)))
dlinkDelete(locptr, &chptr->locchanops);
#ifdef REQUIRE_OANDV
else if((locptr = find_user_link(&chptr->locchanops_voiced, source_p)))
dlinkDelete(locptr, &chptr->locchanops_voiced);
#endif
else
return;
dlinkAdd(source_p, ptr, &chptr->chanops);
dlinkAdd(source_p, locptr, &chptr->locchanops);
if (!on_vchan)
{
sendto_wallops_flags(FLAGS_WALLOP, &me,
"OPME called for [%s] by %s!%s@%s",
parv[1], source_p->name, source_p->username,
source_p->host);
sendto_server(NULL, source_p, NULL, NOCAPS, NOCAPS, LL_ICLIENT,
":%s WALLOPS :OPME called for [%s] by %s!%s@%s",
me.name, parv[1], source_p->name, source_p->username,
source_p->host);
ilog(L_NOTICE, "OPME called for [%s] by %s!%s@%s",
parv[1], source_p->name, source_p->username,
source_p->host);
}
else
{
sendto_wallops_flags(FLAGS_WALLOP, &me,
"OPME called for [%s %s] by %s!%s@%s",
parv[1], parv[2], source_p->name,
source_p->username, source_p->host);
sendto_server(NULL, source_p, NULL, NOCAPS, NOCAPS, LL_ICLIENT,
":%s WALLOPS :OPME called for [%s %s] by %s!%s@%s",
me.name, parv[1], parv[2], source_p->name,
source_p->username, source_p->host);
ilog(L_NOTICE, "OPME called for [%s %s] by %s!%s@%s",
parv[1], parv[2], source_p->name, source_p->username,
source_p->host);
}
sendto_server(NULL, source_p, chptr, CAP_UID, NOCAPS, NOFLAGS,
":%s PART %s", ID(source_p), parv[1]);
sendto_server(NULL, source_p, chptr, NOCAPS, CAP_UID, NOFLAGS,
":%s PART %s", source_p->name, parv[1]);
sendto_server(NULL, source_p, chptr, CAP_UID, NOCAPS, NOFLAGS,
":%s SJOIN %ld %s + :@%s",
me.name, (signed long) chptr->channelts,
parv[1],
source_p->name /* XXX ID(source_p) */ );
sendto_server(NULL, source_p, chptr, NOCAPS, CAP_UID, NOFLAGS,
":%s SJOIN %ld %s + :@%s",
me.name, (signed long) chptr->channelts,
parv[1], source_p->name);
sendto_channel_local(ALL_MEMBERS, chptr,
":%s MODE %s +o %s",
me.name, parv[1], source_p->name);
}

162
contrib/m_tburst.c Normal file
View file

@ -0,0 +1,162 @@
/* contrib/m_tburst.c
* Copyright (C) 2002 Hybrid 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.
*
* $Id: m_tburst.c,v 1.1 2002/08/13 14:35:17 fishwaldo Exp $
*/
#include "stdinc.h"
#include "handlers.h"
#include "client.h"
#include "common.h"
#include "ircd.h"
#include "send.h"
#include "msg.h"
#include "modules.h"
#include "hook.h"
#include "hash.h"
#include "s_serv.h"
#include "s_conf.h"
/* TBURST_PROPAGATE
*
* If this is defined, when we receive a TBURST thats successful
* (ie: our topic changes), the TBURST will be propagated to other
* servers that support TBURST
*/
#define TBURST_PROPAGATE
static void ms_tburst(struct Client *, struct Client *, int, char **);
static void set_topic(struct Client *, struct Channel *,
time_t, char *, char *);
static void set_tburst_capab();
static void unset_tburst_capab();
int send_tburst(struct hook_burst_channel *);
struct Message tburst_msgtab = {
"TBURST", 0, 0, 6, 0, MFLG_SLOW, 0,
{m_ignore, m_ignore, ms_tburst, m_ignore}
};
#ifndef STATIC_MODULES
void
_modinit(void)
{
mod_add_cmd(&tburst_msgtab);
hook_add_hook("burst_channel", (hookfn *)send_tburst);
set_tburst_capab();
}
void
_moddeinit(void)
{
mod_del_cmd(&tburst_msgtab);
hook_del_hook("burst_channel", (hookfn *)send_tburst);
unset_tburst_capab();
}
const char *_version = "$Revision: 1.1 $";
#endif
/* ms_tburst()
*
* parv[0] = sender prefix
* parv[1] = channel timestamp
* parv[2] = channel
* parv[3] = topic timestamp
* parv[4] = topic setter
* parv[5] = topic
*/
static void ms_tburst(struct Client *client_p, struct Client *source_p,
int parc, char *parv[])
{
struct Channel *chptr;
time_t newchannelts;
time_t newtopicts;
newchannelts = atol(parv[1]);
newtopicts = atol(parv[3]);
if((chptr = hash_find_channel(parv[2])))
{
if(chptr->channelts < newchannelts)
return;
else if(chptr->channelts == newchannelts)
{
if(chptr->topic == NULL || (chptr->topic_time > newtopicts))
set_topic(source_p, chptr, newtopicts, parv[4], parv[5]);
else
return;
}
else
set_topic(source_p, chptr, newtopicts, parv[4], parv[5]);
}
}
static void set_topic(struct Client *source_p, struct Channel *chptr,
time_t newtopicts, char *topicwho, char *topic)
{
set_channel_topic(chptr, topic, topicwho, newtopicts);
sendto_channel_local(ALL_MEMBERS, chptr, ":%s TOPIC %s :%s",
ConfigServerHide.hide_servers ? me.name : source_p->name,
chptr->chname, chptr->topic == NULL ? "" : chptr->topic);
#ifdef TBURST_PROPAGATE
sendto_server(source_p, NULL, chptr, CAP_TBURST, NOCAPS, NOFLAGS,
":%s TBURST %ld %s %ld %s :%s",
source_p->name, chptr->channelts, chptr->chname,
chptr->topic_time,
chptr->topic_info == NULL ? "" : chptr->topic_info,
chptr->topic == NULL ? "" : chptr->topic);
#endif
}
static void set_tburst_capab()
{
default_server_capabs |= CAP_TBURST;
}
static void unset_tburst_capab()
{
default_server_capabs &= ~CAP_TBURST;
}
int send_tburst(struct hook_burst_channel *data)
{
if(data->chptr->topic != NULL && IsCapable(data->client, CAP_TBURST))
sendto_one(data->client, ":%s TBURST %ld %s %ld %s :%s",
me.name, data->chptr->channelts, data->chptr->chname,
data->chptr->topic_time, data->chptr->topic_info,
data->chptr->topic);
return 0;
}

View file

@ -0,0 +1,55 @@
/*
* ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
* spy_admin_notice.c: Sends a notice when someone uses ADMIN.
*
* Copyright (C) 2002 by the past and present ircd coders, and others.
*
* 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
*
* $Id: spy_admin_notice.c,v 1.1 2002/08/13 14:35:17 fishwaldo Exp $
*/
#include "stdinc.h"
#include "modules.h"
#include "hook.h"
#include "client.h"
#include "ircd.h"
#include "send.h"
int show_admin(struct hook_spy_data *);
void
_modinit(void)
{
hook_add_hook("doing_admin", (hookfn *)show_admin);
}
void
_moddeinit(void)
{
hook_del_hook("doing_admin", (hookfn *)show_admin);
}
const char *_version = "$Revision: 1.1 $";
int show_admin(struct hook_spy_data *data)
{
sendto_realops_flags(FLAGS_SPY, L_ALL,
"admin requested by %s (%s@%s) [%s]",
data->source_p->name, data->source_p->username,
data->source_p->host, data->source_p->user->server);
return 0;
}

55
contrib/spy_info_notice.c Normal file
View file

@ -0,0 +1,55 @@
/*
* ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
* spy_info_notice.c: Sends a notice when someone uses INFO.
*
* Copyright (C) 2002 by the past and present ircd coders, and others.
*
* 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
*
* $Id: spy_info_notice.c,v 1.1 2002/08/13 14:35:17 fishwaldo Exp $
*/
#include "stdinc.h"
#include "modules.h"
#include "hook.h"
#include "client.h"
#include "ircd.h"
#include "send.h"
int show_info(struct hook_spy_data *);
void
_modinit(void)
{
hook_add_hook("doing_info", (hookfn *)show_info);
}
void
_moddeinit(void)
{
hook_del_hook("doing_info", (hookfn *)show_info);
}
const char *_version = "$Revision: 1.1 $";
int show_info(struct hook_spy_data *data)
{
sendto_realops_flags(FLAGS_SPY, L_ALL,
"info requested by %s (%s@%s) [%s]",
data->source_p->name, data->source_p->username,
data->source_p->host, data->source_p->user->server);
return 0;
}

View file

@ -0,0 +1,57 @@
/*
* ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
* spy_links_notice.c: Sends a notice when someone uses LINKS.
*
* Copyright (C) 2002 by the past and present ircd coders, and others.
*
* 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
*
* $Id: spy_links_notice.c,v 1.1 2002/08/13 14:35:17 fishwaldo Exp $
*/
#include "stdinc.h"
#include "modules.h"
#include "hook.h"
#include "client.h"
#include "ircd.h"
#include "send.h"
int
show_links(struct hook_links_data *);
void
_modinit(void)
{
hook_add_hook("doing_links", (hookfn *)show_links);
}
void
_moddeinit(void)
{
hook_del_hook("doing_links", (hookfn *)show_links);
}
const char *_version = "$Revision: 1.1 $";
int
show_links(struct hook_links_data *data)
{
sendto_realops_flags(FLAGS_SPY, L_ALL,
"LINKS '%s' requested by %s (%s@%s) [%s]",
data->mask, data->source_p->name, data->source_p->username,
data->source_p->host, data->source_p->user->server);
return 0;
}

55
contrib/spy_motd_notice.c Normal file
View file

@ -0,0 +1,55 @@
/*
* ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
* spy_motd_notice.c: Sends a notice when someone uses MOTD.
*
* Copyright (C) 2002 by the past and present ircd coders, and others.
*
* 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
*
* $Id: spy_motd_notice.c,v 1.1 2002/08/13 14:35:17 fishwaldo Exp $
*/
#include "stdinc.h"
#include "modules.h"
#include "hook.h"
#include "client.h"
#include "ircd.h"
#include "send.h"
int show_motd(struct hook_spy_data *);
void
_modinit(void)
{
hook_add_hook("doing_motd", (hookfn *)show_motd);
}
void
_moddeinit(void)
{
hook_del_hook("doing_motd", (hookfn *)show_motd);
}
const char *_version = "$Revision: 1.1 $";
int show_motd(struct hook_spy_data *data)
{
sendto_realops_flags(FLAGS_SPY, L_ALL,
"motd requested by %s (%s@%s) [%s]",
data->source_p->name, data->source_p->username,
data->source_p->host, data->source_p->user->server);
return 0;
}

View file

@ -0,0 +1,81 @@
/*
* ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
* spy_stats_notice.c: Sends a notice when someone uses STATS.
*
* Copyright (C) 2002 by the past and present ircd coders, and others.
*
* 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
*
* $Id: spy_stats_notice.c,v 1.1 2002/08/13 14:35:17 fishwaldo Exp $
*/
#include "stdinc.h"
#include "modules.h"
#include "hook.h"
#include "client.h"
#include "ircd.h"
#include "send.h"
int
show_stats(struct hook_stats_data *);
void
_modinit(void)
{
hook_add_hook("doing_stats", (hookfn *)show_stats);
}
void
_moddeinit(void)
{
hook_del_hook("doing_stats", (hookfn *)show_stats);
}
const char *_version = "$Revision: 1.1 $";
/* show a stats request */
int
show_stats(struct hook_stats_data *data)
{
if((data->statchar == 'L') || (data->statchar == 'l'))
{
if(data->name != NULL)
sendto_realops_flags(FLAGS_SPY, L_ALL,
"STATS %c requested by %s (%s@%s) [%s] on %s",
data->statchar,
data->source_p->name,
data->source_p->username,
data->source_p->host,
data->source_p->user->server,
data->name);
else
sendto_realops_flags(FLAGS_SPY, L_ALL,
"STATS %c requested by %s (%s@%s) [%s]",
data->statchar,
data->source_p->name,
data->source_p->username,
data->source_p->host,
data->source_p->user->server);
}
else
{
sendto_realops_flags(FLAGS_SPY, L_ALL,
"STATS %c requested by %s (%s@%s) [%s]",
data->statchar, data->source_p->name, data->source_p->username,
data->source_p->host, data->source_p->user->server);
}
return 0;
}

View file

@ -0,0 +1,56 @@
/*
* ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
* spy_stats_p_notice.c: Sends a notice when someone uses STATS p.
*
* Copyright (C) 2002 by the past and present ircd coders, and others.
*
* 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
*
* $Id: spy_stats_p_notice.c,v 1.1 2002/08/13 14:35:17 fishwaldo Exp $
*/
#include "stdinc.h"
#include "modules.h"
#include "hook.h"
#include "client.h"
#include "ircd.h"
#include "send.h"
int
show_stats_p(struct hook_stats_data *);
void
_modinit(void)
{
hook_add_hook("doing_stats_p", (hookfn *)show_stats_p);
}
void
_moddeinit(void)
{
hook_del_hook("doing_stats_p", (hookfn *)show_stats_p);
}
const char *_version = "$Revision: 1.1 $";
int show_stats_p(struct hook_stats_data *data)
{
sendto_realops_flags(FLAGS_SPY, L_ALL,
"STATS p requested by %s (%s@%s) [%s]",
data->source_p->name, data->source_p->username,
data->source_p->host, data->source_p->user->server);
return 0;
}

View file

@ -0,0 +1,67 @@
/*
* ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
* spy_trace_notice.c: Sends a notice when someone uses TRACE or LTRACE
*
* Copyright (C) 2002 Hybrid 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
*
* $Id: spy_trace_notice.c,v 1.1 2002/08/13 14:35:17 fishwaldo Exp $
*/
#include "stdinc.h"
#include "modules.h"
#include "hook.h"
#include "client.h"
#include "ircd.h"
#include "send.h"
int show_trace(struct hook_spy_data *);
int show_ltrace(struct hook_spy_data *);
void
_modinit(void)
{
hook_add_hook("doing_trace", (hookfn *)show_trace);
hook_add_hook("doing_ltrace", (hookfn *)show_ltrace);
}
void
_moddeinit(void)
{
hook_del_hook("doing_trace", (hookfn *)show_trace);
hook_del_hook("doing_ltrace", (hookfn *)show_ltrace);
}
const char *_version = "$Revision: 1.1 $";
int show_trace(struct hook_spy_data *data)
{
sendto_realops_flags(FLAGS_SPY, L_ALL,
"trace requested by %s (%s@%s) [%s]",
data->source_p->name, data->source_p->username,
data->source_p->host, data->source_p->user->server);
return 0;
}
int show_ltrace(struct hook_spy_data *data)
{
sendto_realops_flags(FLAGS_SPY, L_ALL,
"ltrace requested by %s (%s@%s) [%s]",
data->source_p->name, data->source_p->username,
data->source_p->host, data->source_p->user->server);
return 0;
}

View file

@ -0,0 +1,63 @@
/*
* ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
* spy_whois_notice.c: Sends a notice when someone uses WHOIS.
*
* Copyright (C) 2002 by the past and present ircd coders, and others.
*
* 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
*
* $Id: spy_whois_notice.c,v 1.1 2002/08/13 14:35:17 fishwaldo Exp $
*/
#include "stdinc.h"
#include "modules.h"
#include "hook.h"
#include "client.h"
#include "ircd.h"
#include "send.h"
int
show_notice(struct hook_mfunc_data *);
void
_modinit(void)
{
hook_add_hook("doing_whois", (hookfn *)show_notice);
}
void
_moddeinit(void)
{
hook_del_hook("doing_whois", (hookfn *)show_notice);
}
const char *_version = "$Revision: 1.1 $";
/* show a whois notice
source_p does a /whois on client_p */
int
show_notice(struct hook_mfunc_data *data)
{
if (MyConnect(data->source_p) && MyConnect(data->client_p) &&
IsOper(data->client_p) && (data->client_p != data->source_p)
&& data->client_p->umodes & FLAGS_SPY)
{
sendto_one(data->client_p, ":%s NOTICE %s :*** Notice -- %s (%s@%s) is doing a whois on you",
me.name, data->client_p->name, data->source_p->name, data->source_p->username,
data->source_p->host);
}
return 0;
}

1
doc/.cvsignore Normal file
View file

@ -0,0 +1 @@
Makefile

316
doc/CIDR.txt Normal file
View file

@ -0,0 +1,316 @@
$Id: CIDR.txt,v 1.1 2002/08/13 14:35:17 fishwaldo Exp $
CIDR Information
----------------
Presently, we all use IPv4. The format of IPv4 is the following:
A.B.C.D
Where letters 'A' through 'D' are 8-bit values. In English, this
means each digit can have a value of 0 to 255. Example:
129.56.4.234
Digits are called octets. Oct meaning 8, hence 8-bit values. An
octet cannot be greater than 255, and cannot be less than 0 (eg. a
negative number).
CIDR stands for "classless inter domain routing", details covered
in RFC's 1518 and 1519. It was introduced mainly due to waste within
A and B classes space. The goal was to make it possible to use
smaller nets than it would seem from (above) IP classes, for instance
by dividing one B class into 256 "C like" classes. The other goal was
to allow aggregation of routing information, so that routers could use
one aggregated route (like 194.145.96.0/20) instead of
advertising 16 C classes.
Class A are all these addresses which first bit is "0",
bitmap: 0nnnnnnn.hhhhhhhh.hhhhhhhh.hhhhhhhh (n=net, h=host)
IP range is 0.0.0.0 - 127.255.255.255
Class B are all these addresses which first two bits are "10",
bitmap: 10nnnnnn.nnnnnnnn.hhhhhhhh.hhhhhhhh (n=net, h=host)
IP range is 128.0.0.0 - 191.255.255.255
Class C are all these addresses which first three bits are "110",
bitmap: 110nnnnn.nnnnnnnn.nnnnnnnn.hhhhhhhh (n=net, h=host)
IP range is 192.0.0.0 - 223.255.255.255
Class D are all these addresses which first four bits are "1110",
this is multicast class and net/host bitmap doesn't apply here
IP range is 224.0.0.0 - 239.255.255.255
I bet they will never IRC, unless someone creates multicast IRC :)
Class E are all these addresses which first five bits are "11110",
this class is reserved for future use
IP range is 240.0.0.0 - 247.255.255.255
So, here is how CIDR notation comes into play.
For those of you who have real basic exposure to how networks are
set up, you should be aware of the term "netmask." Basically, this
is a IPv4 value which specifies the "size" of a network. You can
assume the word "size" means "range" if you want.
A chart describing the different classes in CIDR format and their
wildcard equivalents would probably help at this point:
CIDR version dot notation (netmask) Wildcard equivalent
-----------------------------------------------------------------
A.0.0.0/8 A.0.0.0/255.0.0.0 A.*.*.* or A.*
A.B.0.0/16 A.B.0.0/255.255.0.0 A.B.*.* or A.B.*
A.B.C.0/24 A.B.C.0/255.255.255.0 A.B.C.* or A.B.C.*
A.B.C.D/32 A.B.C.D/255.255.255.255 A.B.C.D
The question on any newbies mind at this point is "So what do all
of those values & numbers actually mean?"
Everything relating to computers is based on binary values (1s and
zeros). Binary plays a *tremendous* role in CIDR notation. Let's
break it down to the following table:
A B C D
-------- -------- -------- --------
/8 == 11111111 . 00000000 . 00000000 . 00000000 == 255.0.0.0
/16 == 11111111 . 11111111 . 00000000 . 00000000 == 255.255.0.0
/24 == 11111111 . 11111111 . 11111111 . 00000000 == 255.255.255.0
/32 == 11111111 . 11111111 . 11111111 . 11111111 == 255.255.255.255
The above is basically a binary table for the most common netblock
sizes. The "1"s you see above are the 8-bit values for each octet.
If you split an 8-bit value into each of it's bits, you find the
following:
00000000
^^^^^^^^_ 1sts place (1)
|||||||__ 2nds place (2)
||||||___ 3rds place (4)
|||||____ 4ths place (8)
||||_____ 5ths place (16)
|||______ 6ths place (32)
||_______ 7ths place (64)
|________ 8ths place (128)
Now, since computers consider zero a number, you pretty much have
to subtract one (so-to-speak; this is not really how its done, but
just assume it's -1 :-) ) from all the values possible. Some
examples of decimal values in binary:
15 == 00001111 (from left to right: 8+4+2+1)
16 == 00010000 (from left to right: 16)
53 == 00110101 (from left to right: 32+16+4+1)
79 == 01001111 (from left to right: 64+8+4+1)
254 == 11111110 (from left to right: 128+64+32+16+8+4+2)
So, with 8 bits, the range (as I said before) is zero to 255.
If none of this is making sense to you at this point, you should
back up and re-read all of the above. I realize it's a lot, but
it'll do you some good to re-read it until you understand :-).
So, let's modify the original table a bit by providing CIDR info
for /1 through /8:
A B C D
-------- -------- -------- --------
/1 == 10000000 . 00000000 . 00000000 . 00000000 == 128.0.0.0
/2 == 11000000 . 00000000 . 00000000 . 00000000 == 192.0.0.0
/3 == 11100000 . 00000000 . 00000000 . 00000000 == 224.0.0.0
/4 == 11110000 . 00000000 . 00000000 . 00000000 == 240.0.0.0
/5 == 11111000 . 00000000 . 00000000 . 00000000 == 248.0.0.0
/6 == 11111100 . 00000000 . 00000000 . 00000000 == 252.0.0.0
/7 == 11111110 . 00000000 . 00000000 . 00000000 == 254.0.0.0
/8 == 11111111 . 00000000 . 00000000 . 00000000 == 255.0.0.0
At this point, all of this should making a lot of sense, and you
should be able to see the precision that you can get by using CIDR
at this point. If not, well, I guess the best way to put it would
be that wildcards always assume /8, /16, or /24 (yes hello Piotr,
we can argue this later: I am referring to IPs *ONLY*, not domains
or FQDNs :-) ).
This table will provide a reference to all of the IPv4 CIDR values
cidr|netmask (dot notation)
----+---------------------
/1 | 128.0.0.0
/2 | 192.0.0.0
/3 | 224.0.0.0
/4 | 240.0.0.0
/5 | 248.0.0.0
/6 | 252.0.0.0
/7 | 254.0.0.0
/8 | 255.0.0.0
/9 | 255.128.0.0
/10 | 255.192.0.0
/11 | 255.224.0.0
/12 | 255.240.0.0
/13 | 255.248.0.0
/14 | 255.252.0.0
/15 | 255.254.0.0
/16 | 255.255.0.0
/17 | 255.255.128.0
/18 | 255.255.192.0
/19 | 255.255.224.0
/20 | 255.255.240.0
/21 | 255.255.248.0
/22 | 255.255.252.0
/23 | 255.255.254.0
/24 | 255.255.255.0
/25 | 255.255.255.128
/26 | 255.255.255.192
/27 | 255.255.255.224
/28 | 255.255.255.240
/29 | 255.255.255.248
/30 | 255.255.255.252
/31 | 255.255.255.254
/32 | 255.255.255.255
So, let's take all of the information above, and apply it to a
present-day situation on IRC.
Let's say you have a set of flooding clients who all show up from
the following hosts. For lack-of a better example, I'll use a
subnet here at Best:
nick1 (xyz@shell9.ba.best.com) [206.184.139.140]
nick2 (abc@shell8.ba.best.com) [206.184.139.139]
nick3 (foo@shell12.ba.best.com) [206.184.139.143]
Most people will assume the they were all in the same class C
(206.184.139.0/24 or 206.184.139.*).
This, as a matter of fact, is not true. Now, the reason *I* know
this is solely because I work on the network here; those IPs are
not delegated to a class C, but two portions of a class C (128 IPs
each). That means the class C is actually split into these two
portions:
Netblock IP range
-------- --------
206.184.139.0/25 206.184.139.0 to 206.184.139.127
206.184.139.128/25 206.184.139.128 to 206.184.139.255
For the record, 206.184.139.0 and 206.184.139.128 are both known as
"network addresses" (not to be confused with "netblocks" or "Ethernet
hardware addresses" or "MAC addresses"). Network addresses are
*ALWAYS EVEN*.
206.184.139.127 and 206.184.139.255 are what are known as broadcast
addresses. Broadcast addresses are *ALWAYS ODD*.
Now, the aforementioned list of clients are in the 2nd subnet shown
above, not the first. The reason for this should be obvious.
The remaining question is, "Well that's nice, you know what the netblock
is for Best. What about us? We don't know that!"
Believe it or not, you can find out the network block size by using
whois -h WHOIS.ARIN.NET on the IP in question. ARIN keeps a list of
all network blocks and who owns them -- quite useful, trust me. I
think I use ARIN 5 or 6 times a day, especially when dealing with
D-lines. Example:
$ whois -h whois.arin.net 206.184.139.140
Best Internet Communications, Inc. (NETBLK-NBN-206-184-BEST)
345 East Middlefield Road
Mountain View, CA 94043
Netname: NBN-206-184-BEST
Netblock: 206.184.0.0 - 206.184.255.255
Maintainer: BEST
Does this mean you should D-line 206.184.0.0/16? Probably not.
That's an entire class B-sized block, while you're only trying
to deny access to a subnetted class C.
So then how do you get the *real* info? Well, truth is, you don't.
You have to pretty much take a guess at what it is, if ARIN reports
something that's overly vague. Best, for example, was assigned the
above class B-sized block. We can subnet it however we want without
reporting back to ARIN how we have it subnetted. We own the block,
and that's all that matters (to ARIN).
Not all subnets are like this, however. Smaller subnets you may
find partitioned and listed on ARIN; I've seen /29 blocks for DSL
customers show up in ARIN before.
So, use ARIN any chance you get. The more precision the better!
Now, there is a small issue I want to address regarding use of CIDR
notation. Let's say you D-line the following in CIDR format (hi
sion ;-) ):
205.100.132.18/24
Entries like this really makes my blood boil, solely because it adds
excessive confusion and is just basically pointless. If you
examine the above, you'll see the /24 is specifying an entire
class C -- so then what's the purpose of using .18 versus .0?
There IS no purpose. The netmask itself will mask out the .18 and
continue to successfully use 205.100.132.0/24.
Doing things this way just adds confusion, especially on non-octet-
aligned subnets (such as /8, /16, /24, or /32). Seeing that on a
/27 or a /19 might make people go "wtf?"
I know for a fact this doc lacks a lot of necessary information,
like how the actual netmask/CIDR value play a role in "masking out"
the correct size, and what to do is WHOIS.ARIN.NET returns no
netblock information but instead a few different company names with
NIC handles. I'm sure you can figure this stuff out on your own,
or just ask an administrator friend of yours who DOES know. A lot
of us admins are BOFH types, but if you ask us the right questions,
you'll benefit from the answer quite thoroughly.
Oh, I almost forgot. Most Linux systems use a different version of
"whois" than FreeBSD does. The syntax for whois on Linux is
"whois <INFO>@whois.arin.net", while under FreeBSD it is
"whois -h whois.arin.net <INFO>" Debian uses yet another version
of whois that is incompatible with the above syntax options.
Note that the FreeBSD whois client has shortcuts for the most commonly
used whois servers. "whois -a <INFO>" is the shortcut for ARIN.
Also note that ARIN is not authoritative for all IP blocks on the
Internet. Take for example 212.158.123.66. A whois query to ARIN
will return the following information:
$ whois -h whois.arin.net 212.158.123.66
European Regional Internet Registry/RIPE NCC (NET-RIPE-NCC-)
These addresses have been further assigned to European users.
Contact information can be found in the RIPE database, via the
WHOIS and TELNET servers at whois.ripe.net, and at
http://www.ripe.net/db/whois.html
Netname: RIPE-NCC-212
Netblock: 212.0.0.0 - 212.255.255.255
Maintainer: RIPE
This query tells us that it is a European IP block, and is further
handled by RIPE's whois server. We must then query whois.ripe.net
to get more information.
$ whois -h whois.ripe.net 212.158.123.66
% Rights restricted by copyright. See
http://www.ripe.net/ripencc/pub-services/db/copyright.html
inetnum: 212.158.120.0 - 212.158.123.255
netname: INSNET-P2P
descr: Point to Point Links for for London Nodes
country: GB
--snip--
This tells us the actual IP block that the query was a part of.
Other whois servers that you may see blocks referred to are:
whois.ripn.net for Russia, whois.apnic.net for Asia, Australia, and
the Pacific, and whois.6bone.net for IPv6 blocks.
Contributed by Jeremy Chadwick <jdc@best.net>
Piotr Kucharski <chopin@sgh.waw.pl>
W. Campbell <wcampbel@botbay.net> and
Ariel Biener <ariel@fireball.tau.ac.il>

244
doc/LazyLinks.txt Normal file
View file

@ -0,0 +1,244 @@
Lazy Links
==========
(Ideas by Dianora and orabidoo; initial spec by orabidoo)
Basic idea: leaf servers don't really need to know everything about
every single user and channel out there; connecting a
new leaf server to the network should be fast, easy and
cheap, instead of taking ages to exchange information
about the state of the whole network.
The result is that we move, from a loop-less graph
topology, to a kind of starfish one, where hubs
form a core (interconnected by the traditional IRC
protocol), and leaves are just appendages on hubs.
In the rest of this text, we assume that the local network configuration
looks like this:
LLL <---> HUB <---> OH <---> ....
^
|
v
ALL
where LLL and ALL are Lazy Link Leaves, Hub is a Hub, and OH is anOther
hub.
1) Channels
Hubs, as usual, have full information about all channels, with their
membership, chanop status, TS, etc. This information is authoritative,
which means that they can use it to make decisions such as "should this
user be given ops at this point". This is just the way things are now
already. And, as usual, traditional leaves have all this information
too, and keep having it.
Lazy Leaves, OTOH, depend on their uplinks for much of their
information. They have partial information, meaning that they don't
have the full channel list. However, when they have something about a
channel, they do have *everything* about it, and their information is
authoritative, so they can decide locally on chanop matters.
For this, hubs need to know which channels each of its Lazy Leaves has.
This is necessarily a double-ended map; it can't be just a single flag
on each channel. For efficiency, it could be implemented on the hub by
adding a 32-bit int to the server-link structure, and assigning a
bitmask (one of 1, 2, 4, ... up to 0x80000000) to each of its Lazy Leaf
links. That would support up to 32 Lazy Leaves per hub, and make it
really easy and cheap to keep this information. (The only slight
downside being that, when a Lazy Leaf link breaks, you need to clear a
bit on every single channel.)
1.1) Joining
When a client on a LLL sends a "JOIN #channel", LLL does as usual: if it
has the channel locally, it just joins the user, sends an SJOIN to HUB,
and all is well; if it doesn't have the channel, it creates it, sends a
SJOIN to HUB with the current time as the TS. LLL tells the user that it
has joined the channel, but it doesn't tell it that it has ops yet. So
LLL sends
[LLL -> HUB] :LLL SJOIN LLL_TS #channel :@LLLuser
[LLL -> LLLuser] :LLLuser JOIN #channel
When HUB gets a SJOIN from LLL, it needs to do a lot of the deciding that
normally goes into m_join:
@) if LLL's bit is already set for #channel, then this is not the
first time LLL is dealing with #channel, so just process it as
a normal SJOIN.
otherwise:
a) if myuser cannot join by can_join rules, send a KICK to LLL:
[HUB --> LLL] :HUB KICK #channel LLLuser :sorry, the channel was +i
in this case, LLL's bit doesn't get set for #channel on HUB.
b) if myuser's join is OK and must be given ops (by usual TS
rules, meaning that either LLL_TS < HUB_TS, or the channel
is opless or didn't exist on the hub side), then HUB sends
something back that validates the join:
[HUB -> LLL] :HUB SJOIN OLDER_TS #channel +modes :@LLLuser +other users
c) if myuser's join is OK but must not be given ops, the HUB
sends the same kind of thing back, but without marking ops:
[HUB --> LLL] :HUB SJOIN OLDER_TS #channel +modes :LLLuser @other +users
in this case, as in case b), HUB sets LLL's bit for #channel,
so it knows that that LLL knows about that channel now.
When LLL gets a SJOIN from its hub that includes in the userlist one of
LLL's local users, it interprets that that validates a join. If LLLuser
has ops in that list, then LLL sends:
[LLL --> LLLuser] :HUB MODE #channel +o LLLuser
If not, it just skips that nick from the list. In either case, it
processes the rest of the SJOIN information (modes, other nicks) by the
usual SJOIN rules.
1.2) Bursts
The beauty of this is that, with the rules above, channel bursts get
avoided, without the need to do anything more.
When LLL and HUB connect to each other, LLL sends a channel burst as
usual; HUB doesn't. By the rules above, HUB will reply to each first
LLL's SJOIN for a channel with a SJOIN back with its own info. So at the
end of the burst, LLL has been put up to date with all the channels it
needs to know about.
1.3) Parts, Kicks and Modes
When one of LLL's clients (say, LLLuser) leaves a channel, or is kicked
out of it, LLL needs to check if that was the last of its clients for
that channel.
If that is the case, then LLL needs to inform HUB that it no longer holds
#channel, and destroy its local information about #channel:
[LLL -> HUB] :LLL DROP #channel
Upon receiving a "DROP" command from a Lazy Leaf, the Hub just clears
the Lazy Leaf's bit on that channel.
Alternatively, a Lazy Leaf could decide to cache channels even without
having any clients on them. All it has to do is not send the "DROP"
command to its hub.
For MODE commands coming from the rest of the net and related to
#channel, HUB only needs to pass them to LLL if LLL's bit is set for
#channel.
For MODE changes related to #channel and done by local users on LLL,
LLL just passes them as usual to HUB.
For the special "MODE #channel" query, done on LLL, for a channel that
doesn't exist on LLL, this must be routed through HUB:
[LLL --> HUB] :LLLuser MODE #channel
[HUB --> LLL] :HUB (numeric) #channel modes
2) Nicks
Nicks are simpler, because they are atomic, there is no list associated
with them.
Again, the hub needs to know, for each nick, which of its Lazy Leaves
know of it. This can be done with the same 32-bit bitmask as with
servers. For each user, the associated bit is 1, unless a NICK command
has been sent or received for that user, on the given Lazy Leaf link.
Once again too, the connect burst gets reduced to just the smaller side:
the Lazy Leaf dumps its user base on the hub, but not the other way
round.
When a Lazy Leaf gets a request from one of its local clients, that
relates to a nick LLL doesn't have, this must be routed through HUB.
2.1) WHOIS
For simplicity, we could kill multiple-destination WHOIS, if that's not
already done, and all kinds of WHOIS *pattern*.
When LLLuser does "WHOIS somenick", if the nick is known to LLL, it
replies normally. If it isn't, then LLL routes it to HUB:
[LLL --> HUB] :LLLuser WHOIS Somenick
HUB replies with the usual numeric, and also with a burst-style NICK
introduction, so that from that point on LLL knows about Somenick. HUB
also sets LLL's bit for Somenick.
[HUB --> LLL] :HUB (numerics) WHOIS info
[HUB --> LLL] NICK nickTS Somenick HopCount Umode ......
2.2) NOTIFY and USERHOST
These all take lists of users; for a NOTIFY or USERHOST on LLL from one
of its users, the server checks if *all* of the nicks involved are
known. If at least one isn't, then the request must be passed as such
to HUB. HUB then replies to the client, and also sends a NICK
introduction for each client that LLL didn't previously have.
Note: this kind of sucks, because most NOTIFY lines will tend to include
a nick or two that isn't on IRC at the moment, which means they will be
relayed. With almost every client out there having NOTIFY, this might
well nullify the whole advantage of nick laziness. Or maybe not.
Someone needs to do some math on it, or some testing, or both.
2.3) PRIVMSG and NOTICE
When LLLuser sends "PRIVMSG somenick :message", this must be sent to
HUB, even if somenick isn't known locally. HUB will figure it out,
and possibly send a numeric back.
Same for NOTICE.
2.4) Anything else???
We've missed a bunch here... NAMES, WHO, TRACE, and probably others I
can't think of.
NAMES actually belongs to channels, and might as well not get routed
(just don't reply) if a LLLUser tries a NAMES for a #channel that it
isn't on, and that LLL doesn't have any info on.
for WHO, if there's a pattern, just pass the entire command to HUB and
let it reply to LLLUser through the link (without introducing any extra
NICKs here).
for TRACE, if the nick is locally unknown, just pass the thing to HUB
and let it deal with it.
4) Avoiding Desyncs
There is one particularly treacherous potential desync: a Lazy Leaf is
convinced that it has authoritative information about a channel, but its
hub is convinced that the leaf doesn't. The hub doesn't keep sending
new information, so the leaf's info grows stale, but it keeps acting on
it, which eventually leads to wrong decisions.
It is important that the protocol ensures that such desyncs are
impossible. There should also be periodic cleanup, whereby a Lazy Leaf
scans its own channel-user list, and deletes its own information about
any channel on which it doesn't have any local users (and complains to
its opers about it, because that should never happen).

89
doc/Makefile.in Normal file
View file

@ -0,0 +1,89 @@
# $Id: Makefile.in,v 1.1 2002/08/13 14:35:18 fishwaldo Exp $
CC = @CC@
INSTALL = @INSTALL@
INSTALL_BIN = @INSTALL_PROGRAM@
INSTALL_DATA = @INSTALL_DATA@
INSTALL_SUID = @INSTALL_PROGRAM@ -o root -m 4755
RM = @RM@
LEX = @LEX@
LEXLIB = @LEXLIB@
CFLAGS = @IRC_CFLAGS@ -DIRCD_PREFIX=\"@prefix@\"
LDFLAGS = @LDFLAGS@
MKDEP = ${CC} -MM
MV = @MV@
RM = @RM@
CP = @CP@
prefix = @prefix@
exec_prefix = @exec_prefix@
exec_suffix = @exec_suffix@
bindir = @bindir@
libexecdir = @libexecdir@
sysconfdir = @sysconfdir@
localstatedir = @localstatedir@
# Change this later! -- adrian
moduledir = @prefix@/modules
automoduledir = @prefix@/modules/autoload
# Local to the etc Makefile
mandir = @prefix@/man8
MANPAGES = ircd.8
CONFS = example.conf example.efnet.conf
DEFAULTCONFS = ircd.motd kline.conf dline.conf
SSL_LIBS = @SSL_LIBS@
SSL_INCLUDES = @SSL_INCLUDES@
IRCDLIBS = @LIBS@ $(SSL_LIBS)
INCLUDES = -I../include $(SSL_INCLUDES)
CPPFLAGS = ${INCLUDES} @CPPFLAGS@
install-mkdirs:
-@if test ! -d $(sysconfdir); then \
echo "mkdir $(sysconfdir)"; \
mkdir $(sysconfdir); \
fi
-@if test ! -d $(mandir); then \
echo "mkdir $(mandir)"; \
mkdir $(mandir); \
fi
install: install-mkdirs build
@for i in $(CONFS); do \
if test -f $(sysconfdir)/$$i; then \
echo $(MV) $(sysconfdir)/$$i $(sysconfdir)/$$i.old; \
$(MV) $(sysconfdir)/$$i $(sysconfdir)/$$i.old; \
fi; \
echo $(INSTALL_DATA) $$i $(sysconfdir); \
$(INSTALL_DATA) $$i $(sysconfdir); \
done
@for i in $(DEFAULTCONFS); do \
if test ! -f $(sysconfdir)/$$i; then \
echo $(INSTALL_DATA) $$i $(sysconfdir); \
$(INSTALL_DATA) $$i $(sysconfdir); \
fi; \
done
@for i in $(MANPAGES); do \
if test ! -f $(mandir)/$$i; then \
echo $(INSTALL_DATA) $$i $(mandir); \
$(INSTALL_DATA) $$i $(mandir); \
fi; \
done
$(CP) convertconf-example.conf $(sysconfdir)/.convertconf-example.conf
build:
clean:
depend:
lint:
distclean:
${RM} -f Makefile

272
doc/Tao-of-IRC.940110 Normal file
View file

@ -0,0 +1,272 @@
The Tao of Internet Relay Chat
Copyright (C) Ove Ruben R Olsen 1994
Version of 940110
Contributing masters: Master ScottM
-----
Something is formed by the electrons, born in the silent cable. Shaping
and growing and ungrowing. It is there yet not there. It is the source of
Internet Relay Chat. I do not know the name, thus I will call it the Tao
of Internet Relay Chat.
If the Tao is great, then the IRC is running ceaselessly. If the IRC is
great then the server is running without ever stoping. If the server is
great then the client will always be the server. The luser is then pleased
and there is Chat in the world.
The Tao of IRC squits far away and connects on returning.
-----
The genetic potential of birth, a lot to know, yet unknown.
In the begining there was nothing.
Out of nothing the Tao gave birth to tolsun.oulu.fi. tolsun gave birth to
OuluBox.
OuluBox gave birth to rmsg.
rmsg was not Tao, so MUT gave birth to IRC.
No one knows when IRC came into existance, the mighty master WiZ have it
to be at the end of the eight month in the year of the Dragon.
-----
Each channel has its purpose, however humble. Each channel is the Yin and
Yang of IRC. Each channels has it's place within the IRC.
In the beginning there was only channel 0, thus channel 0 is the soil of
IRC.
Channel 1 to channel 10 then was open as the sea. Channel 11 to 999 was the
trees and forests of IRC. Channels above 999 should not be mentioned, and
channels below 0 were unborn and contained many secrets.
This was not the right Tao, so IRC gave birth to +channels.
+channels had the yin and yang. Mode does not.
This was not the right Tao still, so IRC gave birth to #channels.
#channels have the yin and yang.
Only channel 0 is the right path to Tao, but avoid speaking on channel 0.
-----
There was a great dispute among the Broom-Walkers of the Relay. Some of them
wanted neither yin nor yang. Out of this Eris came into existance. Some of the
Broom-Walkers then created Eris Free-net.
This was the right Tao.
Kind Gentle and Boring Net was another wrong path to the Tao of Internet Relay
Chat.
Some time later there was a quantity of some lusers who wanted to be
Broom-Walkers also. The Eris Free Broom-Walkers did not agree with them,
thus a new IRC was born. This IRC is called the Undernet.
But this is not the right Tao, either.
-----
There will always be disputes among the Broom-Walkers of Internet Relay Chat.
This is the very nature of the IRC.
-----
Lusers that do not understand the Tao is always using the yang of Mode on
their channels. Lusers that do understand the Tao are always using Ignore
on their channels.
How could this not be so ?
-----
The wise sage luser is told about the Chat and uses it. The luser is told
about the IRC and is looking for it. The flock are told about the Tao and
make a fool of the IRC.
If there was no laughter, there would be no Tao.
-----
The master says:
"Without the Tao of Internet Relay Chat, life becomes meaningless."
The Relay of the old time was mysterious and sacred. We can neither imagine
its thoughts nor path; we are left but to describe.
-----
The sage luser must be aware like a frog crossing the highway.
-----
The great master Wumpus once dreamed that he was an automaton. When he awoke
he exclaimed:
"I don't know whether I am Wumpus dreaming that I am a client,
or a client dreaming that I am Wumpus!"
So was the first Automata born.
The master Nap then said:
"Any automata should not speak unless spoken to.
Any automata shall only whisper when spoken to."
Thus replied the master Gnarfer:
"The lusers shall keep in mind that a automata can be either good or
bad. Create good automata, and the IRC will hail you and you will
gain fame and fortune. Create bad automata and people will start to
hate you, and finaly you will be /KILLed to ethernal damnation"
Many lusers have fallen into the clutches of ethernal damnation. They where
not following the Tao.
-----
There once was a luser who went to #BotSex. Each day he saw the automatons.
The luser decided that he also would have such a automata.
He asked another luser for his automata. The other luser gave his automata
away.
The luser was not within the Tao, so he just started the automata. The automata
had only Yang inside so all the lusers files where deleted.
Some moons laither the same luser then had become a sage luser, and did create
his automata from the very grounds with materials found inside the IRC.
The luser was now within the Tao and his automata lived happily ever after.
-----
There once was a master who wrote automatons without the help of master Phone.
A novice luser, seeking to imitate him, began with the help of master Phone.
When the novice luser asked the master to evaluate his automata the master
replied: "What is a working automata for the master is not for the luser.
You must must BE the IRC before automating."
-----
Master BigCheese gave birth to master Troy; his duty clear. Master Troy gave
birth to master Phone, for the Tao of Irc must be eternal and must flow as the
ceaseless river of Time itself.
-----
Master Phone once said about the ircII client:
"public_msg is for a message from someone NOT on the channel
public_other is for a message on a channel that doesn't belong to
a window. public is for a message on a channel that belongs to a
window!"
Out of this raised the mighty chaos.
-----
The sage luser came to the master who wrote automata without the help of
master Phone. The sage luser asked the master who wrote automata: "Which is
easiest to make. A automata with the help of master Phone or an automata
made with the help of a language ?"
The master who wrote automata then replied:
"With the help of a language."
The sage luser was disapointed and exclaimed: "But, with master Phone you
do not need to know anything about the soil of IRC. Is not that the easiet
way ?"
"Not really" said the master who wrote automata, "when using master Phone
you are closed inside a box. For sure, it is a great box for the lusers,
but the master will need more power, thus a language is the only path to go.
With the language the master will never have to limit himself. When using
such a language the master will seek the best between the need and the
availibility."
"I see", said the sage luser.
This is the essence of Tao of IRC automatas.
-----
A client should be light and be used for communication. The spirit of a good
client is that it should be very convinient for the luser to use, but hard
for the luser who want to create automata.
There should never ever be too many functions or too few functions.
There should always be a ignore.
Without ignore the client is not within the Tao of Chating.
The client should always respond the luser with messages that will not
astnonish him too much. The server likewise. If the server does not, then it
is the clients job to explain what the server says.
A client which fails this, will be useless and cause confusion for the lusers.
The only way to correct this is to use another client or to write a new one.
-----
A luser asked the masters on #IrcHelp: "My client does not work".
The masters replied: "Upgrade your client".
The luser then wondered why the master knew. The master then told him about
the Protocol.
"Your client does not work beaucse it does not understand the server. Why
should it always work ? Only a fool would expect such. But, clients are made
by humans, and humans are not perfect. Only Tao is.
The IRC is solid. The IRC is floating, and will always be dynamic. Live with
that or /quit."
-----
The luser came to the masters of #IrcHelp, asking about the Tao of IRC within
the client.
The masters then said that the Tao of IRC always lies inside the client
regardless of how the client connects to the server.
"Is the Tao in irc ?" asked the luser.
"It so is" replied the masters of #IrcHelp.
"Is the Tao in the ircII, Kiwi, rxirc, vms, rockers and msa ?" asked the
luser.
"In all of them and in the TPC, irchat, zenirc, zircon X11-irc and even the
dos irc has the Tao" said the master quietly.
"Is the Tao in a telnet connection directly to the server ?"
The master then was quiet for a long time and said. "Please leave, such
questions are not within the Tao of IRC".
-----
The master says: "Without the Protocol of TCP the messages will not travel.
Without the client, the server is useless."
-----
There once was a luser who used the ircII client. "ircII can do anything I
ever need for using IRC" said the emacs client user, "I have /ON's, I have
assignments, I have aliasing. Why don't you use this instead of the huge
emacs client, which also has a messy screen?"
The emacs client user then replied by saying that "it is better to have a
scripting language that is the client instead of have a client that has
a scripting language." Upon hearing this, the ircII client luser fell silent.
-----
The master Wumpus said: "Time for you to leave. I did, now I'm happy."
The master Gnarfer replied: "Use, but never overuse IRC, then you will also
be happy within IRC"
-----
A luser came unto the masters of #EU-Opers and asked, "How can I be, yet not
be, a user@host within the IRC?"
The masters of #EU-Opers replied: "To be Tao is to be ones true self. To hide
ones self is not Tao, and is not IRC, you have much to learn before you shall
be at rest within the Flow of Irc. Please leave"

191
doc/challenge.txt Normal file
View file

@ -0,0 +1,191 @@
Oper Challenge and Response System
$Id: challenge.txt,v 1.1 2002/08/13 14:35:18 fishwaldo Exp $
Copyright (c) 2001 by ircd-hybrid team
----------------------------------------------------------------------
In an effort to reduce the damage caused to a network by a hacked O-line,
Hybrid supports an OpenSSL based challenge-response system. This new
system allows the admin to remove all oper block passwords from the conf
file. Authentication is done through a public/private key.
----------------------------------------------------------------------
Requirements
The ircd must be compiled with the --enable-openssl option to configure .
If configure detects a working openssl library, --enable-openssl is
implicitly enabled.
oper {} blocks should not have normal passwords, but should contain the
the name of the private key file. However it is possible for the user to
use both challenge and normal passwords, but this would defeat the purpose
of the challenge system.
m_challenge.so must be loaded.
The oper has their private key file and an implementation of the RSA
Respond tool available to be run.
----------------------------------------------------------------------
Process
Each oper should have a private key file and a public key file. The keys
can be generated with the mkkeypair utility provided in tools/. The keys
are compatible with cryptlink keys.
The oper keeps their private key file in a safe place, and gives their
public key file to their admin(s).
The admin will place an entry for the public key file into a field called
rsa_public_key_file of each oper's oper {} block in the conf file.
The oper wishes to obtain their operator status, and issues the CHALLENGE
command.
The server will print out a long hexadecimal string, that needs to be fed
to the respond utility provided in tools/rsa_respond.
The respond program will generate an answer that is fed back to the
CHALLENGE command.
----------------------------------------------------------------------
Generating the Key Files
The keys can be generated with the openssl command as follows:
openssl genrsa -des3 -out rsa.key 1024
openssl rsa -in rsa.key -pubout -out rsa.pub
It is highly recommended that you set a password on your private key.
A key pair can also be generated with the tools/mkkeypair utility. No
password will be set, however.
----------------------------------------------------------------------
Using CHALLENGE and respond
Note: All examples assume the use of the stock respond client included
with the Hybrid 7 source, run on a UNIX(c) platform.
The administrator of the server you oper on should remove the password in
your oper {} block and replace it with an entry for your public key, so
that /oper will be disabled.
Note: The public key is a VERY long string.
The oper will issue /challenge oper_nick, and see something like below:
*** 56F1FDAE4C590C524CF758917E62C2A2A1376CB9C4C2E7D411BB0AD9C4A
605A2D05A94E7254197E9D71438B5FB565B6FD35465E462305F35F4A2D45311
F983B3E062F635912FA155B4B1E18EAA782CC107F4C9DA83092658D16A2E88A
6BCF9820F5A044A29CDD4C062F05BF509CA3B561375CBC4179BD1CF6026BDE9
60E52C6B
Note: The challenge is all on one line.
Note: With some clients, the oper will have to issue /quote CHALLENGE
instead of /challenge.
The oper will then have to feed that challenge to the respond program.
+------------------------------------------------------------------+
| The respond utility's syntax is: |
| |
|$ ./respond private_key_file challenge_from_server |
| |
| |
| Example: |
| |
|wcampbel@botbay (rsa_respond): ./respond hwy.key \ |
|56F1FDAE4C590C524CF758917E62C2A2A1376CB9C4C2E7D411BB0AD9C4A605A2D0|
|5A94E7254197E9D71438B5FB565B6FD35465E462305F35F4A2D45311F983B3E062|
|F635912FA155B4B1E18EAA782CC107F4C9DA83092658D16A2E88A6BCF9820F5A04|
|4A29CDD4C062F05BF509CA3B561375CBC4179BD1CF6026BDE960E52C6B |
|Keyphrase: |
|6B882932DD00F86123869E401F7334B9B0D0018A60F1DE244E90E47246AA87C7 |
| |
| Note: The challenge parameter must be on one line. |
+------------------------------------------------------------------+
The keyphrase must be entered properly to get the response. The bottom
line is the response that must be sent back to the server.
The oper will issue the following command in order to obtain operator
status:
/challenge
+6B882932DD00F86123869E401F7334B9B0D0018A60F1DE244E90E47246AA87C7
Note: The '+' is needed
If successful, the oper will obtain operator status on the server.
+------------------------------------------------------------------------+
| Warning |
|------------------------------------------------------------------------|
| If the CHALLENGE fails, and you use ircII, EPIC, or BX, you may get |
| disconnected with the client asking for the server password. This is a |
| client bug, not an ircd bug. |
+------------------------------------------------------------------------+
----------------------------------------------------------------------
RSA Respond Tool
The RSA Respond tool is a vital part of challenge/response system. In
order to function, the operator must have must have a way to quickly issue
the respond command, and to copy and paste data to and from the IRC
client.
The respond source code is included with the Hybrid 7 source, in the
tools/rsa_respond directory. A distributable tar file can easily be
created by issuing make rsa_respond in the root of the source tree. The
file rsa_respond.tar.gz will be created in the root of the source tree.
rsa_respond.tar.gz should compile with little or no modifications[1] on
most UNIX(c) and UNIX-like platforms[2]. The README in the tar archive
gives more information.
A copy of the source tar file is available on
http://ircd.botbay.net/pub/hybrid/rsa/rsa_respond.tar.gz.
For Windows platforms, there are two available RSA Respond tools. One is a
text only port of the stock tool. The binary is available from
http://ircd.botbay.net/pub/hybrid/rsa/rsa_respond-bin.tar.gz. The other
tool is a GUI enabled version[3]. The source tree[4] is available from
http://ircd.botbay.net/pub/hybrid/rsa/winrespond-src.tar.gz. A binary
distribution is available from
http://ircd.botbay.net/pub/hybrid/rsa/winrespond-bin.tar.gz.
With the appropriate version of the RSA Respond tool, any operator can
protect their privileged access to the server, with little additional
effort over using standard operator passwords.
----------------------------------------------------------------------
Benefits
The greatest benefit of using the challenge/response system is that there
are no passwords sent over the network in plaintext. There are also no
credentials left on the server side, as only public keys are kept in the
conf. The use of public/private key encryption provides far greater
security over having a single password, and may (if the key is kept
secure, and has a good passphrase) virtually eliminate hacked O-lines.
Notes
[1] Some platforms may require Makefile changes in order to link in the
OpenSSL library. This may change in the future.
[2] Platforms known to function include: Linux, FreeBSD, Solaris, and
Cygwin.
[3] A screenshot of the program is available on
http://kabel.pp.ru/sgml/winrespond.png .
[4] The winrespond source depends on a working, up to date, Cygwin
installation.

View file

@ -0,0 +1,473 @@
/* doc/convertconf-example.conf - ircd-hybrid-7 Example configuration file
* Copyright (C) 2000-2002 Hybrid Development Team
*
* Written by ejb, wcampbel, db, leeh and others
*
* $Id: convertconf-example.conf,v 1.1 2002/08/13 14:35:19 fishwaldo Exp $
*/
/* logging {}: contains information about logfiles. */
logging {
/* log level: the amount of detail to log in ircd.log. The
* higher, the more information is logged. May be changed
* once the server is running via /quote SET LOG. Either:
* L_CRIT, L_ERROR, L_WARN, L_NOTICE, L_TRACE, L_INFO or L_DEBUG
*/
log_level = L_INFO;
};
/* shared {}: users that are allowed to remote kline (OLD U:) */
shared {
/* name: the server the user must be on to set klines. If this is not
* specified, the user will be allowed to kline from all servers.
*/
name = "irc2.some.server";
/* user: the user@host mask that is allowed to set klines. If this is
* not specified, all users on the server above will be allowed to set
* a remote kline.
*/
user = "oper@my.host.is.spoofed";
};
/* kill {}: users that are not allowed to connect (OLD K:)
* Oper issued klines will be added to the specified kline config
*/
kill {
user = "bad@*.hacked.edu";
reason = "Obviously hacked account";
};
/* deny {}: IPs that are not allowed to connect (before DNS/ident lookup)
* Oper issued dlines will be added to the specified dline config
*/
deny {
ip = "10.0.1.0/24";
reason = "Reconnecting vhosted bots";
};
/* exempt {}: IPs that are exempt from deny {} and Dlines. (OLD d:) */
exempt {
ip = "192.168.0.0/16";
};
/* resv {}: nicks and channels users may not use/join (OLD Q:) */
resv {
/* reason: the reason for the proceeding resv's */
reason = "There are no services on this network";
/* resv: the nicks and channels users may not join/use */
nick = "nickserv";
nick = "chanserv";
channel = "#services";
/* resv: wildcard masks are also supported in nicks only */
reason = "Clone bots";
nick = "clone*";
};
/* gecos {}: The X: replacement, used for banning users based on their
* "realname". The action may be either:
* warn: allow client to connect, but send message to opers
* reject: drop clients but also send message to opers.
* silent: silently drop clients who match.
*/
gecos {
name = "*sex*";
reason = "Possible spambot";
action = warn;
};
gecos {
name = "sub7server";
reason = "Trojan drone";
action = reject;
};
gecos {
name = "*http*";
reason = "Spambot";
action = silent;
};
/* The channel block contains options pertaining to channels */
channel {
/* invex: Enable/disable channel mode +I, a n!u@h list of masks
* that can join a +i channel without an invite.
*/
use_invex = yes;
/* except: Enable/disable channel mode +e, a n!u@h list of masks
* that can join a channel through a ban (+b).
*/
use_except = yes;
/* halfops: Enable/disable channel mode "+h <nick>", this allows
* users to perform all channel functions except +/-o and kick
* opped users.
*/
use_halfops = yes;
/* anonops: Enable/disable channel mode +a. This hides the people
* who are opped in the channel from people who are unopped.
*
* The ircd will 'sync' the users oplists when they become opped
* or deopped by sending mode changes. This can cause a flood and
* could potentially be abused.
*/
use_anonops = no;
/* vchans: permit virtual channels, multiple copies of the same
* channel name. read doc/vchans.txt for more details
*
* We advise against using this on production networks
*/
use_vchans = yes;
/* vchans oper only: only allow opers to create vchans via /cjoin */
vchans_oper_only = yes;
/* knock: Allows users to request an invite to a channel that
* is locked somehow (+ikl). If the channel is +p or you are banned
* the knock will not be sent.
*/
use_knock = yes;
/* knock delay: The amount of time a user must wait between issuing
* the knock command.
*/
knock_delay = 5 minutes;
/* knock channel delay: How often a knock to any specific channel
* is permitted, regardless of the user sending the knock.
*/
knock_delay_channel = 1 minute;
/* max chans: The maximum number of channels a user can join/be on. */
max_chans_per_user = 15;
/* quiet on ban: stop banned people talking in channels. */
quiet_on_ban = yes;
/* max bans: maximum number of +b/e/I modes in a channel */
max_bans = 25;
/* persist time: the minimum amount of time a channel will remain with
* all its modes intact once the last user has left the channel.
*
* set to 0 to disable.
*/
persist_time = 30 minutes;
/* splitcode: the ircd will check every 60s as to whether splitmode
* should be disabled or not, so there may be a delay between a
* netsplit ending and splitmode ending.
*
* both split users and split servers must be true to enter splitmode
*
* you may force splitmode to be permanent by /quote set splitmode on
*/
/* split users: when the usercount is lower than this level, consider
* ourselves split. this must be set for automatic splitmode
*/
default_split_user_count = 0;
/* split servers: when the servercount is lower than this, consider
* ourselves split. this must be set for automatic splitmode
*/
default_split_server_count = 0;
/* split no create: disallow users creating channels on split, works in
* tandem with persistant channels, that have retained their modes.
*/
no_create_on_split = no;
/* split: no join: disallow users joining channels at all on a split */
no_join_on_split = no;
};
/* The serverhide block contains the options regarding serverhiding */
serverhide {
/* flatten links: this option will show all servers in /links appear
* that they are linked to this current server
*/
flatten_links = no;
/* links delay: how often to update the links file when it is
* flattened.
*/
links_delay = 5 minutes;
/* hidden: hide this server from a /links output on servers that
* support it. this allows hub servers to be hidden etc.
*/
hidden = no;
/* disable hidden: prevent servers hiding themselves from a
* /links ouput.
*/
disable_hidden = no;
/* hide servers: hide remote servernames everywhere and instead use
* network_name and network_desc.
*/
hide_servers = no;
/* disable remote: disable users doing commands on remote servers */
disable_remote_commands = no;
/* disable local channels: prevent users from joining &channels.
* This is extreme, but its still a flaw in serverhide. It will
* however remove far more from users than it will give back in
* security.
*/
disable_local_channels = no;
};
/* The general block contains many of the options that were once compiled
* in options in config.h. The general block is read at start time.
*/
general {
/* floodcount: the default value of floodcount that is configurable
* via /quote set floodcount. This is the amount of lines a user
* may send to any other user/channel in one second.
*/
default_floodcount = 10;
/* failed oper notice: send a notice to all opers on the server when
* someone tries to OPER and uses the wrong password, host or ident.
*/
failed_oper_notice = yes;
/* dots in ident: the amount of '.' characters permitted in an ident
* reply before the user is rejected.
*/
dots_in_ident=2;
/* dot in ipv6: ircd-hybrid-6.0 and earlier will disallow hosts
* without a '.' in them. this will add one to the end. only needed
* for older servers.
*/
dot_in_ip6_addr = yes;
/* min nonwildcard: the minimum non wildcard characters in k/d/g lines
* placed via the server. klines hand placed are exempt from limits.
* wildcard chars: '.' '*' '?' '@'
*/
min_nonwildcard = 4;
/* max accept: maximum allowed /accept's for +g usermode */
max_accept = 20;
/* nick flood: enable the nickflood control code */
anti_nick_flood = yes;
/* nick flood: the nick changes allowed in the specified period */
max_nick_time = 20 seconds;
max_nick_changes = 5;
/* anti spam time: the minimum time a user must be connected before
* custom quit messages are allowed.
*/
anti_spam_exit_message_time = 5 minutes;
/* ts delta: the time delta allowed between server clocks before
* a warning is given, or before the link is dropped. all servers
* should run ntpdate/rdate to keep clocks in sync
*/
ts_warn_delta = 30 seconds;
ts_max_delta = 5 minutes;
/* client exit: prepend a users quit message with "Client exit: " */
client_exit = yes;
/* kline reason: show the user the reason why they are k/d/glined
* on exit. may give away who set k/dline when set via tcm.
*/
kline_with_reason = yes;
/* kline connection closed: make the users quit message on channels
* to be "Connection closed", instead of the kline reason.
*/
kline_with_connection_closed = no;
/* non redundant klines: flag and ignore redundant klines */
non_redundant_klines = yes;
/* warn no nline: warn opers about servers that try to connect but
* we dont have a connect {} block for. Twits with misconfigured
* servers can get really annoying with this enabled.
*/
warn_no_nline = yes;
/* stats o oper only: make stats o (opers) oper only */
stats_o_oper_only=yes;
/* stats P oper only: make stats P (ports) oper only */
stats_P_oper_only=no;
/* stats i oper only: make stats i (auth {}) oper only. set to:
* yes: show users no auth blocks, made oper only.
* masked: show users first matching auth block
* no: show users all auth blocks.
*/
stats_i_oper_only=masked;
/* stats k/K oper only: make stats k/K (klines) oper only. set to:
* yes: show users no auth blocks, made oper only
* masked: show users first matching auth block
* no: show users all auth blocks.
*/
stats_k_oper_only=masked;
/* caller id wait: time between notifying a +g user that somebody
* is messaging them.
*/
caller_id_wait = 1 minute;
/* pace wait simple: time between use of less intensive commands
* (HELP, remote WHOIS, WHOWAS)
*/
pace_wait_simple = 1 second;
/* pace wait: time between more intensive commands
* (ADMIN, INFO, LIST, LUSERS, MOTD, STATS, VERSION)
*/
pace_wait = 10 seconds;
/* short motd: send clients a notice telling them to read the motd
* instead of forcing a motd to clients who may simply ignore it.
*/
short_motd = no;
/* ping cookies: require clients to respond exactly to a ping command,
* can help block certain types of drones and FTP PASV mode spoofing.
*/
ping_cookie = no;
/* no oper flood: increase flood limits for opers. */
no_oper_flood = yes;
/* glines: enable glines, network wide temp klines */
glines = yes;
/* gline time: the amount of time a gline will remain before exiring */
gline_time = 1 day;
/* idletime: the maximum amount of time a user may idle before
* they are disconnected
*/
idletime = 0;
/* maximum links: the maximum amount of servers to connect to for
* connect blocks without a valid class.
*/
maximum_links = 1;
/* REMOVE ME. The following line checks youve been reading. */
havent_read_conf = 1;
/* logfiles: the logfiles to use for user connects, /oper uses,
* and failed /oper. These files must exist for logging to be used.
*/
fname_userlog = "logs/userlog";
fname_operlog = "logs/operlog";
fname_foperlog = "logs/foperlog";
/* max targets: the maximum amount of targets in a single
* PRIVMSG/NOTICE. set to 0 for unlimited targets.
*/
max_targets = 4;
/* client flood: maximum number of lines in a clients queue before
* they are dropped for flooding.
*/
client_flood = 20;
/* message locale: the default message locale if gettext() is enabled
* and working.
* Use "custom" for the (in)famous Hybrid custom messages.
* Use "standard" for the compiled in defaults.
*/
message_locale = "custom";
/* usermodes configurable: a list of usermodes for the options below
*
* +b - bots - See bot and drone flooding notices
* +c - cconn - Client connection/quit notices
* +d - debug - See debugging notices
* +f - full - See I: line full notices
* +g - callerid - Server Side Ignore
* +i - invisible - Not shown in NAMES or WHO unless you share a
* a channel
* +k - skill - See server generated KILL messages
* +l - locops - See LOCOPS messages
* +n - nchange - See client nick changes
* +r - rej - See rejected client notices
* +s - servnotice - See general server notices
* +u - unauth - See unauthorized client notices
* +w - wallop - See server generated WALLOPS
* +x - external - See remote server connection and split notices
* +y - spy - See LINKS, STATS, TRACE notices etc.
* +z - operwall - See oper generated WALLOPS
*/
/* oper only umodes: usermodes only opers may set */
oper_only_umodes = bots, cconn, debug, full, skill, nchange,
rej, spy, external, operwall, locops, unauth;
/* oper umodes: default usermodes opers get when they /oper */
oper_umodes = locops, servnotice, operwall, wallop;
/* servlink path: path to 'servlink' program used by ircd to handle
* encrypted/compressed server <-> server links.
*
* only define if servlink is not in same directory as ircd itself.
*/
#servlink_path = "/usr/local/ircd/bin/servlink";
/* default cipher: default cipher to use for cryptlink when none is
* specified in connect block.
*/
#default_cipher_preference = "BF/256";
/* use egd: if your system does not have *random devices yet you
* want to use OpenSSL and encrypted links, enable this. Beware -
* EGD is *very* CPU intensive when gathering data for its pool
*/
#use_egd = yes;
/* egdpool path: path to EGD pool. Not necessary for OpenSSL >= 0.9.7
* which automatically finds the path.
*/
#egdpool_path = "/var/run/egd-pool";
/* compression level: level of compression for compressed links between
* servers.
*
* values are between: 1 (least compression, fastest)
* and: 9 (most compression, slowest).
*/
#compression_level = 6;
/* throttle time: the minimum amount of time between connections from
* the same ip. exempt {} blocks are excluded from this throttling.
* Offers protection against flooders who reconnect quickly.
* Set to 0 to disable.
*/
throttle_time = 10;
};
modules {
/* module path: paths to search for modules specified below and
* in /modload.
*/
path = "/usr/local/ircd/modules";
path = "/usr/local/ircd/modules/autoload";
/* module: the name of a module to load on startup/rehash */
#module = "some_module.so";
};

0
doc/dline.conf Normal file
View file

870
doc/example.conf Executable file
View file

@ -0,0 +1,870 @@
/* doc/example.conf - ircd-hybrid-7 Example configuration file
* Copyright (C) 2000-2002 Hybrid Development Team
*
* Written by ejb, wcampbel, db, leeh and others
*
* $Id: example.conf,v 1.1 2002/08/13 14:35:20 fishwaldo Exp $
*/
/* IMPORTANT NOTES:
*
* class {} blocks MUST be specified before anything that uses them. That
* means they must be defined before auth {} and before connect {}.
*
* auth {} blocks MUST be specified in order of precedence. The first one
* that matches a user will be used. So place spoofs first, then specials,
* then general access, then restricted.
*
* Both shell style (#) and C style comments are supported.
*
* Files may be included by either:
* .include "filename"
* .include <filename>
*
* Times/durations are written as:
* 12 hours 30 minutes 1 second
*
* Valid units of time:
* month, week, day, hour, minute, second
*
* Valid units of size:
* megabyte/mbyte/mb, kilobyte/kbyte/kb, byte
*
* Sizes and times may be singular or plural.
*/
/* EFNET NOTE:
*
* This config file is NOT suitable for EFNet. EFNet admins should use
* example.efnet.conf
*/
/* serverinfo {}: Contains information about the server. (OLD M:) */
serverinfo {
/* name: the name of our server */
name = "hades.arpa";
/* description: the description of our server. '[' and ']' may not
* be used here for compatibility with older servers.
*/
description = "hybrid-7 test server";
/* network info: the name and description of the network this server
* is on. Shown in the 005 reply and used with serverhiding.
*/
network_name = "MyNet";
network_desc = "This is My Network";
/* hub: allow this server to act as a hub and have multiple servers
* connected to it. This may not be changed if there are active
* LazyLink servers.
*/
hub = no;
/* vhost: the IP to bind to when we connect outward to ipv4 servers.
* This should be an ipv4 IP only.
*/
#vhost = "192.169.0.1";
/* vhost6: the IP to bind to when we connect outward to ipv6 servers.
* This should be an ipv6 IP only.
*/
#vhost6 = "3ffe:80e8:546::2";
/* max clients: the maximum number of clients allowed to connect */
max_clients = 512;
/* rsa key: the path to the file containing our rsa key for cryptlink.
*
* Example command to store a 2048 bit RSA keypair in
* rsa.key, and the public key in rsa.pub:
*
* openssl genrsa -out rsa.key 2048
* openssl rsa -in rsa.key -pubout -out rsa.pub
* chown <ircd-user>.<ircd.group> rsa.key rsa.pub
* chmod 0600 rsa.key
* chmod 0644 rsa.pub
*/
#rsa_private_key_file = "/usr/local/ircd/etc/rsa.key";
};
/* admin {}: contains admin information about the server. (OLD A:) */
admin {
name = "Smurf target";
description = "Main Server Administrator";
email = "<syn@packets.r.us>";
};
/* logging {}: contains information about logfiles. */
logging {
/* log level: the amount of detail to log in ircd.log. The
* higher, the more information is logged. May be changed
* once the server is running via /quote SET LOG. Either:
* L_CRIT, L_ERROR, L_WARN, L_NOTICE, L_TRACE, L_INFO or L_DEBUG
*/
log_level = L_INFO;
};
/* class {}: contain information about classes for users (OLD Y:) */
class {
/* name: the name of the class. classes are text now */
name = "users";
/* ping time: how often a client must reply to a PING from the
* server before they are dropped.
*/
ping_time = 2 minutes;
/* number per ip: the number of users per host allowed to connect */
number_per_ip = 2;
/* max number: the maximum number of users allowed in this class */
max_number = 100;
/* sendq: the amount of data allowed in a clients queue before
* they are dropped.
*/
sendq = 100 kbytes;
};
class {
name = "restricted";
ping_time = 1 minute 30 seconds;
number_per_ip = 1;
max_number = 100;
sendq = 60kb;
};
class {
name = "opers";
ping_time = 5 minutes;
number_per_ip = 10;
max_number = 100;
sendq = 100kbytes;
};
class {
name = "server";
ping_time = 5 minutes;
/* connectfreq: only used in server classes. specifies the delay
* between autoconnecting to servers.
*/
connectfreq = 5 minutes;
/* max number: the amount of servers to autoconnect to */
max_number = 1;
/* sendq: servers need a higher sendq as they send more data */
sendq=2 megabytes;
};
/* listen {}: contain information about the ports ircd listens on (OLD P:) */
listen {
/* port: the specific port to listen on. if no host is specified
* before, it will listen on all available IPs.
*
* ports are seperated via a comma, a range may be specified using ".."
*/
/* port: listen on all available IPs, ports 6665 to 6669 */
port = 6665 .. 6669;
/* host: set a specific IP/host the ports after the line will listen
* on. This may be ipv4 or ipv6.
*/
host = "1.2.3.4";
port = 7000, 7001;
host = "3ffe:1234:a:b:c::d";
port = 7002;
};
/* auth {}: allow users to connect to the ircd (OLD I:) */
auth {
/* user: the user@host allowed to connect. multiple IPv4/IPv6 user
* lines are permitted per auth block.
*/
user = "*@172.16.0.0/12";
user = "*test@123D:B567:*";
/* password: an optional password that is required to use this block */
password = "letmein";
/* spoof: fake the users host to be be this. This is free-form,
* just do everyone a favour and dont abuse it. (OLD I: = flag)
*/
spoof = "I.still.hate.packets";
/* spoof notice: enable spoofing notification to admins (default yes) */
spoof_notice = yes;
/* exceed limit: allow a user to exceed class limits (OLD I: > flag) */
exceed_limit = yes;
/* kline exempt: exempt this user from k/glines (OLD I: ^ flag) */
kline_exempt = yes;
/* gline exempt: exempt this user from glines (OLD I: _ flag) */
gline_exempt = yes;
/* no tilde: remove ~ from a user with no ident (OLD I: - flag) */
no_tilde = yes;
/* class: the class the user is placed in */
class = "opers";
};
auth {
/* redirect: the server and port to redirect a user to. A user does
* not have to obey the redirection, the ircd just suggests to them
* an alternative server.
*/
redirserv = "irc.fi";
redirport = 6667;
user = "*.fi";
/* class: a class is required even though it is not used */
class = "users";
};
auth {
user = "*@*";
class = "users";
/* restricted: stop the client sending mode changes */
#restricted = yes;
/* have ident: require the user has identd to connect (OLD I: + flag) */
have_ident = yes;
};
/* operator {}: defines ircd operators. (OLD O:)
* ircd-hybrid no longer supports local operators, privileges are
* controlled via flags.
*/
operator {
/* name: the name of the oper */
name = "god";
/* user: the user@host required for this operator. CIDR is not
* supported. multiple user="" lines are supported.
*/
user = "*god@*";
user = "*@127.0.0.1";
/* password: the password required to oper. By default this will
* need to be encrypted using 'mkpasswd'. MD5 is supported.
*/
password = "etcnjl8juSU1E";
/* rsa key: the public key for this oper when using Challenge.
* A password should not be defined when this is used, see
* doc/challenge.txt for more information.
*/
#rsa_public_key_file = "/usr/local/ircd/etc/oper.pub";
/* class: the class the oper joins when they successfully /oper */
class = "opers";
/* privileges: controls the activities and commands an oper are
* allowed to do on the server. All options default to no.
* Available options:
*
* global_kill: allows remote users to be /KILL'd (OLD 'O' flag)
* remote: allows remote SQUIT and CONNECT (OLD 'R' flag)
* kline: allows KILL, KLINE and DLINE (OLD 'K' flag)
* unkline: allows UNKLINE and UNDLINE (OLD 'U' flag)
* gline: allows GLINE (OLD 'G' flag)
* nick_changes: allows oper to see nickchanges (OLD 'N' flag)
* via usermode +n
* rehash: allows oper to REHASH config (OLD 'H' flag)
* die: allows DIE and RESTART (OLD 'D' flag)
* admin: gives admin privileges. admins
* may (un)load modules and see the
* real IPs of servers.
*/
global_kill = yes;
remote = yes;
kline = yes;
unkline = yes;
gline = yes;
die = yes;
rehash = yes;
nick_changes = yes;
admin = yes;
};
/* connect {}: controls servers we connect to (OLD C:, N:, H:, L:) */
connect {
/* name: the name of the server */
name = "irc.uplink.com";
/* host: the host or IP to connect to. If a hostname is used it
* must match the reverse dns of the server.
*/
host = "192.168.0.1";
/* passwords: the passwords we send (OLD C:) and accept (OLD N:).
* The remote server will have these passwords reversed.
*/
send_password = "password";
accept_password = "anotherpassword";
/* encrypted: controls whether the accept_password above has been
* encrypted. (OLD CRYPT_LINK_PASSWORD now optional per connect)
*/
encrypted = no;
/* port: the port to connect to this server on */
port = 6666;
/* hub mask: the mask of servers that this server may hub. Multiple
* entries are permitted
*/
hub_mask = "*";
/* leaf mask: the mask of servers this server may not hub. Multiple
* entries are permitted. Useful for forbidding EU -> US -> EU routes.
*/
#leaf_mask = "*.uk";
/* class: the class this server is in */
class = "server";
/* autoconnect: controls whether we autoconnect to this server or not,
* dependent on class limits.
*/
autoconn = yes;
/* compressed: controls whether traffic is compressed via ziplinks.
* By default this is disabled
*/
#compressed = yes;
/* lazylink: controls whether this server is a LazyLink. LazyLink
* servers may NOT hub. see doc/LazyLinks.as.implemented.txt
*/
#lazylink = yes;
/* masking: the servername we pretend to be when we connect */
#fakename = "*.arpa";
};
connect {
name = "encrypted.auth.example";
host = "some.host.somewhere";
port = 6667;
/* cryptlink: enable full encryption for all data passing between our
* server and this link and rsa authentication.
*/
cryptlink = yes;
/* rsa key: the path to the public keyfile of the server. Used instead
* of passwords.
*/
rsa_public_key_file = "etc/remote.server.keyfile";
/* cipher preference: set the preferred cipher for this link
*
* Available ciphers are:
* BF/256 BF/128 CAST/128 IDEA/128 RC5.16/128
* RC5.12/128 RC5.8/128 3DES/168 DES/56
*
* NOTE: Some ciphers may not be supported by your OpenSSL.
* Check the output from 'configure' for available ciphers.
*
* NOTE2: To help you decide what cipher to use, tools/encspeed
* will show you approximately how fast each cipher is.
* However, blowfish is fast and secure, and is probably
* a good default for most situations.
*
* NOTE3: Default if none is set is BF/128
*
* The cipher *MUST* be the same in both directions. If you
* set a cipher preference, your uplink must set the same cipher,
* else it will not link.
*/
#cipher_preference = "BF/256";
};
connect {
name = "ipv6.some.server";
host = "3ffd:dead:beef::1";
send_password = "password";
accept_password = "password";
port = 6666;
/* aftype: controls whether the connection uses "ipv4" or "ipv6".
* Default is ipv4.
*/
aftype = ipv6;
class = "server";
};
/* shared {}: users that are allowed to remote kline (OLD U:) */
shared {
/* name: the server the user must be on to set klines. If this is not
* specified, the user will be allowed to kline from all servers.
*/
name = "irc2.some.server";
/* user: the user@host mask that is allowed to set klines. If this is
* not specified, all users on the server above will be allowed to set
* a remote kline.
*/
user = "oper@my.host.is.spoofed";
};
/* kill {}: users that are not allowed to connect (OLD K:)
* Oper issued klines will be added to the specified kline config
*/
kill {
user = "bad@*.hacked.edu";
reason = "Obviously hacked account";
};
/* deny {}: IPs that are not allowed to connect (before DNS/ident lookup)
* Oper issued dlines will be added to the specified dline config
*/
deny {
ip = "10.0.1.0/24";
reason = "Reconnecting vhosted bots";
};
/* exempt {}: IPs that are exempt from deny {} and Dlines. (OLD d:) */
exempt {
ip = "192.168.0.0/16";
};
/* resv {}: nicks and channels users may not use/join (OLD Q:) */
resv {
/* reason: the reason for the proceeding resv's */
reason = "There are no services on this network";
/* resv: the nicks and channels users may not join/use */
nick = "nickserv";
nick = "chanserv";
channel = "#services";
/* resv: wildcard masks are also supported in nicks only */
reason = "Clone bots";
nick = "clone*";
};
/* gecos {}: The X: replacement, used for banning users based on their
* "realname". The action may be either:
* warn: allow client to connect, but send message to opers
* reject: drop clients but also send message to opers.
* silent: silently drop clients who match.
*/
gecos {
name = "*sex*";
reason = "Possible spambot";
action = warn;
};
gecos {
name = "sub7server";
reason = "Trojan drone";
action = reject;
};
gecos {
name = "*http*";
reason = "Spambot";
action = silent;
};
/* The channel block contains options pertaining to channels */
channel {
/* invex: Enable/disable channel mode +I, a n!u@h list of masks
* that can join a +i channel without an invite.
*/
use_invex = yes;
/* except: Enable/disable channel mode +e, a n!u@h list of masks
* that can join a channel through a ban (+b).
*/
use_except = yes;
/* halfops: Enable/disable channel mode "+h <nick>", this allows
* users to perform all channel functions except +/-o and kick
* opped users.
*/
use_halfops = yes;
/* anonops: Enable/disable channel mode +a. This hides the people
* who are opped in the channel from people who are unopped.
*
* The ircd will 'sync' the users oplists when they become opped
* or deopped by sending mode changes. This can cause a flood and
* could potentially be abused.
*/
use_anonops = no;
/* vchans: permit virtual channels, multiple copies of the same
* channel name. read doc/vchans.txt for more details
*
* We advise against using this on production networks
*/
use_vchans = yes;
/* vchans oper only: only allow opers to create vchans via /cjoin */
vchans_oper_only = yes;
/* knock: Allows users to request an invite to a channel that
* is locked somehow (+ikl). If the channel is +p or you are banned
* the knock will not be sent.
*/
use_knock = yes;
/* knock delay: The amount of time a user must wait between issuing
* the knock command.
*/
knock_delay = 5 minutes;
/* knock channel delay: How often a knock to any specific channel
* is permitted, regardless of the user sending the knock.
*/
knock_delay_channel = 1 minute;
/* max chans: The maximum number of channels a user can join/be on. */
max_chans_per_user = 15;
/* quiet on ban: stop banned people talking in channels. */
quiet_on_ban = yes;
/* max bans: maximum number of +b/e/I modes in a channel */
max_bans = 25;
/* persist time: the minimum amount of time a channel will remain with
* all its modes intact once the last user has left the channel.
*
* set to 0 to disable.
*/
persist_time = 30 minutes;
/* splitcode: the ircd will check every 60s as to whether splitmode
* should be disabled or not, so there may be a delay between a
* netsplit ending and splitmode ending.
*
* both split users and split servers must be true to enter splitmode
*
* you may force splitmode to be permanent by /quote set splitmode on
*/
/* split users: when the usercount is lower than this level, consider
* ourselves split. this must be set for automatic splitmode
*/
default_split_user_count = 0;
/* split servers: when the servercount is lower than this, consider
* ourselves split. this must be set for automatic splitmode
*/
default_split_server_count = 0;
/* split no create: disallow users creating channels on split, works in
* tandem with persistant channels, that have retained their modes.
*/
no_create_on_split = no;
/* split: no join: disallow users joining channels at all on a split */
no_join_on_split = no;
};
/* The serverhide block contains the options regarding serverhiding */
serverhide {
/* flatten links: this option will show all servers in /links appear
* that they are linked to this current server
*/
flatten_links = no;
/* links delay: how often to update the links file when it is
* flattened.
*/
links_delay = 5 minutes;
/* hidden: hide this server from a /links output on servers that
* support it. this allows hub servers to be hidden etc.
*/
hidden = no;
/* disable hidden: prevent servers hiding themselves from a
* /links ouput.
*/
disable_hidden = no;
/* hide servers: hide remote servernames everywhere and instead use
* network_name and network_desc.
*/
hide_servers = no;
/* disable remote: disable users doing commands on remote servers */
disable_remote_commands = no;
/* disable local channels: prevent users from joining &channels.
* This is extreme, but it is still a flaw in serverhide. It will
* however remove far more from users than it will give back in
* security.
*/
disable_local_channels = no;
};
/* The general block contains many of the options that were once compiled
* in options in config.h. The general block is read at start time.
*/
general {
/* floodcount: the default value of floodcount that is configurable
* via /quote set floodcount. This is the amount of lines a user
* may send to any other user/channel in one second.
*/
default_floodcount = 10;
/* failed oper notice: send a notice to all opers on the server when
* someone tries to OPER and uses the wrong password, host or ident.
*/
failed_oper_notice = yes;
/* dots in ident: the amount of '.' characters permitted in an ident
* reply before the user is rejected.
*/
dots_in_ident=2;
/* dot in ipv6: ircd-hybrid-6.0 and earlier will disallow hosts
* without a '.' in them. this will add one to the end. only needed
* for older servers.
*/
dot_in_ip6_addr = yes;
/* min nonwildcard: the minimum non wildcard characters in k/d/g lines
* placed via the server. klines hand placed are exempt from limits.
* wildcard chars: '.' '*' '?' '@'
*/
min_nonwildcard = 4;
/* max accept: maximum allowed /accept's for +g usermode */
max_accept = 20;
/* nick flood: enable the nickflood control code */
anti_nick_flood = yes;
/* nick flood: the nick changes allowed in the specified period */
max_nick_time = 20 seconds;
max_nick_changes = 5;
/* anti spam time: the minimum time a user must be connected before
* custom quit messages are allowed.
*/
anti_spam_exit_message_time = 5 minutes;
/* ts delta: the time delta allowed between server clocks before
* a warning is given, or before the link is dropped. all servers
* should run ntpdate/rdate to keep clocks in sync
*/
ts_warn_delta = 30 seconds;
ts_max_delta = 5 minutes;
/* client exit: prepend a users quit message with "Client exit: " */
client_exit = yes;
/* kline reason: show the user the reason why they are k/d/glined
* on exit. may give away who set k/dline when set via tcm.
*/
kline_with_reason = yes;
/* kline connection closed: make the users quit message on channels
* to be "Connection closed", instead of the kline reason.
*/
kline_with_connection_closed = no;
/* non redundant klines: flag and ignore redundant klines */
non_redundant_klines = yes;
/* warn no nline: warn opers about servers that try to connect but
* we dont have a connect {} block for. Twits with misconfigured
* servers can get really annoying with this enabled.
*/
warn_no_nline = yes;
/* stats o oper only: make stats o (opers) oper only */
stats_o_oper_only=yes;
/* stats P oper only: make stats P (ports) oper only */
stats_P_oper_only=no;
/* stats i oper only: make stats i (auth {}) oper only. set to:
* yes: show users no auth blocks, made oper only.
* masked: show users first matching auth block
* no: show users all auth blocks.
*/
stats_i_oper_only=masked;
/* stats k/K oper only: make stats k/K (klines) oper only. set to:
* yes: show users no auth blocks, made oper only
* masked: show users first matching auth block
* no: show users all auth blocks.
*/
stats_k_oper_only=masked;
/* caller id wait: time between notifying a +g user that somebody
* is messaging them.
*/
caller_id_wait = 1 minute;
/* pace wait simple: time between use of less intensive commands
* (HELP, remote WHOIS, WHOWAS)
*/
pace_wait_simple = 1 second;
/* pace wait: time between more intensive commands
* (ADMIN, INFO, LIST, LUSERS, MOTD, STATS, VERSION)
*/
pace_wait = 10 seconds;
/* short motd: send clients a notice telling them to read the motd
* instead of forcing a motd to clients who may simply ignore it.
*/
short_motd = no;
/* ping cookies: require clients to respond exactly to a ping command,
* can help block certain types of drones and FTP PASV mode spoofing.
*/
ping_cookie = no;
/* no oper flood: increase flood limits for opers. */
no_oper_flood = yes;
/* glines: enable glines, network wide temp klines */
glines = yes;
/* gline time: the amount of time a gline will remain before exiring */
gline_time = 1 day;
/* idletime: the maximum amount of time a user may idle before
* they are disconnected
*/
idletime = 0;
/* maximum links: the maximum amount of servers to connect to for
* connect blocks without a valid class.
*/
maximum_links = 1;
/* REMOVE ME. The following line checks you've been reading. */
havent_read_conf = 1;
/* logfiles: the logfiles to use for user connects, /oper uses,
* and failed /oper. These files must exist for logging to be used.
*/
fname_userlog = "logs/userlog";
fname_operlog = "logs/operlog";
fname_foperlog = "logs/foperlog";
/* max targets: the maximum amount of targets in a single
* PRIVMSG/NOTICE. set to 999 NOT 0 for unlimited.
*/
max_targets = 4;
/* client flood: maximum number of lines in a clients queue before
* they are dropped for flooding.
*/
client_flood = 20;
/* use help: whether an improved help system per command is available
* to users. If this is disabled, users will just be shown a command
* list.
*
* this is non-caching and the help file will be read per command
* which should be an adverse consideration for large servers.
*/
use_help = yes;
/* message locale: the default message locale if gettext() is enabled
* and working.
* Use "custom" for the (in)famous Hybrid custom messages.
* Use "standard" for the compiled in defaults.
*/
message_locale = "custom";
/* usermodes configurable: a list of usermodes for the options below
*
* +b - bots - See bot and drone flooding notices
* +c - cconn - Client connection/quit notices
* +d - debug - See debugging notices
* +f - full - See I: line full notices
* +g - callerid - Server Side Ignore
* +i - invisible - Not shown in NAMES or WHO unless you share a
* a channel
* +k - skill - See server generated KILL messages
* +l - locops - See LOCOPS messages
* +n - nchange - See client nick changes
* +r - rej - See rejected client notices
* +s - servnotice - See general server notices
* +u - unauth - See unauthorized client notices
* +w - wallop - See server generated WALLOPS
* +x - external - See remote server connection and split notices
* +y - spy - See LINKS, STATS, TRACE notices etc.
* +z - operwall - See oper generated WALLOPS
*/
/* oper only umodes: usermodes only opers may set */
oper_only_umodes = bots, cconn, debug, full, skill, nchange,
rej, spy, external, operwall, locops, unauth;
/* oper umodes: default usermodes opers get when they /oper */
oper_umodes = locops, servnotice, operwall, wallop;
/* servlink path: path to 'servlink' program used by ircd to handle
* encrypted/compressed server <-> server links.
*
* only define if servlink is not in same directory as ircd itself.
*/
#servlink_path = "/usr/local/ircd/bin/servlink";
/* default cipher: default cipher to use for cryptlink when none is
* specified in connect block.
*/
#default_cipher_preference = "BF/256";
/* use egd: if your system does not have *random devices yet you
* want to use OpenSSL and encrypted links, enable this. Beware -
* EGD is *very* CPU intensive when gathering data for its pool
*/
#use_egd = yes;
/* egdpool path: path to EGD pool. Not necessary for OpenSSL >= 0.9.7
* which automatically finds the path.
*/
#egdpool_path = "/var/run/egd-pool";
/* compression level: level of compression for compressed links between
* servers.
*
* values are between: 1 (least compression, fastest)
* and: 9 (most compression, slowest).
*/
#compression_level = 6;
/* throttle time: the minimum amount of time between connections from
* the same ip. exempt {} blocks are excluded from this throttling.
* Offers protection against flooders who reconnect quickly.
* Set to 0 to disable.
*/
throttle_time = 10;
};
modules {
/* module path: paths to search for modules specified below and
* in /modload.
*/
path = "/usr/local/ircd/modules";
path = "/usr/local/ircd/modules/autoload";
/* module: the name of a module to load on startup/rehash */
#module = "some_module.so";
};

932
doc/example.efnet.conf Normal file
View file

@ -0,0 +1,932 @@
/* doc/example.efnet.conf - ircd-hybrid-7 EFnet Example configuration file
*
* Modified for EFnet by: Disciple
* Based on example.conf written by ejb, wcampbel, db, leeh and others
*
* $Id: example.efnet.conf,v 1.1 2002/08/13 14:35:21 fishwaldo Exp $
*/
/* IMPORTANT NOTES:
*
* class {} blocks MUST be specified before anything that uses them. That
* means they must be defined before auth {} and before connect {}.
*
* auth {} blocks MUST be specified in order of precedence. The first one
* that matches a user will be used. So place spoofs first, then specials,
* then general access, then restricted.
*
* Both shell style (#) and C style comments are supported.
*
* Files may be included by either:
* .include "filename"
* .include <filename>
*
* Times/durations are written as:
* 12 hours 30 minutes 1 second
*
* Valid units of time:
* month, week, day, hour, minute, second
*
* Valid units of size:
* megabyte/mbyte/mb, kilobyte/kbyte/kb, byte
*
* Sizes and times may be singular or plural.
*/
/* EFNET NOTE:
*
* This configuration file is a BASIC configuration file for use
* on EFnet. You MUST still take the time to set this file up
* properly.
*
* DISCLAIMER: This file was NOT generated by the ircd-hybrid team,
* it was submitted and maintained by Disciple@EFnet
*/
/* serverinfo {}: Contains information about the server. (OLD M:) */
serverinfo {
/* name: the name of our server */
name = "efnet.irc";
/* description: the description of our server. '[' and ']' may not
* be used here for compatibility with older servers.
*/
description = "ircd-hybrid-7 EFnet Server";
/* network info: the name and description of the network this server
* is on. Shown in the 005 reply and used with serverhiding.
*/
network_name = "EFnet";
network_desc = "Eris Free Network";
/* 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.
* This should be an ipv4 IP only.
*/
#vhost = "192.169.0.1";
/* vhost6: the IP to bind to when we connect outward to ipv6 servers.
* This should be an ipv6 IP only.
*/
#vhost6 = "3ffe:80e8:546::2";
/* max clients: the maximum number of clients allowed to connect */
max_clients = 512;
/* rsa key: the path to the file containing our rsa key for cryptlink.
*
* Example command to store a 2048 bit RSA keypair in
* rsa.key, and the public key in rsa.pub:
*
* openssl genrsa -out rsa.key 2048
* openssl rsa -in rsa.key -pubout -out rsa.pub
* chown <ircd-user>.<ircd.group> rsa.key rsa.pub
* chmod 0600 rsa.key
* chmod 0644 rsa.pub
*/
#rsa_private_key_file = "/usr/local/ircd/etc/rsa.key";
};
/* admin {}: contains admin information about the server. (OLD A:) */
admin {
name = "EFnet Admin";
description = "Main Server Administrator";
email = "<irc-admin@efnet.irc>";
};
/* logging {}: contains information about logfiles. */
logging {
/* log level: the amount of detail to log in ircd.log. The
* higher, the more information is logged. May be changed
* once the server is running via /quote SET LOG. Either:
* L_CRIT, L_ERROR, L_WARN, L_NOTICE, L_TRACE, L_INFO or L_DEBUG
*/
log_level = L_INFO;
};
/* class {}: contain information about classes for users (OLD Y:) */
class {
/* name: the name of the class. classes are text now */
name = "users";
/* ping time: how often a client must reply to a PING from the
* server before they are dropped.
*/
ping_time = 2 minutes;
/* number per ip: the number of users per host allowed to connect */
number_per_ip = 2;
/* max number: the maximum number of users allowed in this class */
max_number = 100;
/* sendq: the amount of data allowed in a clients queue before
* they are dropped.
*/
sendq = 100 kbytes;
};
class {
name = "restricted";
ping_time = 1 minute 30 seconds;
number_per_ip = 1;
max_number = 100;
sendq = 60kb;
};
class {
name = "opers";
ping_time = 5 minutes;
number_per_ip = 10;
max_number = 100;
sendq = 1 mbyte;
};
class {
name = "server";
ping_time = 5 minutes;
/* connectfreq: only used in server classes. specifies the delay
* between autoconnecting to servers.
*/
connectfreq = 5 minutes;
/* max number: the amount of servers to autoconnect to */
max_number = 1;
/* sendq: servers need a higher sendq as they send more data */
sendq = 15 megabytes;
};
/* listen {}: contain information about the ports ircd listens on (OLD P:) */
listen {
/* port: the specific port to listen on. if no host is specified
* before, it will listen on all available IPs.
*
* ports are seperated via a comma, a range may be specified using ".."
*/
/* port: listen on all available IPs, ports 6665 to 6669 */
port = 6665 .. 6669;
/* host: set a specific IP/host the ports after the line will listen
* on. This may be ipv4 or ipv6.
*/
host = "1.2.3.4";
port = 7000, 7001;
host = "3ffe:1234:a:b:c::d";
port = 7002;
};
/* auth {}: allow users to connect to the ircd (OLD I:) */
auth {
/* user: the user@host allowed to connect. multiple IPv4/IPv6 user
* lines are permitted per auth block.
*/
user = "*@172.16.0.0/12";
user = "*test@123D:B567:*";
/* password: an optional password that is required to use this block */
password = "letmein";
/* spoof: fake the users host to be be this. This is free-form,
* just do everyone a favour and dont abuse it. (OLD I: = flag)
*/
spoof = "I.still.hate.packets";
/* spoof notice: enable spoofing notification to admins (default yes) */
spoof_notice = yes;
/* exceed limit: allow a user to exceed class limits (OLD I: > flag) */
exceed_limit = yes;
/* kline exempt: exempt this user from k/glines (OLD I: ^ flag) */
kline_exempt = yes;
/* gline exempt: exempt this user from glines (OLD I: _ flag) */
gline_exempt = yes;
/* no tilde: remove ~ from a user with no ident (OLD I: - flag) */
no_tilde = yes;
/* class: the class the user is placed in */
class = "opers";
};
auth {
/* redirect: the server and port to redirect a user to. A user does
* not have to obey the redirection, the ircd just suggests to them
* an alternative server.
*/
redirserv = "irc.fi";
redirport = 6667;
user = "*.fi";
/* class: a class is required even though it is not used */
class = "users";
};
auth {
user = "*@*";
class = "users";
/* restricted: stop the client sending mode changes */
#restricted = yes;
/* have ident: require the user has identd to connect (OLD I: + flag) */
have_ident = yes;
};
/* operator {}: defines ircd operators. (OLD O:)
* ircd-hybrid no longer supports local operators, privileges are
* controlled via flags.
*/
operator {
/* name: the name of the oper */
name = "god";
/* user: the user@host required for this operator. CIDR is not
* supported. multiple user="" lines are supported.
*/
user = "*god@*";
user = "*@127.0.0.1";
/* password: the password required to oper. By default this will
* need to be encrypted using 'mkpasswd'. MD5 is supported.
*/
password = "crYpTpwH3r3"
/* rsa key: the public key for this oper when using Challenge.
* A password should not be defined when this is used, see
* doc/challenge.txt for more information.
*/
#rsa_public_key_file = "/usr/local/ircd/etc/oper.pub";
/* class: the class the oper joins when they successfully /oper */
class = "opers";
/* privileges: controls the activities and commands an oper are
* allowed to do on the server. All options default to no.
* Available options:
*
* global_kill: allows remote users to be /KILL'd (OLD 'O' flag)
* remote: allows remote SQUIT and CONNECT (OLD 'R' flag)
* kline: allows KILL, KLINE and DLINE (OLD 'K' flag)
* unkline: allows UNKLINE and UNDLINE (OLD 'U' flag)
* gline: allows GLINE (OLD 'G' flag)
* nick_changes: allows oper to see nickchanges (OLD 'N' flag)
* via usermode +n
* rehash: allows oper to REHASH config (OLD 'H' flag)
* die: allows DIE and RESTART (OLD 'D' flag)
* admin: gives admin privileges. admins
* may (un)load modules and see the
* real IPs of servers and spoofed
* users IP.
*/
global_kill = yes;
remote = yes;
kline = yes;
unkline = yes;
gline = yes;
die = yes;
rehash = yes;
nick_changes = yes;
admin = yes;
};
/* connect {}: controls servers we connect to (OLD C:, N:, H:, L:) */
connect {
/* name: the name of the server */
name = "irc.uplink.com";
/* host: the host or IP to connect to. If a hostname is used it
* must match the reverse dns of the server.
*/
host = "192.168.0.1";
/* passwords: the passwords we send (OLD C:) and accept (OLD N:).
* The remote server will have these passwords reversed.
*/
send_password = "password"; # OLD C:
accept_password = "anotherpassword"; # OLD N:
/* encrypted: controls whether the accept_password above has been
* encrypted. (OLD CRYPT_LINK_PASSWORD now optional per connect)
*/
encrypted = no;
/* port: the port to connect to this server on (OLD P:) */
port = 6666;
/* hub mask: the mask of servers that this server may hub. Multiple
* entries are permitted (OLD H:)
*/
hub_mask = "*";
/* leaf mask: the mask of servers this server may not hub. Multiple
* entries are permitted. Useful for forbidding EU -> US -> EU routes.
* (OLD L:)
*/
#leaf_mask = "*.uk";
/* class: the class this server is in */
class = "server";
/* autoconnect: controls whether we autoconnect to this server or not,
* dependent on class limits.
*/
autoconn = no;
/* compressed: controls whether traffic is compressed via ziplinks.
* By default this is disabled (OLD c: (lowercased))
*/
#compressed = yes;
/* lazylink: controls whether this server is a LazyLink. LazyLink
* servers may NOT hub. see doc/LazyLinks.as.implemented.txt
*
* EFnet Note: With this enabled, you download a connect burst
* as it is needed, instead of all at once. This
* could allow servers on much smaller lines (modems) to
* link a server. As such, this is probably not a
* good idea to run on EFnet.
*/
#lazylink = no; # Not a good idea on EFnet
/* masking: the servername we pretend to be when we connect */
#fakename = "*.arpa";
};
connect {
name = "encrypted.auth.example";
host = "some.host.somewhere";
port = 6667;
/* cryptlink: enable full encryption for all data passing between our
* server and this link and rsa authentication.
*/
cryptlink = yes;
/* rsa key: the path to the public keyfile of the server. Used instead
* of passwords.
*/
rsa_public_key_file = "etc/remote.server.keyfile";
/* cipher preference: set the preferred cipher for this link
*
* Available ciphers are:
* BF/256 BF/128 CAST/128 IDEA/128 RC5.16/128
* RC5.12/128 RC5.8/128 3DES/168 DES/56
*
* NOTE: Some ciphers may not be supported by your OpenSSL.
* Check the output from 'configure' for available ciphers.
*
* NOTE2: To help you decide what cipher to use, tools/encspeed
* will show you approximately how fast each cipher is.
* However, blowfish is fast and secure, and is probably
* a good default for most situations.
*
* NOTE3: Default if none is set is BF/128
*
* The cipher *MUST* be the same in both directions. If you
* set a cipher preference, your uplink must set the same cipher,
* else it will not link.
*/
#cipher_preference = "BF/256";
};
connect {
name = "ipv6.some.server";
host = "3ffd:dead:beef::1";
send_password = "password";
accept_password = "password";
port = 6666;
/* aftype: controls whether the connection uses "ipv4" or "ipv6".
* Default is ipv4.
*/
aftype = ipv6;
class = "server";
};
/* shared {}: users that are allowed to remote kline (OLD U:)
*
* EFnet Note: This can be effectively used for remote klines.
* Please note that there is no password authentication
* for users setting remote klines. You must also be
* /oper'd in order to issue a remote kline.
*/
shared {
/* name: the server the user must be on to set klines. If this is not
* specified, the user will be allowed to kline from all servers.
*/
name = "irc2.some.server";
/* user: the user@host mask that is allowed to set klines. If this is
* not specified, all users on the server above will be allowed to set
* a remote kline.
*/
user = "oper@my.host.is.spoofed";
};
/* kill {}: users that are not allowed to connect (OLD K:)
* Oper issued klines will be added to the specified kline config
*/
kill {
user = "bad@*.hacked.edu";
reason = "Obviously hacked account";
};
/* deny {}: IPs that are not allowed to connect (OLD D:) (before DNS/ident
* lookup) Oper issued dlines will be added to the specified dline config
*/
deny {
ip = "10.0.1.0/24";
reason = "Reconnecting vhosted bots";
};
/* exempt {}: IPs that are exempt from deny {} and Dlines. (OLD d:)
*
* EFnet Note: exempt {} blocks are NOT hidden, so do NOT exempt
* EFnet server IP's.
*/
exempt {
ip = "192.168.0.0/16";
};
/* resv {}: nicks and channels users may not use/join (OLD Q:) */
resv {
/* reason: the reason for the proceeding resv's */
reason = "There are no services on this network";
/* resv: the nicks and channels users may not join/use */
nick = "nickserv";
nick = "chanserv";
nick = "operserv";
nick = "JUPES";
nick = "JUPE";
nick = "CH?NF?X"; # CHANFIX (services.int)
/* These are totally optional, but may be a good idea */
nick = "oper";
nick = "ircop";
nick = "op";
nick = "ident";
nick = "pass";
channel = "#jupedchan";
/* resv: wildcard masks are also supported in nicks only */
reason = "Clone bots";
nick = "clone*";
};
/* gecos {}: The X: replacement, used for banning users based on their
* "realname". The action may be either:
* warn: allow client to connect, but send message to opers
* reject: drop clients but also send message to opers.
* silent: silently drop clients who match.
*/
gecos {
name = "*sex*";
reason = "Possible spambot";
action = warn;
};
gecos {
name = "sub7server";
reason = "Trojan drone";
action = reject;
};
gecos {
name = "*http*";
reason = "Spambot";
action = silent;
};
/* The channel block contains options pertaining to channels */
channel {
/* invex: Enable/disable channel mode +I, a n!u@h list of masks
* that can join a +i channel without an invite.
*
* EFNet Note: This should NOT be run on EFnet.
*/
use_invex = no; # Don't enable this on EFnet
/* except: Enable/disable channel mode +e, a n!u@h list of masks
* that can join a channel through a ban (+b).
*
* EFNet Note: This should NOT be run on EFnet.
*/
use_except = no; # Don't enable this on EFnet
/* halfops: Enable/disable channel mode "+h <nick>", this allows
* users to perform all channel functions except +/-o and kick
* opped users.
*
* EFNet Note: This should NOT be run on EFnet.
*/
use_halfops = no; # Don't enable this on EFnet
/* anonops: Enable/disable channel mode +a. This hides the people
* who are opped in the channel from people who are unopped.
*
* The ircd will 'sync' the users oplists when they become opped
* or deopped by sending mode changes. This can cause a flood and
* could potentially be abused.
*
* EFNet Note: This should NOT be run on EFnet.
*/
use_anonops = no; # Don't enable this on EFnet
/* vchans: permit virtual channels, multiple copies of the same
* channel name. read doc/vchans.txt for more details
*
* If you ./configure'd with --enable-efnet, the code for this
* feature will not be compiled into the ircd
*
* EFNet Note: This should NOT be run on EFnet (this feature
* would very badly break EFnet).
*
*/
use_vchans = no; # Don't enable this on EFnet
/* vchans oper only: only allow opers to create vchans via /cjoin */
vchans_oper_only = yes;
/* knock: Allows users to request an invite to a channel that
* is locked somehow (+ikl). If the channel is +p or you are banned
* the knock will not be sent.
*
* EFnet Note: As this feature is used by European servers, but
* not North American ones, it has been left enabled
* by default. Please feel free to disable this
* if you do not want to run channel knock.
*/
use_knock = yes;
/* knock delay: The amount of time a user must wait between issuing
* the knock command.
*/
knock_delay = 1 minute;
/* knock channel delay: How often a knock to any specific channel
* is permitted, regardless of the user sending the knock.
*/
knock_delay_channel = 1 minute;
/* max chans: The maximum number of channels a user can join/be on. */
max_chans_per_user = 25;
/* quiet on ban: stop banned people talking in channels. */
quiet_on_ban = yes;
/* max bans: maximum number of +b/e/I modes in a channel */
max_bans = 25;
/* persist time: the minimum amount of time a channel will remain with
* all its modes intact once the last user has left the channel.
*
* set to 0 to disable.
*/
persist_time = 30 minutes;
/* splitcode: the ircd will check every 60s as to whether splitmode
* should be disabled or not, so there may be a delay between a
* netsplit ending and splitmode ending.
*
* both split users and split servers must be true to enter splitmode
*
* you may force splitmode to be permanent by /quote set splitmode on
*/
/* split users: when the usercount is lower than this level, consider
* ourselves split. this must be set for automatic splitmode
*/
default_split_user_count = 10000;
/* split servers: when the servercount is lower than this, consider
* ourselves split. this must be set for automatic splitmode
*/
default_split_server_count = 10;
/* split no create: disallow users creating channels on split, works in
* tandem with persistant channels, that have retained their modes.
*/
no_create_on_split = no;
/* split: no join: disallow users joining channels at all on a split */
no_join_on_split = no;
};
/* The serverhide block contains the options regarding serverhiding */
serverhide {
/* flatten links: this option will show all servers in /links appear
* that they are linked to this current server
*
* EFnet Note: While this is not a requirement on EFnet, it
* may be a good idea.
*/
flatten_links = yes;
/* links delay: how often to update the links file when it is
* flattened.
*/
links_delay = 5 minutes;
/* hidden: hide this server from a /links output on servers that
* support it. this allows hub servers to be hidden etc.
*/
hidden = no;
/* disable hidden: prevent servers hiding themselves from a
* /links ouput.
*/
disable_hidden = no;
/* hide servers: hide remote servernames everywhere and instead use
* network_name and network_desc.
*/
hide_servers = no;
/* disable remote: disable users doing commands on remote servers */
disable_remote_commands = no;
/* disable local channels: prevent users from joining &channels.
* This is extreme, but it is still a flaw in serverhide. It will
* however remove far more from users than it will give back in
* security.
*/
disable_local_channels = no;
};
/* The general block contains many of the options that were once compiled
* in options in config.h. The general block is read at start time.
*/
general {
/* floodcount: the default value of floodcount that is configurable
* via /quote set floodcount. This is the amount of lines a user
* may send to any other user/channel in one second.
*/
default_floodcount = 10;
/* failed oper notice: send a notice to all opers on the server when
* someone tries to OPER and uses the wrong password, host or ident.
*/
failed_oper_notice = yes;
/* dots in ident: the amount of '.' characters permitted in an ident
* reply before the user is rejected.
*/
dots_in_ident=0;
/* dot in ipv6: ircd-hybrid-6.0 and earlier will disallow hosts
* without a '.' in them. this will add one to the end. only needed
* for older servers.
*/
dot_in_ip6_addr = no;
/* min nonwildcard: the minimum non wildcard characters in k/d/g lines
* placed via the server. klines hand placed are exempt from limits.
* wildcard chars: '.' '*' '?' '@'
*/
min_nonwildcard = 3;
/* max accept: maximum allowed /accept's for +g usermode */
max_accept = 20;
/* nick flood: enable the nickflood control code */
anti_nick_flood = yes;
/* nick flood: the nick changes allowed in the specified period */
max_nick_time = 20 seconds;
max_nick_changes = 5;
/* anti spam time: the minimum time a user must be connected before
* custom quit messages are allowed.
*/
anti_spam_exit_message_time = 5 minutes;
/* ts delta: the time delta allowed between server clocks before
* a warning is given, or before the link is dropped. all servers
* should run ntpdate/rdate to keep clocks in sync
*/
ts_warn_delta = 30 seconds;
ts_max_delta = 5 minutes;
/* client exit: prepend a users quit message with "Client exit: " */
client_exit = no;
/* kline reason: show the user the reason why they are k/d/glined
* on exit. may give away who set k/dline when set via tcm.
*/
kline_with_reason = yes;
/* kline connection closed: make the users quit message on channels
* to be "Connection closed", instead of the kline reason.
*/
kline_with_connection_closed = yes;
/* non redundant klines: flag and ignore redundant klines */
non_redundant_klines = yes;
/* warn no nline: warn opers about servers that try to connect but
* we dont have a connect {} block for. Twits with misconfigured
* servers can get really annoying with this enabled.
*/
warn_no_nline = yes;
/* stats o oper only: make stats o (opers) oper only */
stats_o_oper_only=yes;
/* stats P oper only: make stats P (ports) oper only */
stats_P_oper_only=yes;
/* stats i oper only: make stats i (auth {}) oper only. set to:
* yes: show users no auth blocks, made oper only.
* masked: show users first matching auth block
* no: show users all auth blocks.
*/
stats_i_oper_only=yes;
/* stats k/K oper only: make stats k/K (klines) oper only. set to:
* yes: show users no auth blocks, made oper only
* masked: show users first matching auth block
* no: show users all auth blocks.
*/
stats_k_oper_only=yes;
/* caller id wait: time between notifying a +g user that somebody
* is messaging them.
*/
caller_id_wait = 1 minute;
/* pace wait simple: time between use of less intensive commands
* (HELP, remote WHOIS, WHOWAS)
*/
pace_wait_simple = 1 second;
/* pace wait: time between more intensive commands
* (ADMIN, INFO, LIST, LUSERS, MOTD, STATS, VERSION)
*/
pace_wait = 10 seconds;
/* short motd: send clients a notice telling them to read the motd
* instead of forcing a motd to clients who may simply ignore it.
*/
short_motd = no;
/* ping cookies: require clients to respond exactly to a ping command,
* can help block certain types of drones and FTP PASV mode spoofing.
*/
ping_cookie = no;
/* no oper flood: increase flood limits for opers. */
no_oper_flood = yes;
/* glines: enable glines, network wide temp klines
*
* EFnet Note: This feature is required for European EFnet servers
* and is used by several North American servers. As
* such, it has been left on by default. If you
* do not want your server to participate in G:Lines
* you should disable this.
*/
glines = yes;
/* gline time: the amount of time a gline will remain before exiring */
gline_time = 1 day;
/* idletime: the maximum amount of time a user may idle before
* they are disconnected
*/
idletime = 0;
/* maximum links: the maximum amount of servers to connect to for
* connect blocks without a valid class.
*/
maximum_links = 1;
/* REMOVE ME. The following line checks you've been reading. */
havent_read_conf = 1;
/* logfiles: the logfiles to use for user connects, /oper uses,
* and failed /oper. These files must exist for logging to be used.
*/
fname_userlog = "logs/userlog";
fname_operlog = "logs/operlog";
fname_foperlog = "logs/foperlog";
/* max targets: the maximum amount of targets in a single
* PRIVMSG/NOTICE. set to 999 NOT 0 for unlimited.
*/
max_targets = 4;
/* client flood: maximum number of lines in a clients queue before
* they are dropped for flooding.
*/
client_flood = 20;
/* use help: whether an improved help system per command is available
* to users. If this is disabled, users will just be shown a command
* list.
*
* EFNET NOTE: It is not recommended you enable this due to the method
* of reading help files.
*/
use_help = no;
/* message locale: the default message locale if gettext() is enabled
* and working.
* Use "custom" for the (in)famous Hybrid custom messages.
* Use "standard" for the compiled in defaults.
*/
message_locale = "standard";
/* usermodes configurable: a list of usermodes for the options below
*
* +b - bots - See bot and drone flooding notices
* +c - cconn - Client connection/quit notices
* +d - debug - See debugging notices
* +f - full - See I: line full notices
* +g - callerid - Server Side Ignore (for privmsgs etc)
* +i - invisible - Not shown in NAMES or WHO unless you share a
* a channel
* +k - skill - See server generated KILL messages
* +l - locops - See LOCOPS messages
* +n - nchange - See client nick changes
* +r - rej - See rejected client notices
* +s - servnotice - See general server notices
* +u - unauth - See unauthorized client notices
* +w - wallop - See server generated WALLOPS
* +x - external - See remote server connection and split notices
* +y - spy - See LINKS, STATS, TRACE notices etc.
* +z - operwall - See oper generated WALLOPS
*/
/* oper only umodes: usermodes only opers may set */
oper_only_umodes = bots, cconn, debug, full, skill, nchange,
rej, spy, external, operwall, locops, unauth;
/* oper umodes: default usermodes opers get when they /oper */
oper_umodes = locops, servnotice, operwall, wallop;
/* servlink path: path to 'servlink' program used by ircd to handle
* encrypted/compressed server <-> server links.
*
* only define if servlink is not in same directory as ircd itself.
*/
#servlink_path = "/usr/local/ircd/bin/servlink";
/* default cipher: default cipher to use for cryptlink when none is
* specified in connect block.
*/
#default_cipher_preference = "BF/256";
/* use egd: if your system does not have *random devices yet you
* want to use OpenSSL and encrypted links, enable this. Beware -
* EGD is *very* CPU intensive when gathering data for its pool
*/
#use_egd = yes;
/* egdpool path: path to EGD pool. Not necessary for OpenSSL >= 0.9.7
* which automatically finds the path.
*/
#egdpool_path = "/var/run/egd-pool";
/* compression level: level of compression for compressed links between
* servers.
*
* values are between: 1 (least compression, fastest)
* and: 9 (most compression, slowest).
*/
#compression_level = 6;
/* throttle time: the minimum amount of time between connections from
* the same ip. exempt {} blocks are excluded from this throttling.
* Offers protection against flooders who reconnect quickly.
* Set to 0 to disable.
*
* EFnet Note: exempt {} blocks are NOT hidden, so do NOT exempt
* EFnet server IP's.
*/
throttle_time = 0;
};
modules {
/* module path: paths to search for modules specified below and
* in /modload.
*/
path = "/usr/local/ircd/modules";
path = "/usr/local/ircd/modules/autoload";
/* module: the name of a module to load on startup/rehash */
#module = "some_module.so";
};

36
doc/guidelines.txt Normal file
View file

@ -0,0 +1,36 @@
ircd-hybrid documentation guidelines
1. When a major change in the code affects users, it MUST be documented
in whats-new and all other appropriate locations.
2. When something affects the configuration file, and it's compatibility
with previous versions, it MUST be documented in example.conf and in a
proposed new document README.NOW. This is VERY important during the beta
phase to help anyone who mans the "help desk".
3. All documentation must properly fit in an 80 character wide terminal.
SGML and other "professional" documentation systems are good for some
projects, but hybrid is intended to be used on minimal UNIX installations
where any extra binary is a security risk. Text only docs, sized to fit
properly in an 80 character wide console, are what admins expect, and that's
what they should get.
4. All documentation must be spell checked before a release or a beta.
'ispell' (using either the US or British dictionary) is probably the
easiest way to spell check the documentation. 'ispell -a' at the command
line will allow you to check individual words as you are editing.
5. When a document is over approximately 5 pages long, it should be split
into sections to facilitate users reading them.
6. All docs (except docs specifically describing code) should be written
in a way that all users of the software (not just programmers) will be able
to easily understand.
7. Don't make documentation a chore. If it's done while coding, or shortly
after, it usually is more accurate and the documentation tasks don't get
pushed back and pile up.
8. Don't forget to include a CVS Id.
# $Id: guidelines.txt,v 1.1 2002/08/13 14:35:21 fishwaldo Exp $

38
doc/index.txt Normal file
View file

@ -0,0 +1,38 @@
# $Id: index.txt,v 1.1 2002/08/13 14:35:21 fishwaldo Exp $
Here is the overview of the documents in the doc/ directory.
CIDR.txt - Description of CIDR in IPv4
LazyLinks.txt - The lazylinks leaf concept
Tao-of-IRC.940110 - No comment...
challenge.txt - Overview of the challenge/response system for
obtaining operator status
dline.conf - A blank dline.conf file used by make install
example.conf - An example ircd.conf file describing most of the
user settable options
guidelines.txt - Documentation guidelines
index.txt - This file
ircd.8 - The new revised manpage, read with the following
commands in the prefix directory:
man -M . ircd
ircd.motd - A default ircd.motd used by make install
kline.conf - A blank kline.conf file used by make install
kline.txt - Outline of the remote K-line protocol for both
opers and servers
messages.txt - A general help file for users and admins to
customize ircd's messages.
modeg.txt - An in depth description of the server side silence
user mode (+g)
modes.txt - A list of all user and channel modes
operguide.txt - EFnet operator's guide
opermyth.txt - Oper myth's, describes what opers can and cannot do
resv.txt - Outline of the RESV command.
server-version-info - Overview of the flags shown in /version
serverhide.txt - Information about the server hide options
simple.conf - A simple ircd.conf useful for beginning admins
vchans.txt - The paper describing virtual channels
whats-new.txt - What new features are available
Also in the contrib/ directory you will find:
example_module.c - An example module, detailing what the code in a module
does. Useful for building your own modules.

114
doc/ircd.8 Normal file
View file

@ -0,0 +1,114 @@
.\" @(#)ircd.8 7b10 25 Oct 2001
.\" $Id: ircd.8,v 1.1 2002/08/13 14:35:21 fishwaldo Exp $
.TH IRCD 8 "ircd-hybrid-7 25 Oct 2001
.SH NAME
ircd \- The Internet Relay Chat Program Server
.SH SYNOPSIS
.hy 0
.IP \fBircd\fP
[-dlinefile filename] [-configfile filename] [-klinefile filename]
[-logfile filename] [-pidfile filename] [-foreground] [-version] [-debug]
.SH DESCRIPTION
.LP
\fIircd\fP is the server (daemon) program for the Internet Relay Chat
Program. The \fIircd\fP is a server in that its function is to "serve"
the client program \fIirc(1)\fP with messages and commands. All commands
and user messages are passed directly to the \fIircd\fP for processing
and relaying to other ircd sites.
.SH OPTIONS
.TP
.B \-dlinefile filename
Specifies the D-line file to be used. This file is used for both reading
D-lines at startup, and writing to while \fIircd\fP is running.
.TP
.B \-configfile filename
Specifies the ircd.conf file to be used for this ircdaemon. The option
is used to override the default ircd.conf given at compile time.
.TP
.B \-klinefile filename
Specifies the K-line file to be used. This file is used for both reading
K-lines at startup, and writing to while \fIircd\fP is running.
.TP
.B \-logfile filename
Specifies an alternative logfile to be used than that specified in config.h
.TP
.B \-pidfile filename
Specifies the ircd.pid used. The option is used to override the default
ircd.pid given at compile time.
.TP
.B \-foreground
Makes \fIircd\fP run in the foreground
.TP
.B \-version
Makes \fIircd\fP print its version, and exit.
.TP
.B \-debug
Makes \fIircd\fP start in debug mode. \fIIrcd\fP must be compiled in DEBUGMODE
for this to work.
.SH USAGE
If you plan to connect your \fIircd\fP server to an existing Irc-Network,
you will need to alter your local IRC configuration file (typically named
"ircd.conf") so that it will accept and make connections to other \fIircd\fP
servers. This file contains the hostnames, Network Addresses, and sometimes
passwords for connections to other ircds around the world. Because
description of the actual file format of the "ircd.conf" file is beyond the
scope of this document, please refer to the file INSTALL in the IRC source
files documentation directory.
.LP
.SH BOOTING THE SERVER
The \fIircd\fP server can be started as part of the
Unix boot procedure or just by placing the server into Unix Background.
Keep in mind that if it is \fBnot\fP part of your Unix's boot-up procedure
then you will have to manually start the \fIircd\fP server each time your
Unix is rebooted. This means if your Unix is prone to crashing
or going for for repairs a lot it would make sense to start the \fIircd\fP
server as part of your UNIX bootup procedure.
.SH EXAMPLE
.RS
.nf
tolsun% \fBbin/ircd\fP
.fi
.RE
.LP
Places \fIircd\fP into Unix background and starts up the server for use.
Note: You do not have to add the "&" to this command, the program will
automatically detach itself from tty.
.RS
.nf
leguin% \fBbin/ircd -foreground\fP
.fi
.RE
.LP
Runs ircd in the foreground.
.RS
.nf
.SH COPYRIGHT
(c) 1988,1989 University of Oulu, Computing Center, Finland,
.LP
(c) 1988,1989 Department of Information Processing Science,
University of Oulu, Finland
.LP
(c) 1988,1989,1990,1991 Jarkko Oikarinen
.LP
(c) 1997,1998,1999,2000,2001 The IRCD-Hybrid project.
.LP
For full COPYRIGHT see LICENSE file with IRC package.
.LP
.RE
.SH FILES
"ircd.conf"
.SH "SEE ALSO"
ircd.conf(5)
.SH BUGS
None... ;-) if somebody finds one, please inform author
.SH AUTHOR
irc2.8 and earlier: Jarkko Oikarinen, currently jto@tolsun.oulu.fi.
.LP
ircd-hybrid-7: IRCD-Hybrid Project, ircd-hybrid@the-project.org.
.LP
manual page written by Jeff Trim, jtrim@orion.cair.du.edu,
later modified by jto@tolsun.oulu.fi.
.LP
modified for ircd-hybrid-7 by Edward Brocklesby, ejb@klamath.uucp.leguin.org.uk.
.LP
updated by W. Campbell, wcampbel@botbay.net

1
doc/ircd.motd Normal file
View file

@ -0,0 +1 @@
This is ircd-hybrid MOTD replace it with something better

0
doc/kline.conf Normal file
View file

108
doc/kline.txt Normal file
View file

@ -0,0 +1,108 @@
/* doc/kline.txt - Overview of the remote kline system
*
* Copyright (C) 2001-2002 Hybrid Development Team
*
* $Id: kline.txt,v 1.1 2002/08/13 14:35:21 fishwaldo Exp $
*/
Introduction
------------
ircd-hybrid-7 will allow opers to add klines on multiple servers, an extension
and replacement of the old ircd-hybrid-6 method of sharing all klines between
servers. Remote unkline is not currently supported, however an unofficial
patch to support this exists in contrib/. Read contrib/README for more
information.
In this implementation, it is extended to be routable among servers which
understand the "KLN" capability. This allows us to continue to "talk"
to non remote kline capable servers without breaking anything.
Usage
-----
The old kline method has not been changed. To place a kline it is still:
/quote kline <nick|user@host> :reason
/quote kline [tkline_duration] <nick|user@host> :reason
Scenario 1
----------
Oper wishes to kline user@host on server irc.xyz.net
/quote kline <nick|user@host> on irc.xyz.net :reason
/quote kline [duration] <nick|user@host> on irc.xyz.net :reason
Scenario 2
----------
Oper wishes to kline user@host on all servers named *.uk
/quote kline <nick|user@host> on *.uk :reason
/quote kline [duration] <nick|user@host> on *.uk :reason
Scenario 3
----------
Oper wishes to place a network wide kline on user@host
/quote kline <nick|user@host> on * :reason
/quote kline [duration] <nick|user@host> on * :reason
Authorisation
-------------
For the kline to be accepted by the remote server, the server must have
explicitly allowed klines from that user. This is done via a shared {};
block in ircd.conf.
The shared block contains two settings, a user@host mask of the oper
who is allowed to kline, and a servername.
- If both of these options are present, klines will only be allowed
from that specific user@host on that specific server.
- If only the servername is present, all klines from opers on that
server will be accepted.
- If only the user@host is present, all klines from that user@host on
any server will be accepted.
- If neither are present, the shared block is invalid.
shared {
/* The name of the server we allow klines from */
name = "this.server.net";
/* the user@host allowed to kline */
user = "user@host.com";
};
Server to Server Protocol
-------------------------
As mentioned above, each server capable of remote klines passes
the capability KLN along. No server will send a KLINE to a server
without a KLN capability.
Server to server messages are formatted like this:
":oper KLINE target.server duration user host :reason"
Note the difference between hybrid-6 GLINE which explicitly passed
the oper user@host and server along. This was originally done to handle
possible desync conditions, but is now shelved in favor of saving
some bandwidth.
oper: the nick of the oper performing the kline
target.server: the server(s) this kline is destined for
duration: the duration if a tkline, 0 if permanent.
user: the 'user' portion of the kline
host: the 'host' portion of the kline
reason: the reason for the kline.

99
doc/messages.txt Normal file
View file

@ -0,0 +1,99 @@
Message Customization Overview
$Id: messages.txt,v 1.1 2002/08/13 14:35:21 fishwaldo Exp $
Copyright (c) 2001 by ircd-hybrid team
----------------------------------------------------------------------
Hybrid now supports gettext (provided in GNU gettext/libintl) to enable
easier customization of messages, allow message files to be changed at
runtime, and to provide pre-made translations.
This document is split into two parts, using message files, and creating
your own.
----------------------------------------------------------------------
Using Provided or Pre-made Message Files
There are a number of message files provided with Hybrid 7. These can be
found in the source tree in messages/ and messages/translations/.
The ircd will install custom.po and ayb.po upon a make install on systems
that configure finds a working gettext on. These will be installed into
the prefix directory under messages/. To install the provided
translations, you must change to the messages/translations directory in
the source tree. In this directory, you can run make install, and ircd
will install all of the translated .po's into messages/ in the prefix.
There is no way at the present time to install a single .po file.
These message files can be used in ircd once they are installed. Try the
installed message file with /quote SET MSGLOCALE <locale> first. Locale
will be 'standard' for the plain messages that are Hybrid's default. 'ayb'
and 'custom' are available on any installation that configure finds a
working gettext for. If the translations were installed, they can be set
by 'ircd-<language>', such as 'ircd-danish' or 'ircd-norwegian'.
If the desired message file works without any issues, it can be set to be
the default message file in the ircd.conf file. Refer to example.conf's
documentation on the message_locale setting.
----------------------------------------------------------------------
Creating Your Own Messages
This process is a little more complicated. The easiest way to start
editing messages is to take a file such as custom.po, make a copy, and
change whatever msgstr lines you wish.
Important: Please do NOT ever change msgid lines, as this will prevent
your customization from being used by gettext.
Once you have your customized message file ready, place it into messages/
in the source tree, and open Makefile.in in a text editor. Insert a line
in the middle of the SRCS line, for example right after or right before
custom.po. Place the name of your customized message file on this line,
followed by a \.
Example:
SRCS = \
custom.po \
new.po \
ayb.po
Since these directories are under configure's control, any Makefile
changes must be done to Makefile.in. This also requires configure to be
rerun with at minimum the prefix option.
You will now be able to cd into messages/ and run make install.
There is always a chance of creating a syntax error, but the benefit to
using gettext over Hybrid 6's src/messages_cust.tab is that syntax errors
will not break the compile of the server, just of the message file.
Creating a message file from scratch is relatively simple as well. cd into
messages/ and run ./create_po <name>.po. This command will generate a
blank message file, listing all of the ircd default message ID's, with no
replacements. Any message that you wish to keep the same as the ircd
defaults, you will leave the msgstr set to "". Any message that you wish
to change requires you to write a complete replacement for in msgstr.
Again, please do NOT change the msgid. The replacement string must contain
the same number of % arguments, and the arguments must be kept in the same
order.
Once your message file is complete, you must put it into Makefile.in as
described above. You must then rerun configure as described above. If the
default (standard locale) messages ever change in Hybrid, your file can be
updated with the make mrupdate command in the messages/ directory. Be sure
and have a backup of your old one first, as this sometimes will give
unusual entries in the .po files. Before attempting to use the updated
message file, you must read through the customized file and be sure that
it is correct.
If you create a translation for a new language, or an update to an
existing translation, please do not hesitate in sending the .po file to
the Hybrid team. Providing a translation will be a way that nearly anyone
who knows multiple languages to contribute to ircd, and get their name in
the translation credits.

140
doc/modeg.txt Normal file
View file

@ -0,0 +1,140 @@
User Mode +g Documentation
Hybrid 7 includes a new and power feature that all users can take advantage
of to help prevent flooding and unwanted messages. This new feature is
invoked by setting user mode +g. When a client is set +g, that user will
be in "Caller ID" mode. Any user that messages a +g client will receive
a notice saying that they are in +g (server side ignore) mode. The target
client (who is set +g) will also receive a notice saying that so and so
messaged them, and that they are in +g mode.
The target of the message will only receive one notification per minute, from
any client, in order to help prevent flooding. The sender will NOT have the
rate limit, and will receive a notice saying the target is in +g mode every
time they send a message. Note that this behavior is similar to the way AWAY
messages are done.
There are numerous benefits for both opers and regular users, including the
ability to stop spambot messages from ever reaching your client, stopping
private message and CTCP floods, and being able to sit on IRC in privacy.
One question that arises is how to message specific users, while blocking
out everyone else. The command ACCEPT is your answer. To add a user to
your accept list, issue the raw command ACCEPT <nick>,<nick>,<nick>,...
You will not receive a reply from the ACCEPT command if it is succesful,
only if an error has occured. There are three possible errors, shown by
numerics:
ERR_ACCEPTFULL (456): :irc.server 456 client :Accept list is full
- This is sent when an accept list is full.
ERR_ACCEPTEXIST (457): :irc.server 457 client target :already exists
- This is sent when a client tries to add a user to the accept list
that already exists there
ERR_ACCEPTNOT (458): :irc.server 458 client target :doesnt exist
- This is sent when a client tries to remove a user from their accept
list who is not on the accept list.
That user will now be able to send messages to your client until the
association is broken.
Associations break in one of the following situations: when an accepted user
QUIT's (or is on the other side of a split), you QUIT, or the accepted user
changes their nick. The reason why a remote user's nick change will remove
them from your accept list is so that you cannot track a user after they
changed their nick.
Viewing the accept list is also very easy. Issue the raw command ACCEPT *.
Removing a user from your accept list is also simple. Issue the command
ACCEPT -<nick>.
Sample Session
The easiest way to see how this works is by experiencing it. Seeing a sample
session can help understand what goes on though.
Client Hwy-LL is set +g initially.
Client Hwy101 wants to message Hwy-LL
Note that some clients may have to use /quote ACCEPT instead of /accept.
--
Client Hwy101: /msg Hwy-LL hi
Hwy101 will see: -Hwy-LL- *** I'm in +g mode (server side ignore).
-Hwy-LL- *** I've been informed you messaged me.
Hwy-LL will see: Client Hwy101 [wcampbel@admin.irc.monkie.org] is messaging
you and you are +g
The sender will receive the NOTICE from the target of the message, while
the recipient will receive the NOTICE from the server.
--
If Hwy101 sends another message to Hwy-LL (before the minute expires), he will
see: -Hwy-LL- *** I'm in +g mode (server side ignore).
and will not receive the second notice
Hwy-LL will NOT see any notice.
--
Hwy-LL now wishes to see messages from Hwy101 and SpamBot
Client Hwy-LL: /accept Hwy101,SpamBot
Neither side will be told of the change in the accept list, Hwy-LL should
presume that the accept was succesful if no error occurs.
Now Hwy-LL can see messages from Hwy101 and SpamBot without any blockage.
If Hwy101 was also set +g, then he would have to issue /accept Hwy-LL
before he would be able to see messages from Hwy-LL.
--
Hwy-LL now wants to see who is on his accept list.
Client Hwy-LL: /accept *
Hwy-LL will see:
irc.server 281 Hwy-LL Hwy101 SpamBot
irc.server 282 Hwy-LL :End of /ACCEPT list
The replies are in numeric form to help parsing by scripts.
--
Hwy-LL realises he added a spambot to his list, and wants to remove it, and
allow messages from services
Client Hwy-LL: /accept -SpamBot,services
Hwy-LL will now only accept messages from Hwy101 and services.
--
The nicks to be added can be in ANY order, however you cannot add or remove
AND list.
/ACCEPT x,y,-z,f,-a would be acceptable.
/ACCEPT x,y,-z,* would ignore the * and generate an invalid nick
response.
Like Dalnet and Undernet's SILENCE system, the accept list only exists while
you are connected to IRC. In order for you to have the same accept list
every time you come onto IRC, you must put the accept commands into your
client's auto-perform, or manually issue the commands each time.
This system may seem similar to the SILENCE system, but it is actually a
reverse SILENCE. SILENCE ignores certain users and allows the rest. Mode
+g ignores all users except certain ones (on your accept list.) Both systems
have their place, but the mode +g in Hybrid 7 is what the developers thought
would be most useful for clients.
The goals of this user mode is to provide protection from flooding and
spamming, and to provide users with a means to keep their privacy.
We hope that these goals are obtained.
--
W. Campbell
$Id: modeg.txt,v 1.1 2002/08/13 14:35:21 fishwaldo Exp $

57
doc/modes.txt Normal file
View file

@ -0,0 +1,57 @@
irc.corefailure.com hybrid-7beta5 oiwszcerkfydnxbaugl biklmnopstveIha bkloveIh
User Modes:
+a - admin - Admin status. Shown as an admin in WHOIS, able to
load and unload modules, and see IP's in STATS c
+b - bots - See bot and drone flooding notices
+c - cconn - Client connection/quit notices
+d - debug - See debugging notices
+f - full - See I: line full notices
+g - callerid - Server Side Ignore
+i - invisible - Not shown in NAMES or WHO unless you share a
a channel
+k - skill - See server generated KILL messages
+l - locops - See LOCOPS messages
+n - nchange - See client nick changes
+o - oper - Operator status
+r - rej - See rejected client notices
+s - servnotice - See general server notices
+u - unauth - See unauthorized client notices
+w - wallop - See server generated WALLOPS
+x - external - See remote server connection and split notices
+y - spy - See LINKS, STATS (if configured), TRACE notices
+z - operwall - See oper generated WALLOPS
Channel Modes:
+a - hideops - Anonymous ops, chanops are hidden
+b - ban - Channel ban on nick!user@host
+e - exempt - Exemption from bans
+h - halfop - Half op (%), can kick non ops, not full ops
+I - invex - Invite exceptions, nick!user@host does not need to be
explicitly INVITE'd into the channel before being able
JOIN
+i - invite - Invite only
+k - key - Key/password for the channel. VChans with a key can be
JOIN'ed with JOIN #vchanned-channel !vkey password
+l - limit - Limit the number of users in a channel
+m - moderated - Users without +v/h/o cannot send text to the channel
+n - noexternal - Users must be in the channel to send text to it
+o - chanop - Full operator status
+p - private - Private is obsolete, this now restricts KNOCK, and can be
set at the same time as +s. This will also prevents
halfops from setting +/-h.
+s - secret - The channel does not show up on NAMES or LIST or in the
WHOIS channel list unless you are a member of the channel
+t - topic - Only chanops can change the topic
+v - voice - Can speak in a moderated channel, and is exempt from flood
restrictions
The third part of the 004 numeric lists channel modes that require arguments.
Currently these are bkloveIh.
Note that most of the channel modes can be disabled in the conf file for
networks that do not wish to support them.
# $Id: modes.txt,v 1.1 2002/08/13 14:35:22 fishwaldo Exp $

137
doc/old/Authors Normal file
View file

@ -0,0 +1,137 @@
/************************************************************************
* IRC - Internet Relay Chat, doc/AUTHORS
* Copyright (C) 1990
*
* AUTHORS FILE:
* This file attempts to remember all contributors to the IRC
* developement. Names can be only added this file, no name
* should never be removed. This file must be included into all
* distributions of IRC and derived works.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 1, or (at your option)
* any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
IRC was conceived of and written by Jarkko Oikarinen <jto@tolsun.oulu.fi>.
IRC was originally written in University of Oulu, Computing Center.
Jan 1991 - IRC 2.6 jto@tolsun.oulu.fi
- Multiple Channels and protocol changes
Contributions were made by a cast of dozens, including the following:
Markku Jarvinen <mta@tut.fi>: Emacs-like editing facility for the client
Kimmo Suominen <kim@kannel.lut.fi>: HP-UX port
Jeff Trim <jtrim@orion.cair.du.edu>: enhancements and advice
Vijay Subramaniam <vijay@lll-winken.llnl.gov>: advice and ruthless publicity
Karl Kleinpaste <karl@cis.ohio-state.edu>: user's manual
Greg Lindahl <gl8f@virginia.edu>: AUTOMATON code, the Wumpus GM automaton,
myriad bug fixes
Bill Wisner <wisner@hayes.fai.alaska.edu>: numerous bug fixes and code
enhancements
Tom Davis <conslt16@zeus.unl.edu> and Tim Russell <russell@zeus.unl.edu>:
VMS modifications
Markku Savela <msa@tel4.tel.vtt.fi>: advice, support, and being the
incentive to do some of our *own* coding. :)
Tom Hopkins <hoppie@buengf.bu.edu>: bug fixes, quarantine lines,
consolidation of various patches.
Christopher Davis <ckd@cs.bu.edu>: EFnet/Anet gateway coding,
many automata ;), documentation fixing.
Helen Rose <hrose@cs.bu.edu>: documentation updating, and fixing.
Tom Hinds <rocker@bucsf.bu.edu>: emacs client updating.
Tim Miller <cerebus@bu-pub.bu.edu>: various server and client-breaking
features.
Darren Reed <avalon@coombs.anu.edu.au>: various bug fixes and enhancements.
Introduced nickname and channelname hash tables into the server.
The version 2.2 release was coordinated by Mike Bolotski
<mikeb@salmon.ee.ubc.ca>.
The version 2.4 release was coordinated by Markku Savela and
Chelsea Ashley Dyerman
The version 2.5.2 release was coordinated by Christopher Davis, Helen Rose,
and Tom Hopkins.
The versions 2.6.2, 2.7 and 2.8 releases were coordinated by Darren Reed.
Contributions for the 2.8 release from the following people:
Matthew Green <phone@coombs.anu.edu.au>
Chuck Kane <ckane@ece.uiuc.edu>
Matt Lyle <matt@oc.com>
Vesa Ruokonen <ruokonen@lut.fi>
Markku Savela <Markku.Savela@vtt.fi> / April 1990
Fixed various bugs in 2.2PL1 release server (2.2msa.4) and changed
sockets to use non-blocking mode (2.2msa.9). [I have absolutely
nothing to do with clients :-]
Chelsea Ashley Dyerman <chelsea@earth.cchem.berkeley.edu> / April 1990
Rewrote the Makefiles, restructuring of source tree. Added libIrcd.a to
the Makefile macros, numerous reformatting of server text messages, and
added mkversion.sh to keep track of compilation statistics. Numerous
bug fixes and enhancements, and co-coordinator of the 2.4 release.
jarlek@ifi.uio.no added mail functions to irc.
Armin Gruner <gruner@informatik.tu-muenchen.de> / May, June 1990:
* Patched KILL-line feature for ircd.conf, works now.
Enhancement: Time intervals can be specified in passwd-field.
Result: KILL-Line is only active during these intervals
* Patched PRIVMSG handling, now OPER can specify masks for sending
private messages, advantage: msg to all at a specified server or host.
* Little tests on irc 2.5 alpha, fixed some little typos in client code.
Change: common/debug.c has been moved to ircd/s_debug.c, and a
irc/c_debug.c has been created, for the benefit that wrong server msg
are displayed if client does not recognize them. (strange, if a server
sends an 'unknown command', isn't it?)
Tom Hopkins <hoppie@buengf.bu.edu> / September, October 1990:
* Patched msa's K lines for servers (Q lines).
* Consolidated several patches, including Stealth's logging patch.
* Fixed several minor bugs.
* Has done lots of other stuff that I can't seem to remember, but he
always works on code, so he has to have done alot more than three
lines worth. :)
Thanks go to those persons not mentioned here who have added their advice,
opinions, and code to IRC.
Various modifications, bugreports, cleanups and testing by:
Hugo Calendar <hugo@ucscb.ucsc.edu>
Bo Adler <adler@csvax.cs.caltech.edu>
Michael Sandrof <ms5n+@andrew.cmu.edu>
Jon Solomon <jsol@cs.bu.edu>
Jan Peterson <jlp@hamblin.math.byu.edu>
Nathan Glasser <nathan@brokaw.lcs.mit.edu>
Helen Rose <hrose@eff.org>
Mike Pelletier <stealth@caen.engin.umich.edu>
Basalat Ali Raja <gwydion@tavi.rice.edu>
Eric P. Scott <eps@toaster.sfsu.edu>
Dan Goodwin <fornax@wpi.wpi.edu>
Noah Friedman <friedman@ai.mit.edu>

84
doc/old/Etiquette Normal file
View file

@ -0,0 +1,84 @@
/************************************************************************
* IRC - Internet Relay Chat, doc/etiquette
* Copyright (C) 1990, Lea Viljanen and Ari Husa
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 1, or (at your option)
* any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
HOW TO BEHAVE ON IRC
Authors: Lea Viljanen (LadyBug) viljanen@kreeta.helsinki.fi
Ari Husa (luru) so-luru@tolsun.oulu.fi
1) Language
The most widely understood and spoken language on IRC is English.
However! As IRC is used in many different countries, English is by
no means the only language. If you want to speak some other language
than English (for example with your friends), go to a separate channel
and set the topic (with /topic) to indicate that. For example
/topic Finnish only!
would mean that this channel would be reserved for Finnish discussion.
On the other hand, you should check the topic (with /list command)
before you move to a channel to see if there are any restrictions about
language.
On a channel not restricted by /topic, please speak a language
everybody can understand. If you want to do otherwise, change channels
and set the topic accordingly.
2) Hello/Goodbye
It's not necessary to greet everybody on a channel personally.
Usually one "Hello" or equivalent is enough. And don't expect everybody
to greet you back. On a channel with 20 people that would mean one
screenful of hellos. It's sensible not to greet, in order not to be rude
to the rest of the channel. If you must say hello, do it with a private /msg.
The same applies to goodbyes.
3) Discussion
When you come to a new channel it's advised you to listen
for a while to get an impression of what's discussed. Please feel free
to join in, but do not try to force your topic into the discussion
if that doesn't come naturally.
4) {}|[]\
IRC has quite a lot of people from Scandinavian countries,
the above characters are letters in their alphabet. This
has been explained on IRC about a thousand and one times, so
read the following, do not ask it on IRC:
{ is an A with 2 dots over it
} is an A with a small circle above it
| is either an O with 2 dots over it or an O with a dash (/) through it
[, ], and \ are the preceding three letters in upper case.
There are a lot of people from Japan as well, who use Kanji characters
which may look quite exotic as well. As I don't know Kanji I don't
even try to explain any of the characters.
5) ATTENTION!
Remember, people on IRC form their opinions about you only by
your actions, writings and comments on IRC. So think before you type.
Do not "dump" to a channel or user (send large amounts of unwanted
information). This is likely to get you /kicked off the channel or
/killed off from irc. Dumping causes network 'burbs', connections going
down because servers cannot handle the large amount of traffic any more.

8
doc/old/README Normal file
View file

@ -0,0 +1,8 @@
This stuff is so ancient it's not even funny anymore. Take it with
a grain of salt when you read it. --JRL
The Bill Wisner example.conf has been updated, I have also included
Helen Roses example.conf as example.conf.trillian (taken from
the CSR tree ) as it is superiour in some respects to Bill's version.
Updated as well to reflect hybrid . --Dianora

212
doc/old/US-Admin/Networking Normal file
View file

@ -0,0 +1,212 @@
/************************************************************************
* IRC - Internet Relay Chat, doc/NETWORKING
* Copyright (C) 1990, Helen Rose
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 1, or (at your option)
* any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
Author: Helen Rose
hrose@cs.bu.edu
Date: 10 Oct 1990
*** Please read this before doing any connecting or writing to ask for
connections. The information contained in this section is crucial to the
way IRC is run.
In August of 1990, IRC suffered a critical split in viewpoints of key
people in the IRC heirarchy. The result was IRC split into two networks,
EFnet (Eris Free network) and Anet (Anarchy network). This split continues
today. There is some debate over whether IRC will ever reunite, however,
neither side is willing to bend from their standpoint.
Below is a paragraph from each side, listing their viewpoints on why their
respective net is "better" than the other. Please read these, and decide
for yourself which is the better network. Currently, there are about 95
servers on EFnet (and the same number of users) and 15 servers on Anet (and
about half the number of users).
Anet
====
joshua@coombs.anu.edu.au
(DCLXVI == Josh Geller)
Arguments in favor of joining Anet include stabler links, ease of
connecting (just connect your server to eris.berkeley.edu; if you decide
later you wish to be on EFnet you merely have to add whatever patches are
required and get a link from the appropriate EFnet server), no likelihood
of regulation of numbers of servers (there has been some talk of limiting
the number of servers on EFnet).
EFnet
*===*
ckd@cs.bu.edu, hrose@cs.bu.edu
(ckd = Christopher Davis, Trillian = Helen Rose)
Arguments in favor of joining EFnet are virtually limitless. From a
redundant backbone plan (which assures everyone of getting a close,
fast link and tries to keep traffic off of long haul networks) to the
fact that the obvious security hole that exists with open-server servers
does not exist. (Anyone running an open server allows any user with
telnet access to crash the server's machine without too much work.)
---real networking document---
Throughout this document every effort will be made to apply to *BOTH* ANet
and EFnet. If this is not possible, EFnet will be referred to, considering
it is the side where the majority is located.
Anet has one network coordinator:richardt@legato.com. Mail to him for all
correspondence. At this time, no backbone layouts have been published for
Anet.
EFnet is coordinated in several areas:
ckd@cs.bu.edu and hrose@cs.bu.edu coordinate the US routing. They also
coordinate all incoming connections to the US. If you are in the United
States and need a link, please mail to "operlist-request@cs.bu.edu"
supplying the information listed below.
savela@tel.vtt.fi, irc@tolsun.oulu.fi, and d88-skl@nada.kth.se coordinate
the NORDUnet connections. (msa, WiZ, and meLazy on irc, respectively)
muts@fysak.fys.ruu.nl coordinates Dutch servers.
stumpf@Informatik.TU-Muenchen.de and Gruner@Informatik.TU-Muenchen.de
coordinate German servers. (Maex and Armin/Gonzo)
phil@cnam.cnam.fr coordinates the one French IRC server, and any others
that might want be started.
avalon@coombs.anu.oz.au coordinates the Australian servers.
bowles@is.s.u-tokyo.ac.jp coordinates the Japanese servers.
==how to get an IRC connection==
(1) If you are in the United States and on Anet, mail to
richardt@legato.com.
(2) If you are in the United States and on EFnet:
a) find out if your system has /etc/ping (sometimes /usr/etc/ping)
and ping the following hosts-
server/machine name IP Address Geographical Location
bucsd.bu.edu 128.197.10.2 Boston, MA
irc.mit.edu 18.70.0.224 Cambridge, MA
poe.acc.virginia.edu 128.143.20.20 Charlottesville, VA
sindri.cs.cornell.edu 128.84.254.96 Ithaca, NY
polaris.ctr.columbia.edu 128.59.64.79 New York City, NY
fairhope.andrew.cmu.edu 128.2.11.213 Pittsburgh, PA
*.umich.edu 141.212.66.36 Ann Arbor, MI
h.ece.uiuc.edu 128.174.115.18 Urbana-Champaign, IL
minnie.cc.utexas.edu 128.83.135.13 Austin, TX
ucsu.colorado.edu 128.138.129.83 Boulder, CO
badger.ugcs.caltech.edu 131.215.128.29 Pasadena, CA
*.spies.com 130.143.3.3 Cupertino, CA
*.washington.edu 128.95.152.35 Seattle, WA
(yes, this seems like alot, but the backbone structure is quite complex and
redundant so when we have a network break, servers can pick up other
servers within moments)
b) a simple ping hostname (or ping IP address) will suffice. Ping the
five geographically closest machines. Let the ping run for 100 packets.
This allows the network coordinators to best evaluate your position
on the network and to give you a connection that is fastest.
Note: when using the SunOS version of ping, use ping -s machinename;
"regular" SunOS ping is useless.
c) mail these results to operlist-request@cs.bu.edu requesting a link.
(3) If you are in Europe and are requesting a link, mail to the
appropriate contact listed above, and they will instruct you on how to
secure a link for your server.
These are the results of the typical /etc/ping command:
(note that since bucsd.bu.edu runs SunOS, I used ping -s...)
bucsd% /usr/etc/ping -s betwixt.cs.caltech.edu
PING betwixt.cs.caltech.edu: 56 data bytes
64 bytes from betwixt.cs.caltech.edu (131.215.128.4): icmp_seq=0. time=169. ms
64 bytes from betwixt.cs.caltech.edu (131.215.128.4): icmp_seq=1. time=190. ms
64 bytes from betwixt.cs.caltech.edu (131.215.128.4): icmp_seq=2. time=200. ms
64 bytes from betwixt.cs.caltech.edu (131.215.128.4): icmp_seq=3. time=170. ms
[...]
64 bytes from betwixt.cs.caltech.edu (131.215.128.4): icmp_seq=18. time=180. ms
64 bytes from betwixt.cs.caltech.edu (131.215.128.4): icmp_seq=19. time=220. ms
64 bytes from betwixt.cs.caltech.edu (131.215.128.4): icmp_seq=20. time=170. ms
64 bytes from betwixt.cs.caltech.edu (131.215.128.4): icmp_seq=21. time=200. ms
^^ ^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^ ^^ ^^^^^^^
Size of packet hostname IP address packet number trip time
----betwixt.cs.caltech.edu PING Statistics----
22 packets transmitted, 22 packets received, 0% packet loss
round-trip (ms) min/avg/max = 160/179/220
When you send pings to operlist-request, please only send the results
(the above three lines)--we *don't* need each packet's time.
Guidelines:
Avg Time Connection is
======== =============
20-50 ms Optimal
50-80 ms Excellent
80-120 ms Very Good
120-180 ms Average
180-240 ms Acceptable
240-300 ms Below Average
300-400 ms Bad
400+ ms Find a better link, if possible
** *** WHERE TO FIND HELP!!! ***
**
** If you have any other questions about connecting to an irc server, please
** mail to operlist-request@cs.bu.edu. If you have problems mailing there,
** try mailing hrose@cs.bu.edu or ckd@cs.bu.edu.
**
** *** WHERE TO FIND HELP!!! ***
If you are in need of further help, you may find it by using your IRC
client, entering IRC, and sending a /wallops. Be sure to read the help
information on /wallops before doing so. Please use /wallops for IRC
questions or help only, and not for questions like "have you seen nicky
I need to talk to him". /wallops with care, or you will be annoying
every operator on IRC.
Appendix
========
Open client servers
Until such a time that your server becomes connected, you should use your
irc client and connect to open client servers. Some of these servers are-
irc.mit.edu
bucsd.bu.edu
fairhope.andrew.cmu.edu
hermes.tcad.ee.ufl.edu
mingin.engin.umich.edu
minnie.cc.utexas.edu
badger.ugcs.caltech.edu
ucsu.colorado.edu
dharma.cpac.washington.edu
fysak.fys.ruu.nl
nic.funet.fi
coombs.anu.edu.au
Start up your irc client, and then type /help for help.
Happy IRC'ing!

253
doc/old/US-Admin/Operators Normal file
View file

@ -0,0 +1,253 @@
Internet Relay Chat Operator Etiquette Guide
January, 1991
Welcome! You've either been selected to be an IRC Operator or you have set
up your server and thus have taken on the dual task of IRC Server
Administrator and IRC Operator. Your future days will be filled with hours
of fun chatting on IRC, and then wondering why everyone you talked to went
away, because the links had apparently broken.
Linking:
========
You will be assigned links from the IRC Routing Coordinators. Please use
these links and these links ONLY. The links have been designed to maximize
efficiency and make delays in chatting minimal. You will be given two
links, one to each regional backbone site. Connect to the primary site
first and then to the secondary site. You should not need to connect to any
other sites. You will be informed if this policy changes.
Kills and Walls:
===============
/kill and /wall are special operator commands. You should use them with
care, and only if absolutely needed. The format are as follows:
/kill USERNAME comment. comment can be a phrase of almost any length
(within reason) and should be used for specifying the reason of the kill.
example: /kill Trillian She's a Ghost
IRC Ghosts are created after a net split has occured and the net has yet to
relink.
/wall PHRASE. This is used for an emergency command like the net is about
to split into little pieces, and everyone should reconfigure their links
as soon as possible. You will see a WALL when it happens, an operators
nickname will appear with # signs around it.
#Trillian# Server bucsd.bu.edu coming down for upgrade. Prepare to
reconfigure links.
/wallops PHRASE This is used to talk to ALL operators at once. It is not
often warranted, but is useful. Often, when there is an important IRC
situation that requires all the operators attention, /wallops is used. The
form for wallops is a nickname with ! signs around it.
!Trillian! Australia should leaf off of eris, not carry all the US traffic.
/TRACE command
/TRACE is useful to know what servers are connected to what. Sometimes
/trace can be confusing, especially you are using it for the first time.
Here is an example of a trace from bucsd.bu.edu to betwixt.cs.caltech.edu.
/TRACE betwixt.cs.caltech.edu
IRC log started Mon Aug 26 17:04
*** Link eff.org<2.6.1a> ==> h.ece.uiuc.edu
-bucsd.bu.edu- *** Link bucsd.bu.edu<2.6.1a> ==> h.ece.uiuc.edu
-h.ece.uiuc.edu- *** Serv Class[3] h.ece.uiuc.edu ==> ucsu.colorado.EDU
-h.ece.uiuc.edu- *** Serv Class[2] h.ece.uiuc.edu ==> bucsd.bu.edu
-h.ece.uiuc.edu- *** Serv Class[10] h.ece.uiuc.edu ==> silver.ucs.indiana.edu
-h.ece.uiuc.edu- *** Serv Class[11] h.ece.uiuc.edu ==> monitor.ece.uiuc.edu[h.ece.uiuc.edu]
-h.ece.uiuc.edu- *** User Class[0] h.ece.uiuc.edu ==> Razorbone[uxa.cso.uiuc.edu]
-h.ece.uiuc.edu- *** Serv Class[10] h.ece.uiuc.edu ==> MHD54.MOORHEAD.MSUS.EDU[134.29.97.1]
-h.ece.uiuc.edu- *** Serv Class[4] h.ece.uiuc.edu ==> *.umich.edu[mingin.engin.umich.edu]
-h.ece.uiuc.edu- *** User Class[0] h.ece.uiuc.edu ==> BooServ[sunc4.cs.uiuc.edu]
-h.ece.uiuc.edu- *** Serv Class[10] h.ece.uiuc.edu ==> nic.stolaf.edu
-h.ece.uiuc.edu- *** Oper Class[0] h.ece.uiuc.edu ==> SodaPop[h.ece.uiuc.edu]
-h.ece.uiuc.edu- *** Serv Class[4] h.ece.uiuc.edu ==> oddjob.uchicago.edu
-h.ece.uiuc.edu- *** User Class[0] h.ece.uiuc.edu ==> Deviant[isca01.isca.uiowa.edu]
-h.ece.uiuc.edu- *** Serv Class[10] h.ece.uiuc.edu ==> *.uc.edu[hilbert.che.uc.edu]
-h.ece.uiuc.edu- *** Class 0 Entries linked: 4
-h.ece.uiuc.edu- *** Class 11 Entries linked: 1
-h.ece.uiuc.edu- *** Class 10 Entries linked: 4
-h.ece.uiuc.edu- *** Class 4 Entries linked: 2
-h.ece.uiuc.edu- *** Class 3 Entries linked: 1
-h.ece.uiuc.edu- *** Class 2 Entries linked: 1
This shows that from eff.org (running version 2.6.1a to h.ece.uiuc.edu,
routing goes through bucsd.bu.edu before reaching h.ece.uiuc.edu.
"h" is connected to ucsu.colorado.edu, silver.ucs.indiana.edu,
monitor.ece.uiuc.edu (which resolves to [h.ece.uiuc.edu], hence the
square brackets), mhd54.moorhead.msus.edu, *.umich.edu (which resolves
to mingin.engin.umich.edu), nic.stolaf.edu, oddjob.uchicago.edu,
*.uc.edu (which resolves to hilbert.che.uc.edu), and bucsd.bu.edu, which
is known as its "uplink". It is quite normal for a server to have
several "uplinks" if it is busy. An uplink is the link towards the top
of the tree which carries alot of traffic. "h" also has several users on
it, RazorBone, BooServ, and Deviant. SodaPop is also an active operator
on h.ece.uiuc.edu. You can tell each host from what each person is
logged into by looking just past their nickname. For example, Deviant is
logged in from isca01.isca.uiowa.edu.
/SQUIT server {comment}
/squit isolates a specified link from the next closest uplink server.
This is usually used in conjunction with CONNECT (explained later) to
reroute traffic. This will be described in detail in the section
"routing", preceding CONNECT.
SQUIT can be used in one of two ways. It can be used on a local
server, which would cause the server name specified to be unlinked
relative to your path; or you can send a message to another server
instructing it to issue an SQUIT to that server, in which case the
break will be relative to the remote server.
Usage (and examples):
/squit E
If the network looks like this initially (and you are on server A)
A <---> B <---> C <---> D
^
|
v
G <---> E <---> F <---> ... (rest of the net)
Then after issuing the previous /squit the network would look like this:
A <---> B <---> C <---> D
G <---> E <---> F <---> ...
/squit E {comment}
It usually helps to give a reason why you are sending a
SQUIT for a server. This can be accomplished by sending
the command "/squit server This link is making the US route
through Finland". The SQUIT will then be sent out, and the
server sending the squit will WALLOP sending the comment
so all operators can see it.
/CONNECT server {portnum server2}
/connect is used to establish a link between two servers. These
connections must be authorized by each server's ircd.conf file, but
any operator can issue a CONNECT between authorized servers. This
command is most often used in conjunction with SQUIT to reroute
traffic.
If only one argument is given, this command causes the server you
are on to attempt to connect to the server specified. For example,
"/connect B" (in the previous example) would cause your server (A) to
connect to B.
Suppose you wanted to reconnect server F to server E? You cannot
contact server F since it is no longer part of your network. However,
you can tell server E to connect to it. A remote CONNECT can be issued
to server E.
Examples (assume you are on server A):
/connect B
If the network initially looks like this:
A B <---> ... (rest of network)
Then afterwards (if the connection succeeds) the network will look
like this:
A <---> B <---> ...
In the example where you wanted to reconnect server E to F, the
following syntax would be appropriate (note: we are assuming that
F's irc socket port is 6667, which is the default)
/connect F 6667 E
If the network initially looks like this:
A <---> B <---> C <---> D
^
|
v
G <---> E F <---> ...
Then after your CONNECT request the network topology will look like this:
A <---> B <---> C <---> D
^
|
v
G <---> E <---> F <---> ...
Be careful when connecting servers that you know which command to
use! If you simply issued "/connect F" from your server, the
network would look like this:
... <---> F <---> A <---> B <---> C <---> D
^
|
v
G <---> E
which for various reasons (discussed below) might be very
undesirable.
Routing
=======
When and how should you do rerouting? This depends on where your
server is topologically located and whether you route traffic. If you
are a leaf node (i.e. only connect to one server at a time) then
chances are you won't need to do any routing at all. Your ircd.conf
file should be written to connect to the best possible servers first
before trying alternates. At the most, you may decide to squit an
alternate server and connect to your primary if/when it goes back up.
This only involves local squits, however.
If you are operating a backbone site, you may find yourself
rerouting things quite often. If the EFnet servers (see the file
doc/networking) badger.ugcs.caltech.edu (Pasadena, CA),
irc.mit.edu (Boston, MA), minnie.cc.utexas.edu (Austin, TX) and
ucsu.colorado.edu (Boulder, CO) were routing traffic in the following way:
... <---> minnie <---> badger <---> bucsd <---> ucsu <---> ...
It would make sense to either squit ucsu and reconnect it to minnie,
or disconnect minnie from badger and connect to ucsu, because
topologically (and geographically) ucsu and minnie are rather close.
There are occasions when US traffic for some reasons winds up being
routed through Australia. This is another case where traffic should
definitely be rerouted. However, there are sometimes occasions when
routing is going through "backdoor" methods. If you see something
totally outrageous (like the east coast and the west coast being
connected by eff.org) please /WALLOPS and ask before you send any
squits, because chances are, it's like that for a reason.
Of course, any operator can remotely squit or connect servers, so
if you see a problem and you're sure you know how to fix it, it's a
good idea to do so. If the operator of a server which is is being
routed poorly is online, it's probably best to contact him/her first,
though.
Chances are that hub operators will be more familiar with the
general topology of the network and which servers connect to which
(which is why most of the manual routing is left to them), so if you
have any problems, talk to the other operators via /wallops. That's
what it's there for!
Also, be aware that servers will notify all the operators online of
remote SQUITs and CONNECTs via WALLOPS.
Please let us know if there should be any additions to this guide. Again,
this is not MANDATORY, this is just a GUIDE. Please conduct yourself as
an IRC Operator would...you are looked upon for assistance, both emotional
and mental.
Helen Rose Christopher Davis
<hrose@cs.bu.edu> <ckd@cs.bu.edu>
Noah Friedman
<friedman@ai.mit.edu>
January, 1991

3
doc/old/US-Admin/README Normal file
View file

@ -0,0 +1,3 @@
This stuff is so ancient it's not even funny anymore. Take it with
a grain of salt if you bother to read it.

View file

@ -0,0 +1,369 @@
# IRC - Internet Relay Chat, doc/example.conf
# Copyright (C) 1994, Helen Rose
##
## updated by Diane Bruce Dec 19 1997, aka db or Dianora
## My changes will be shown in ## marks
##
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 1, or (at your option)
# any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
#
# This is an example configuration file for the IRC server
#
# You only need an ircd.conf (IRC server configuration file) if you are
# running an IRC server. If you are running a standalone client this file
# is not necessary.
#
# This file will explain the various lines in the IRC server
# configuration file. Not all lines are mandatory. You can check to make
# sure that your configuration file is correct by using the program
# "chkconf", provided in the server distribution (and when you do "make
# install" this program will be installed in the same directory as the irc
# server).
#
# The options for whether a line is needed or not are:
# MANDATORY: you absolutely MUST have this line
# NETWORKED: you must have this line if you are connecting this irc
# server to any other server (servers can run standalone).
# SUGGESTED: it is highly suggested that you use this line
# OPTIONAL: it's completely up to you whether to define this or not
# DISCOURAGED: you really really should not use this line if at all
# possible.
# NOT NECESSARY: an old or out of date line that isn't needed.
#
# MANDATORY lines are absolute *musts*, that is, if you do not have this
# line then your server will not work properly. SUGGESTED lines are
# close-to-mandatory (that is, the server will run without it, but you are
# highly encouraged to use these lines).
#
# Note that "*" in a field indicates an "unused" field.
#
#
# ========================================================================
# NOTE! this entire configuration file is read UPSIDE-DOWN! So if you have
# to put something in a specific order (for example, client-connection
# lines), put them in reverse order!
# ========================================================================
#
#
# M: [MANDATORY]. This line sets your server's name, description, and
# port number. Fields, in order, are:
#
# M:hostname:*:Description Of Your Server:6667
#
M:csa.bu.edu:*:Boston University Computer Science Department:6667
#
# A: [MANDATORY]. This line lists your administrative information
# (contact address, etc). To view this information, /admin (server) will
# show it to you.
#
# The A: line has no set information, in fact, you can put arbitrary text
# in there if you wish (it is encouraged that you put at *least* a contact
# address for a person responsible for the irc server, however)
#
A:Boston University CS Department:Main Client Server:Helen Rose <hrose@cs.bu.edu>
#
# Y: [SUGGESTED]. These lines define connection classes. Connection
# classes allow you to fine-tune your client and server connections. It is
# suggested that clients and servers be placed in seperate classes, and if
# you have lots of server connections (if you do have lots of servers you
# shouldn't be reading this file :-) each set of servers (defined
# arbitrarily by you) should have its own class. If you have clients
# coming in from lots of different sites, you may want to seperate them
# out into classes. For instance, you may want to put local users in one
# class, with remote users in another class.
#
# The class numbers are not arbitrary. In auto-connecting servers -- that
# is, servers that you have a port number (e.g. 6667) on the end of the C:
# line (see below) the higher the number the higher the priority in
# auto-connecting.
#
# The fields in order are: class number, ping frequency (in seconds),
# connect frequency (in seconds), maximum number of links (used for
# auto-connecting, and for limiting the number of clients in that class),
# and sendq (this overrides any value set in include/config.h for #define
# MAXSENDQLENGTH).
#
# Note that it is a good idea to have ping frequency the same at both ends
# of the link.
#
# in this case, connect-frequency is 0 indicating that this is a client
# class (servers never connect to clients, it is the other way around).
Y:1:90:0:20:100000
#
##
## in the case of hybrid and Csr servers, the connect-frequency
## field is now used as a count of number of clients to allow per IP
## (or in the case of CSr the number of clients per IP or clients per
## idented host; soon to be in Hybrid as well :-) )
## i.e. to limit one set of I lines to 1 client connection per IP
##
##Y:1:90:1:20:100000
## -db
##
#
# this is a normal server connection (normal as of March, 1994)
Y:2:90:300:1:600000
#
Y:10:90:0:3:100000
#
# I: [MANDATORY]. The I: lines are client-authorization lines. Without
# these lines, no clients will be able to connect to your server.
# Wildcards ("*") are permitted. Passwords are also permitted (clients can
# be configured to send passwords).
#
# Ident (for more information on this, see rfc1413) can also be used by
# placing a @ in the appropriate fields.
#
# Fields are as follows:
# I:IP-address-mask:optional password:domain-mask::connection class (opt)
#
# With a password..... This will allow anyone from anywhere to connect
# as long as they know the password ("foobar"). Note listing this I: line
# first, it will be read *last*, meaning it is the "fall-through". That
# is, anyone who doesn't match the I: lines listed below must know the
# password ("foobar") to connect.
#
I:*@*:foobar:*@*::1
# This is a standard vanilla I: line which will permit anyone with an IP
# address starting with 128.197 OR with a hostname ending in .bu.edu to
# connect to the server. NOTE, the ircd matches on the *right-most* match,
# so if I connect as hrose@csa.bu.edu (which is hrose@128.197.10.3) I will
# show up on irc as hrose@csa.bu.edu since that is the first match it
# found. (Even though the second match is valid).
I:128.197.*::*.bu.edu::1
#
# using ident
I:*@128.197.*::*@*.bu.edu::1
# and you can even specify just certain usernames running ident (as long
# as the client's site is running the ident daemon):
I:NOMATCH::hrose@csa.bu.edu::1
# putting NOMATCH in the first field will stop the ircd from matching
# automatically against the IP address and it will force the server to
# match against the hostname. (the "NOMATCH" string is not mandatory, you
# can use any arbitrary text in the first field).
#
#
# O: [OPTIONAL]. These lines define operator access. You do not need to
# have an operator to run a server. A well configured leaf site should not
# need an operator online, if it's connections are well defined, the irc
# administrator can use kill -HUP on the ircd to reload the configuration
# file.
##
## *sigh* unfortunately, O lines are now pretty mandatory
## in a modern EFnet
## -db
##
# The fields are as follows:
# O:hostname (ident "@" permitted):password:NickName
# if the person in "NickName" is not coming from the hostname defined in
# the first field then the person will get the error message "No O: lines
# for your host".
# NOTE that since Crypted Passwords are defined by default in
# include/config.h this text probably will not be plaintext. See
# ircd/crypt/README for more information.
#
O:*.bu.edu:Zaphod:Trillian::10
#
# and this line forces ident:
O:hrose@csa.bu.edu:Zaphod:Trillian::10
#
# This line is a "local operator", it is specified with a lower-case "o"
# -- it is the only lower-case type in the ircd.conf file.
#
# this line permits the nickname "jhs" with the password of "ITBites" to
# be a local operator only (be able to issue commands locally -- can /kill
# and /squit and /connect -- but *only* locally)
#
o:*.bu.edu:ITBites:jhs::10
#
# a crypted password line (NOTE that if you have crypted passwords, *all*
# of you passwords must be crypted! In fact, if you are getting an error
# "Incorrect Password" it may well be because crypted passwords are
# defined and you have used plaintext. So my example of plaintext and
# crypted strings in the same IRC server configuration file is an
# impossibility (but it is just theoretical, which is why I explained both).
#
O:rocker@csa.bu.edu:T0eiVgHrqeKTQ:Rocker::10
#
# U: [NOT NECESSARY]. This line defines the default server for the IRC
# client that ships with the server -- the default client is in irc/irc
# You should not use U: lines but instead use the UPHOST definition in
# include/config.h
U:csa.bu.edu:foobar:csa.bu.edu
##
## U lines are now obsolete in hybrid. ignore.
## - db
##
#
# The host part of C/N lines MUST contain a valid hostname or IP address
# The host part in the C:line MUST be identical to the host part in the N:line
# The name part of the C/N lines MUST match the associated H/L line name
#
# C: [NETWORKED]. These lines define what servers your server tries to
# connect to.
# N: [NETWORKED]. These lines define what servers your server permits
# connections to be initiated from.
# C/N lines MUST be used in pairs. You cannot have one without the other.
#
# C: lines contain the following fields:
# C:remote server's hostname:passwd:remote server's name:port:conn class
# (connection class)
# N: lines contain the following fields:
# N:remote server's hostname:passwd:remote server's name:host mask:conn class
# (connection class)
# "host mask" is the number of parts in *your* hostname to mask to. For
# instance, with my servername being "csa.bu.edu", if I wanted to present
# my servername to be "*.bu.edu" I would have a host-mask portion of "1".
#
# it is *strongly* advised that your C/N line passwords be different for
# security's sake.
#
# ident is allowed in the server's hostname part of the field.
# these lines tell the server to automatically (note the port number, that
# means automatic connection) connect to cs-ftp.bu.edu:
C:hrose@cs-ftp.bu.edu:bigspark:cs-ftp.bu.edu:6667:2
N:hrose@cs-ftp.bu.edu:bigalpha:cs-ftp.bu.edu::2
#
# This server's connection lines are more vanilla, masking the host to
# *.bu.edu (as described above):
C:irc-2.mit.edu:camelsrk00l:irc-2.mit.edu::2
N:irc-2.mit.edu:andsoarellamas:irc-2.mit.edu:1:2
#
# K: [OPTIONAL]. These lines define user@host patterns to be banned from
# this particular server (with an optional time field). Note that K: lines
# are *not* global, and if you ban a user they can still use any other IRC
# server (unless they have specifically been banned there as well).
#
# the fields are defined as:
# K:hostmask:time field:username
# wildcards are permitted in any one of the fields, in other words, you can
# K:*::* if you wanted (but your server wouldn't be used much ;-)
#
# This K: line bans the username "FSSPR" (the wildcards are used to make
# sure that any ident-checking character will match) on any machine from
# the University of Alaska.
K:*.alaska.edu::*FSSPR*
#
# This K: line bans any users from acs*.bu.edu between the hours of 8am
# and 12pm and 1pm and 5pm (the time is always the server's local time):
K:acs*.bu.edu:0800-1200,1300-1700:*
# Note that 24 hour time is used (no "AM" or "PM").
#
# R: [DISCOURAGED]. These lines restrict user access based on a more
# stringent checking system than is available in the K: line. It looks for
# a match (based on hostname and username) and then runs an outside
# program (which MUST be specified using a full pathname). The output of
# the program should be a string in the form "Y <message>" (which permits
# access for the user) or "N <message>" (which denies access for the
# user). If "Y <message>" is received by the server, the server ignores
# the message and permits access for the user. If "N <message>" is
# returned, the server tells the user that he/she is not permitted to
# access that irc server, and gives the reason.
#
# Again, like K: lines, R: lines are local and thus not very effective in
# blocking certain machines from having IRC access.
#
# Use of R: requires that you have defined R_LINES in include/config.h
#
# The fields are as follows:
# R:hostmask:/full/path/to/program:username
# you can use wildcards in either the hostmask or username portion
#
R:csl.bu.edu:/home/hrose/bin.sun3/sun3access:*
##
## R lines are HIGHLY discouraged in hybrid right now
## -db
##
#
# Q: [DISCOURAGED]. These lines "quarantine" specified servers. Because
# of the way they operates, the same Q: lines MUST be installed by
# everyone or the net will keep breaking. I CANNOT EMPHASIZE THIS ENOUGH.
# Do NOT use Q: lines lightly!
#
# The fields are as follows:
# Q:*:reason why quarantine is in place:servername
#
Q::this server is too slow and lags the net:cm5.eng.umd.edu
##
## Q line support was completely removed from hybrid. So, even
## if you did add a Q line, it wouldn't do anything :-)
## -db
##
#
# L: [OPTIONAL]. These lines "Leaf" specified servers. They are only
# useful if you are a non-leaf site yourself. There are two ways you can
# use L: lines. The first will limit one particular site to a particular
# tree depth (including 0, which would mean the server has to connect with
# no servers linked behind it otherwise the connection will fail). The
# second will allow you to be selective about which other servers you wish
# the connecting server to behave as a leaf towards.
#
# The fields are as follows:
# L:disallow connections to this hostmask::server name:depth
# For example, this will force kaja.gi.alaska.edu to connect only as a
# leaf (if it is not a leaf, the link will be dropped):
L:::kaja.gi.alaska.edu
# This line will force cm5.eng.umd.edu to have a depth of only 1 below it
# (that is, it is allowed to have only leaves connected to it):
L:::cm5.eng.umd.edu:1
#
# This line will prohibit anything matching *.edu to be connected behind
# any server matching *.au:
L:*.edu::*.au
#
# H: [OPTIONAL]. These lines define who you permit to act as a "hub" to
# you (that is, who you permit to connect non-leafed servers to you).
#
# the first field may use wildcards, the third field *must* be an exact
# match for a server's name (NOT a server's hostname, if they differ, the
# server's name must be used). If the servername is a wildcard (e.g. *.au)
# that is an acceptable name for the third field.
#
# The fields are as follows:
# H:servers which are permitted entry::hub server
#
# Example, permit cs-ftp.bu.edu to allow any servers behind it to connect:
H:*::cs-ftp.bu.edu
#
# Example, permit irc-2.mit.edu to allow any MIT servers behind it to
# connect:
H:*.mit.edu::irc-2.mit.edu
#
# P: [OPTIONAL]. This field allows the server to listen on various ports
# (other than 6667) for connections. Any internet domain port that is
# below 1024 means the ircd has to be run from inetd. The server can
# listen to ports in the UNIX domain or the internet domain. If you wish
# to create a port in the UNIX domain you must compile with UNIXPORT
# defined in include/config.h. If you are permitting connections to a
# seperate port, you can control access to that port by the host field.
#
# The fields are as follows::
# P:hostmask or UNIX socket file:*:*:port number
# for example, an internet domain socket on port 6665 for South African
# users:
P:*.za:*:*:6665
#
# This line is an example of a UNIX domain socket in /tmp
P:/tmp/.ircd:*:*:6666
##
## There IS no UNIX domain socket support in hybrid, thats how
## we gained some speed :-)
## It makes no sense at all, when you read the new-server requirements
## an irc server has to be run on a dedicated server now. UNIX domain
## sockets aren't much use if no shell users are allowed on the server.
## -db
##
## D line E line etc. are described in the other example.conf
## -db

477
doc/old/example_old.conf Executable file
View file

@ -0,0 +1,477 @@
#
# IRC - Internet Relay Chat, doc/example.conf
# Copyright (C) 1992, Bill Wisner
#
# $Id: example_old.conf,v 1.1 2002/08/13 14:35:25 fishwaldo Exp $
#
# Example of an old style ircd.conf file, which h7 will not parse
# but is kept here for historical interest
#
# Modified by Rodder, Jon Lusky <lusky@blown.net>,
# at one time, but he didn't credit his changes.
# Updated Dec 19, 1997 Diane Bruce aka db/Dianora <db@db.net>
# please also read example.conf.trillian, it covers
# elements this example misses.
# -db
# Updated again July 17, 1998 -db
# Updated 990102 to take out P: line connection limiting code
# Updated again July 5, 1999 -db
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 1, or (at your option)
# any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
#
#
# IRC example configuration file
#
# This file describes the information that should be present in your IRC
# configuration and how to present it.
#
# M: set your server's name. Fields are, in order, host name (domain style),
# optional bind address, a text name, and unused.
#
# NOTE: The "optional bind address" is an address used in binding to a
# local address when we connect outbound. For example, if your server machine
# is myhost.example.com (192.168.1.5) and you want IRCD to connect to others
# from irc.example.com (192.168.1.250), you'd put 192.168.1.250 in the
# "optional bind address" field. If left blank, UNIX will choose the primary
# address of the interface closest to the destination.
#
# NOTE: As of hybrid-6, the port field no longer binds a port by default.
# It is an inoperative and obsolete field.
#
M:hayes.ims.alaska.edu:192.168.1.250:University of Alaska Fairbanks:
#
# A: administrative information. This line should have three fields, which
# may contain any arbitrary text. It is printed by the /ADMIN command.
#
A:University of Alaska Institute of Marine Science:Fairbanks, AK USA:Bill Wisner <wisner@ims.alaska.edu>
#
# .include lines, insert a file from DPATH directory into the conf
# you could use this to insert a common file between several
# ircd's if you wished. include files are handled after all the
# other lines in the conf file are done. i.e. a .include is always
# as if it was at the end of the conf file.
#
.include "olines.conf"
#
# Y: define connection class. A class must be defined in a Y: line before
# it is used in a C, N, or I line. The fields are, in order, class number,
# ping frequency in seconds, connect frequency in seconds, maximum
# number of links (used for auto-connecting), and size of sendq.
# For servers a sendq of at least 4mb is recommended if not more.
#
# N.B. Y lines must be defined before I lines and O lines, since
# both I lines and O lines make reference to Y lines or classes.
#
# For clients, the connect frequency field is used to set the maximum
# number of connects from same IP address. i.e. setting this field to '1'
# will limit every I line using this Y, to one connection per IP address.
# leaving it blank or 0, will disable any such checking.
#
# Class numbers must be positive to ensure future modification of ircd to
# use -1 internally could not be complicated with it's use externally.
#
Y:1:90:0:20:100000
Y:2:90:300:10:4000000
#
# I: authorize clients to connect to your server. You can use domains,
# IP addresses, and asterisk wildcards. The second field can contain a
# password that the client must use in order to be allowed to connect.
# The optional fifth field may contain a connection class number.
#
I:NOMATCH::*.alaska.edu::1
I:NOMATCH:password:acad3.alaska.edu::1
#
# If using IDENT, to activate it, you need to place a "user@" in the
# host segment.
#
I:*@acad3.alask.edu::*@acad3.alaska.edu::1
I:root@acad.alask.edu::root@acad.alaska.edu::1
#
# The above are bad examples of I-lines, what really happens is something
# like this:
#
## both these are obsolete in hybrid-6
##I:128.250.*::*.mu.oz.au::1
##I:root@128.250.*::root@*.mu.oz.au::1
## This is a correct example in hybrid-6, the username
## is not used for an IP I line (this may be changed, its a simple change
## but EFnet is currently deprecating the use of non resolving client hosts)
## If the IP block has a resolving host name, it will be shown instead
## of the IP address. This just serves to allow on an entire block of ip's
## without needing to specify each individual hostname.
## Note, you must use an 'x' in the name field
I:128.250.0.0/16::x::1
#
# You can also limit the number of connections from one host
# to any value. This can be used to stop cloners
# This is done using the normally unused confreq line in the Y line.
#
# i.e.
# Allow 100 users in a "bad boy" class, but allow only ONE
# user per IP to connect at a time.
#
Y:3:90:1:100:100000
#
# Remember to put your "bad boy" I line last in the file, so it
# seen first and matches first before your standard I lines
#
# With hybrid ircd, max connections is taken from the class
# not per I line. i.e. the 3 I lines following will always add
# up to 100 or less, not 100 per I line.
#
I:NOMATCH::*@*ppp*::3
I:NOMATCH::*@*slip*::3
I:NOMATCH::*@*ts*::3
#
# a name pattern in the first field will never cause a match since it's only
# ever matched against an IP# in the form a.b.c.d and a number in the third
# field will never match since a hostname is always compared against this
# field. The '@' needs to be in the IP# section for ident to be used.
#
## additional prefix characters in I lines are defined
##
## from comstud
##
## 1) There are noticable differences in I: lines now.
## There are 4 special characters that you can stick in front
## of a hostname or ip# that do special things.
## These characers are:
## - This will never put a ~ for a user not running identd
## + This will force people matching this I: to require identd
## ! This means to only allow 1 connection per ip# in this I:
## $ (Not used in hybrid)
##
## Examples:
##
## a) I:x::!*@*ppp*::class will only allow X connections per ip# for people
## who have *ppp* in their hostname where X is given in the Y: line.
## If there is no ! and you have a limit in your Y: line, then it matches
## full user@host instead of just host.
## b) I:x::-*@*.cris.com::class will never show a ~, even though they may
## not be running identd. (This is equivilent to the old way of not
## specifying a @ in the I: line).
## Additionally since ircd-hybrid-6
## B/E/F lines were removed and replaced with 3 other special characters
## in I lines
##
## ^ This will exempt a user from K/G lines, limited protection from D lines
## & User can run bots (old B line)
## > This user is exempt from I line/server side connection limits
## (old F line)
##
## A variant of amm's spoofing code was added
## = Spoof this users IP, normally only used for opers
##
## Examples
## c) I:NOMATCH::^db@koruna.varner.com::3
## This user is exempt from k/g lines
## d) I:NOMATCH::&jerdfelt@*mindspring.net::3
## This user can run a bot, and is also "e lined"
## e) I:NOMATCH::>lusky@*vol.com::3
## This user is immune from I line limits
## f) I:NOMATCH::^&>mpearce@*varner.com::3
## This user can run a bot, is exempt
## from client connect limits.
## g) I:smurfers.are.lame::=dgalas@*somewhere.com::3
## Show this user as being dgalas@smurfers.are.lame
## an IP can be used instead as long as the name field does not begin
## with an 'x'
## i.e.
## I:192.168.0.0/24::x::3 #this is an IP I line
## I:192.168.0.0::db@*somesite.com::3 #this is a spoofed IP
#
# O: authorize operators. Fields are, in order, host name the operator must
# be logged in from (wildcards allowed), operator's password, operator's
# nickname.
## The 4th field is the port number used in c/n's, in ircd-hybrid
## this field is used to contain oper flags for this oper
## You may wish to constrain an oper from using global kill or unkline
## for example.
## The flags are:
## K/k - allow/disallow kill and kline
## O/o - allow/disallow global kill
## R/r - allow/disallow remote squit/connect
## U/u - allow/disallow unkline
## G/g - allow/disallow gline
## N/n - allow the use of +n , which should be restricted to tcm use only
## for privacy reasons. (+c probably belongs controlled here too but isn't)
## H/h - allow the use of /rehash, default is H for O and o, add h to
## disable an opers use of /rehash
## D/d - allow the use of /die or /restart. Default is d for disallowing
## /die /restart
##
## Default flags for opers are GKORUH
## Default flags for local ops, KUH
## These flags over-rule what the normal privs of an oper would be,
## but they cannot allow a local oper to do global kills for example.
##
## The global kill of a global oper can be disabled by using o for
## example, in the port field.
##
# The first example allows me to become an operator from any
# machine in alaska.edu by typing /oper crunchy frog.
#
O:*.alaska.edu:frog:crunchy
#
## This example allow this oper, to global kill, do remote squit/connect
## unklines, glines, and use umode +n
##
O:db@*db.net:-encrypted password-:Dianora:ORUGN:3
#
##
## This example disables this opers use of global kill, unkline, and gline
## The oper can still do remote squits/connects
##
O:newbie@*some.net:-encrypted password-:newbie:oug:3
##
## This example disables this opers use of global kill, unkline,
## gline and gline and remote squits/connects
## essentially the same permissions as a local oper, but with the "vanity"
## They can still local kill and kline for example.
##
O:vanity@*some.net:-encrypted password-:vanity:oug:3
##
## you could make someone vantiy even more, by disabling their
## kill/kline privs... note they can still do full traces
## umode +c (watch connections) and do rehash
## But otherwise, this set of flags is not practical for
## a normal oper.
##
O:vanity@*some.net:-encrypted password-:vanity:nougk:3
#
## a monitor bot could be given the following privs
## k - no kline/kill
## g - make sure no GLINE
## o - no global kill (already taken care of by 'k' flag above)
## r - no remote routing/squits
## N - allow this monitor to use umode +n for nick changes
##
## Some admins do not like remote tcm kills/klines. If this
## tcm oper gets compromised, the best they can do is
## rehash/trace/umode +cn , i.e. no global kills or "fun" for the
## compromised o line. But its still quite usuable for monitoring
## clones and nick flooders.
##
#
o:tcm@*varner.com:-encrypted password-:tcm:kgorN:3
#
## Of course, leaving out the flags entirely defaults to
## reasonable defaults, so if you don't want to worry about it, then don't.
## You can always add G later for example.
#
## O : Global operator
## No explicit G or G-line flag, no N or allow umode +n flag
##
O:db@ircd.dianora.com:-encrypted password-:Dianora::3
#
# o : local operator.
o:trainee@shell.box.com:password:MyNick::3
#
##
## The fifth field of an O line, is the new class this oper will join
##
# C:, N: set up connections to other servers.
#
# C: specifies a server that your server may connect to.
# N: allows a remote server to connect to your own.
#
# The two lines are usually given in pairs.
#
# These lines may contain a password in the second field. In fact, to
# maintain proper security, *all* IRC server links must have passwords.
#
# If a C: line contains four fields (the fourth being a TCP port number)
# IRC will actively try to connect to that server. You should have at least
# one such line.
#
# If an N: line contains four fields, the fourth should contain a number that
# specifies how many components of your own server's name to strip off the
# front and be replaced with a *. This is done to implement hostmasking.
# For example, to make hayes.ims.alaska.edu present itself to the world as
# *.alaska.edu, I would use a 2 (to strip off the first two parts). If you
# use this, be sure to tell the administrator of the servers you link to --
# they must add your hostmasked name to their configuration file or you will
# be unable to connect.
#
# The host part of C/N lines MUST contain a valid hostname or IP address
# The host part in the C:line MUST be identical to the host part in the N:line
# The name part of the C/N lines MUST match the associated H/L line name
#
# The fifth field may contain a connection class number.
#
# The following two lines tell my server to try connecting to
# byron.u.washington.edu.
#
C:byron.u.washington.edu:crunchyfrog:byron.u.washington.edu:6667:2
N:byron.u.washington.edu:crunchyfrog:byron.u.washington.edu:2:2
#
# The following two lines allow a server to connect to my server, but my
# server will not make any attempt to connect to it. Note that since the
# server is local to me, I am not using hostmasking.
#
C:kaja.gi.alaska.edu:llamas:kaja.gi.alaska.edu::2
N:kaja.gi.alaska.edu:llamas:kaja.gi.alaska.edu::2
#
# C and N lines may also use the "user@" combination in the same way as
# the I-lines.
#
C:wisner@kaja.gi.alaska.edu:llamas:kaja.gi.alaska.edu::2
N:wisner@kaja.gi.alaska.edu:llamas:kaja.gi.alaska.edu::2
#
# K: kill a user automatically upon connecting. This is used to deny
# troublesome users access to your server. The fields are, in order,
# hostname (wildcards are allowed), time of day, and username.
## Timed k-lines and R: lines are not recommended by the hybrid
## team. They might not even work. Timed-klines made more sense
## for university ircd's but nowadays with so many open irc servers
## around, it just seems pointless.
## -Dianora
# The second example restricts access from acad3.alaska.edu from
# 9:00am to noon, and 2:00pm to 5:00pm. This form is only supported if
# TIMED_KLINES is defined.
#
K:*.alaska.edu::FSSPR
K:acad3.alaska.edu:0900-1200,1400-1700:*
#
# R: restrict user access. This is an extended form of the K: line.
# It looks for a match then runs an outside program that will determine
# whether the person should be allowed on. The fields are hostname,
# program, and username. A full pathname to the program should be used.
# The output of the program should be a string of the form "Y <message>"
# to allow the user, or "N <message>" to block them. In the first case
# the message is ignored; in the latter, it is sent as an error message
# to the user. R: lines are only functional if activated in config.h.
#
R:kaja.gi.alaska.edu:/usr/local/lib/irc/does-eric-get-in:ejo
#
#
# L: leaf. This forces the server listed to act as a leaf. If such a
# server allows any other servers to connect to it, its link is
# dropped. If a port parameter is non-zero, it is used to control the
# maximum depth that link will allow, where depth is the tree depth of
# that branch.
#
L:::kaja.gi.alaska.edu
L:::cm5.eng.umd.edu:1
#
# A new extension to the L-line allows you to be selective
# about which other servers you wish the connecting server to behave as
# as a leaf towards. The following would not allow any server connecting
# with a name that matches *.fi to introduce a server matching *.edu.
#
L:*.edu::*.fi
#
# H: Hub. This is required to allow other servers which connect to you as
# a hub and introduce other servers.
#
H:*.au:*:*.au
#
# P : port. The port line allows the server to listen on various ports for
# connections. Fields in order: unused,
# address to bind to, unused, port to listen on
#
# NOTE: As of hybrid-6, you MUST have at least one P: line defining a port
# to listen on, or the server won't do much.
#
P::::6667
P::209.42.128.252::31337
#
# Listen on port 6665 on all available interfaces. Only allow connections from
# net 128.32. This is checked before existance of other access is available.
# 128.32.* == 128.32.0.0 where 0 is a wildcard.
# Also listen to port 31337 on only 209.42.128.252. Allow connections from
# anywhere.
#
# D : dump. Dumps all connect attempts from the matched IP
# without any procesing.
#
# First arg is target IP and CIDR mask, second is a comment.
#
D:208.148.84.3:bot host that changes domain names frequently
D:128.183.0/24:NASA users aren't supposed to be on IRC
#
# d : immunity to D dump
# As in D line , First arg is targe IP and CIDR mask, second is a comment.
#
d:199.0.154.0/24:Don't D line ais.net:
#
# server "clusters"
# U: lines treat each of these servers as being part of your server cluster
# klines placed on this server will be forwarded to the servers named
# in the U lines here. LOCOPS will also be forwarded, but will appear
# as "SLOCOPS" instead of "LOCOPS"
#
# i.e. irc_hub.somewhere.net has leaf servers irc1.somewhere.net
# irc2.somewhere.net
# Hub server would have
U:irc1.somewhere.net:
U:irc2.somewhere.net
# each client server would have
U:irc_hub.somewhere.net
#
#
# Q lines, not the old server Q lines, but Quarantine lines for
# nicks. Only checked at NICK time, i.e. if added and hashed in
# will not kill users who match this nick.
#
Q:dcc-*:dcc bots not allowed on this server
Q:lamestbot:You have to be kidding me
Q:crush:In memory of Janet Pippin
Q:cwush:In memory of Janet Pippin
Q:callas:Only allowed from this host:callas@oper.irc.arpa.com
#
# if JUPE_CHANNEL is defined you can also jupe a channel locally
# i.e. no one on your server can join this channel.
# You need the backslash to escape the # in the channel
#
Q:\#packet:I am tired of the packet fights for this channel
#
# X lines.
# Used to match gecos fields and prohibit users or warn about users
# who have matching strings in those fields from getting on the server.
#
# All X line matches are sent to opers in +r user mode
# On an X line, a non 0 value for port exits that client
# a 0 value, only warns on +r
#
# These three examples only warn
X:*www*:Possible spambot warning 1::0
X:*http*:Possible spambot warning 2::0
X:*sex*:Possible spambot warning 3::0
#
# These two examples reject the client
# use this to reject IPHONE users
X:* vc:IPHONE user::1
# This is a very probable spambot
X:*see me at*:This has GOT to be a spambot::1
X:*hi baby*:This has GOT to be a spambot::1

145
doc/old/ircd.8 Normal file
View file

@ -0,0 +1,145 @@
.\" @(#)ircd.8 2.0 (beta version) 29 Mar 1989
.TH IRCD 8 "29 March 1989"
.SH NAME
ircd \- The Internet Relay Chat Program Server
.SH SYNOPSIS
.hy 0
.IP \fBircd\fP
[-a] [-c] [-i] [-o] [-q] [-t] [-d directory] [-f configfile]
[-x debuglevel] [-h hostname] [-p portnum] [-s]
.SH DESCRIPTION
.LP
\fIircd\fP is the server (daemon) program for the Internet Relay Chat
Program. The \fIircd\fP is a server in that its function is to "serve"
the client program \fIirc(1)\fP with messages and commands. All commands
and user messages are passed directly to the \fIircd\fP for processing
and relaying to other ircd sites. The \fIirc(1)\fP program depends upon
there being an \fIircd\fP server running somewhere (either on your local
UNIX site or a remote ircd site) so that it will have somewhere to connect
to and thus allow the user to begin talking to other users.
.SH OPTIONS
.TP
.B \-d directory
This option tells the server to change to that directory and use
that as a reference point when opening \fIircd.conf\fP and other startup
files.
.TP
.B \-o
Starts up a local ircdaemon. Standard input can be used to send IRC
commands to the daemon. The user logging in from standard input will
be given operator privileges on this local ircd. If ircd is a setuid program,
it will call setuid(getuid()) before going to local mode. This option
can be used in inetd.conf to allow users to open their own irc clients
by simply connecting their clients to the correct ports. For example:
.TP
.B
irc stream tcp nowait irc /etc/ircd ircd \\-f/etc/ircd.conf \\-o
allows users connecting to irc port (specified in /etc/services) to start
up their own ircdaemon. The configuration file should be used to check from
which hosts these connections are allowed from. This option also turns
on the autodie option -a.
.TP
.B \-a
Instructs the server to automatically die off if it loses all it's clients.
.TP
.B \-t
Instructs the server to direct debugging output to standard output.
.TP
.B \-x#
Defines the debuglevel for ircd. The higher the debuglevel, the more stuff
gets directed to debugging file (or standard output if -t option was used
as well).
.TP
.B \-i
The server was started by inetd and it should start accepting connections
from standard input. The following inetd.conf-line could be used to start
up ircd automatically when needed:
.TP
.B
ircd stream tcp wait irc /etc/ircd ircd \-i
allows inetd to start up ircd on request.
.TP
.B \-f filename
Specifies the ircd.conf file to be used for this ircdaemon. The option
is used to override the default ircd.conf given at compile time.
.TP
.B \-c
This flag must be given if you are running ircd from \fI/dev/console\fP or
any other situation where fd 0 isnt a tty and you want the server to fork
off and run in the background. This needs to be given if you are starting
\fIircd\fP from an \fIrc\fP (such as \fI/etc/rc.local\fP) file.
.TP
.B \-q
Using the -q option stops the server from doing DNS lookups on all the
servers in your \fIircd.conf\fP file when it boots. This can take a lengthy
amount of time if you have a large number of servers and they are not all
close by.
.TP
.B \-h hostname
Allows the user to manually set the server name at startup. The default
name is hostname.domainname.
.TP
.B \-p portname
Specifies the port where the daemon should start waiting for connections.
This overrides the default which is given at compile time.
.TP
.B \-s
Send debugging output to stderr and don't fork. Exteremely useful
when IRCD runs and immediately exits.
.TP
.SH
If you plan to connect your \fIircd\fP server to an existing Irc-Network,
you will need to alter your local IRC CONFIGURATION FILE (typically named
"ircd.conf") so that it will accept and make connections to other \fIircd\fP
servers. This file contains the hostnames, Network Addresses, and sometimes
passwords for connections to other ircds around the world. Because
description of the actual file format of the "ircs.conf" file is beyond the
scope of this document, please refer to the file INSTALL in the IRC source
files documentation directory.
.LP
BOOTING THE SERVER: The \fIircd\fP server can be started as part of the
UNIX boot procedure or just by placing the server into Unix Background.
Keep in mind that if it is *not* part of your UNIXES Boot-up procedure
then you will have to manually start the \fIircd\fP server each time your
UNIX is rebooted. This means if your UNIX is prone to crashing
or going for for repairs a lot it would make sense to start the \fIircd\fP
server as part of your UNIX bootup procedure. In some cases the \fIirc(1)\fP
will automatically attempt to boot the \fIircd\fP server if the user is
on the SAME UNIX that the \fIircd\fP is supposed to be running on. If the
\fIirc(1)\fP cannot connect to the \fIircd\fP server it will try to start
the server on it's own and will then try to reconnect to the newly booted
\fIircd\fP server.
.SH EXAMPLE
.RS
.nf
tolsun% \fBircd\fP
.fi
.RE
.LP
Places \fIircd\fP into UNIX Background and starts up the server for use.
Note: You do not have to add the "&" to this command, the program will
automatically detach itself from tty.
.SH COPYRIGHT
(c) 1988,1989 University of Oulu, Computing Center, Finland,
.LP
(c) 1988,1989 Department of Information Processing Science,
University of Oulu, Finland
.LP
(c) 1988,1989,1990,1991 Jarkko Oikarinen
.LP
For full COPYRIGHT see LICENSE file with IRC package.
.LP
.RE
.SH FILES
/etc/utmp
"ircd.conf"
.SH "SEE ALSO"
irc(1)
.SH BUGS
None... ;-) if somebody finds one, please inform author
.SH AUTHOR
Jarkko Oikarinen, currently jto@tolsun.oulu.fi,
manual page written by Jeff Trim, jtrim@orion.cair.du.edu,
later modified by jto@tolsun.oulu.fi.

62
doc/old/simple.conf Executable file
View file

@ -0,0 +1,62 @@
# IRC minimal example configuration file
#
# $Id: simple.conf,v 1.1 2002/08/13 14:35:25 fishwaldo Exp $
# $Id: simple.conf,v 1.1 2002/08/13 14:35:25 fishwaldo Exp $
#
# This is a basic ircd.conf that will get you up and running with
# little or no modifications. See the example.conf file for more
# detailed explanations.
#
# M: set your server's name. Fields are, in order, host name (domain style),
# optional bind ip address, a text name, and unused.
#
M:irc.example.com::Test IRC Server:
#
# A: administrative information. This line should have three fields, which
# may contain any arbitrary text. It is printed by the /ADMIN command.
#
A:Example, Inc Test IRC Server:Atlanta, GA USA:John Doe <jdoe@example.com>
#
# Y: see example.conf for docs on how Y/I lines work
#
# class 1, 90 second ping timeout, no limit of clients per ip
# 200 max clients in this class, 100k sendq
Y:1:90:0:200:100000
#
# class 2 give opers more sendq, only 10 opers max on this server
Y:2:90:0:10:500000
#
# allow anyone to connect, but force ident, clients go into class 1
I:NOMATCH::*@*::1
#
#
# O: authorize operators. Fields are, in order, host name the operator must
# be logged in from (wildcards allowed), operator's password, operator's
# nickname. Use the 'mkpasswd' command from the tools dir to encrypt
# a password.
# When opered, client goes into class 2 where they have more sendq
#
O:*.example.com:yl9xlY019Bbfc:JohnDoe::2
#
# P: port. The port line allows the server to listen on various ports for
# connections. Fields in order: unused,
# address to bind to, unused, port to listen on
#
# NOTE: As of hybrid-6, you MUST have at least one P: line defining a port
# to listen on, or the server won't do much.
# The line below listens to port 6667 on all IP addresses of a machine
P::::6667
# The above below listens to port 31337 on only 192.168.1.123
P::192.168.1.123::31337
#
#
# Q: Quarantine a nick: not the old server Q lines, but Quarantine
# lines for nicks. Only checked at NICK time, i.e. if added
# and hashed in will not kill users who match this nick.
#
Q:dcc-*:dcc bots not allowed on this server
Q:lamestbot:You have to be kidding me
Q:nickserv:There is no nickserv on this net!
#
# There are many more configuration options, see example.conf for the rest.
#

368
doc/operguide.txt Normal file
View file

@ -0,0 +1,368 @@
EFnet Oper Guide
Last update: 02-21-2002
Written and maintained by Riedel
E-Mail: dennisv@vuurwerk.nl
1. Commands you should know about
2. The client of your choice
3. Your primary responsibilities
4. Re-routing
4.1 Re-routing other servers and remote connects
5. Kills and klines
6. Kill and K-Line requests
7. Happy birthday!
8. Security
9. Know who your friends are
10. The TCM bot
11. Services
12. G-Lines
1. Commands you should know about
This is no longer covered here. IRCD-hybrid is changing too rapidly, so
this section would be outdated in no time ;) For an up-to-date version,
please download the latest hybrid at www.ircd-hybrid.org.
2. The client of your choice
There are many IRC clients around for a wide variety of operating systems.
Being an IRC Operator doesn't *require* you to use a UNIX client, however
I personally prefer UNIX-based clients. If you're familiar with UNIX and
use UNIX for opering, I suggest ircII / epic. There are a lot of scripts
available for those two clients, and it's not that hard to write scripts
yourself to suite your needs. It is important that you know how to operate
your client, and familiarize yourself with the options and features. For
whatever client you chose this goes for any of them: You should be in
control of your client, instead of the client being in control of you.
Resources :
www.mirc.co.uk - mIRC (MS-Windows)
www.irchelp.org - a variety of clients and scripts
ftp.blackened.com - several UNIX based clients available
3. Your primary responsibilities
As an IRC Operator, you're responsible for maintaining the server on a
real-time basis. You represent your server, and you represent the network.
Irresponsible / rude / offensive / stupid behavior may discredit your server
and the network. You should focus on the task you were chosen for...
maintainance. Sounds simple, no? It means getting rid of users that abuse
the service, enforcing the server's policy and keeping the server linked.
Users will ask you questions, and expect you to know all the answers.. after
all, you're the oper!
Be prepared for users trying to fool you, sweet talk you into things you
don't want, lie and deceive. Most users are handling in good faith...
however, the abusers have learned how to manipulate opers. They have studied
the alien creature 'oper' for ages like biologists study animals. Be
paranoid, be curious and be suspicious. I can't stress the importancy of that
often enough.
Second priority has the network. You were not chosen to maintain the network
but you were chosen to maintain the server. However, you may want to be able
to reroute servers. If you see something broken, don't be afraid to fix it.
If you do, be sure you fix things and don't make it worse. Before you
step into routing, be sure you've familiarized yourself with the network's
topology, and be confident enough to perform such actions. (re)routing is
covered in the next chapter.
Opers on the network depend on a trusting relationship. You can usually take
the word from an oper. Other opers are considered -trusted-, however, there
are exceptions. Sometimes even opers lie to opers to get things done. Don't
be afraid to ask for proof of a certain statement, such as logs.
This doesn't mean you distrust the oper in question, but -you- and you alone
are responsible for your actions. You call the shots on your server, unless
your admin says otherwise.
4. Re-routing
Re-routing is not hard, and it's not scary but it is important that you do it
right. The commands you'll use are SQUIT and CONNECT. First, a very simple
example. Let's say your server, irc.yourserver.com is lagged to it's uplink,
irc.uplink.com and you want to reroute your server. You have to think about
where you want your server to be linked, and you have to time your reroute.
An example topology :
irc.yourserver.com ---- irc.uplink.com
| | \
B C D
/ \
E F
/ \
G H --- O
/ | \ | \
I J K L M
\
N
In this case, you're uplinked by irc.uplink.com
irc.uplink.com also hubs B, C and D. Server B functions as hub for E and F;
F hubs G and H; H hubs L, M and O. G hubs I, J and K. M hubs N.
Your server is allowed to connect to server B, F and G. So you consider the
servers you're able to connect to. Is the lag caused by a server that uplinks
irc.uplink.com ? Use /stats ? irc.uplink.com to determine lag to the other
servers. If irc.uplink.com does not respond, the lag is to your uplink. If
so, you cannot be sure about the state of the other uplinks, so you'd have to
get on a remote server and determine lag by using /stats ? and /trace. For
example, you could connect to server N, and /trace yournick. Yournick, being
the nick on your server. You'll see which route it takes, and what the
problem server is. Example /trace output :
S:[SERVER-N ] V:[2.8/hybrid] U:[SERVER-M ]
S:[SERVER-M ] V:[2.8/hybrid] U:[SERVER-H ]
S:[SERVER-H ] V:[2.8/hybrid] U:[SERVER-F ]
S:[SERVER-F ] V:[2.8/hybrid] U:[SERVER-B ]
S:[SERVER-B ] V:[2.8/hybrid] U:[irc.uplink.com ]
S:[irc.uplink.com ] V:[2.8/hybrid] U:[irc.yourserver.com ]
The trace doesn't complete... server-b announces irc.uplink.com, and
irc.uplink.com announces your server. Your server should return something
like :
S:[irc.yourserver.] OPER [yournick!user@yourhost]
If it doesn't, we know the lag is only between yourserver and uplink.
Usually if there is lag between your server and your uplink, the send-queue
rises. This is not always the case. Sometimes your server can write perfectly
to your uplink, but not reverse. That is called one sided lag.
We pick server B to link to. It means we have to SQUIT and CONNECT.
To unlink from irc.uplink.com and connect to SERVER_B we'd type:
/quote SQUIT irc.uplink.com :reroute
/connect SERVER_B
we *DON'T* SQUIT irc.yourserver.com... and I'll try to explain why:
If we wanted to remove hub M from the network, and with it N, we'd issue
a SQUIT M. An SQUIT follows a path, relays the SQUIT request to each server
in that path. Finally it reaches server H, which is the hub for M. Server H
sees the SQUIT and drops the link to M.
Now a different situation, we want to separate yourserver, uplink, C and D
from the rest of the network, in order to reroute. We'd have to SQUIT server
B, since we want the -uplink- of server B (being irc.uplink.com) to drop the
link to server B.
If you'd SQUIT irc.yourserver.com, you ask yourserver.com to drop the link to
itself, which is impossible. If you SQUIT irc.uplink.com, you ask yourserver
to drop the link to uplink, which is what we want to do.
After the SQUIT and CONNECT, the new situation looks like this :
irc.uplink.com
| | \
irc.yourserver.com -- B C D
/ \
E F
/ \
G H --- O
/ | \ | \
I J K L M
\
N
If yourserver is a Hub, it makes the situation more complex, since your
actions have more impact.
4.1 - Re-routing other servers and remote connects
Example topology :
irc.uplink.com
| | \
irc.yourserver.com -- B C D
/ \
E F
/ \
G H --- O
/ | \ | \
I J K L M
\
N
Let's say, hub H is way lagged to F, but G to F is fine... we want to reroute
H, and stick H to G.
We'd do :
/quote SQUIT serverh :re-routing you babe
/connect serverh 6667 serverg
A global wallops will be sent :
!serverg! Remote CONNECT serverh 6667 from ItsMe
When re-routing, always give the server some time to prevent nick collides.
When there is lag, people will connect to another server. When you SQUIT and
CONNECT to fast, a lot of those clients will be collided. Also, stick to your
territory. How enthusiastic you may be, you cannot route the world. If you're
an oper on the US side, stick to the US side when re-routing. Needless to
say, if you're EU, keep it to EU ;)
5. Kills and klines
As an oper, you're given the incredible power *cough* of KILL and KLINE.
/kill nick reason disconnects a client from IRC with the specified reason.
A /quote kline *evil@*.dude.org :reason here bans the user from your server.
Abusive kills and klines may draw attacks to your server, so always consider
if a kline or kill is deserved. If the server gets attacked after a valid
kill or kline, well.. tough luck. You should never be 'afraid' to kline
anyone on your server. If it's a good reason, make it so. Even if you know
it may cause the server to be attacked. Maybe good to think about is this:
- if /ignore solves the problem rather than a kick, /ignore
- kick if a ban is unneeded
- ban if a /kill is unwarranted for
- kill rather than kline if that solves the problem
- kline when a server ban is really needed.
You kline a user when you absolutely don't want this user to use the service
your server is providing.
Crosskills (killing users on another server) are another issue. Some admins
don't care if users get /kill'ed off their server, for any reason or no
reason at all... and other admins are very anal about it. A good way to go
(IMO) is to issue a KILL if there is an absolute need for the target user to
be disconnected. If there are active opers on that server, let them handle
it. They'll be upset if you /kill a user off their server, without
contacting them. /stats p irc.server.here shows the active opers on a
particular server. Some opers have multiple o-lines and are not watching all
sessions. If you can't find an active oper on a server, you can
/quote operwall a request for opers from that server.
Ghost KILLs are another story, an often misunderstood one.
When you see a /KILL from an oper with the reason 'ghosted' they usually
KILL a client that's about to ping timeout. That is not what a ghost is!
To quote Dianora: "a ghost happens because a client misses being killed when
it should be. Its a race condition due to nick chasing". In other words,
Server X thinks client A has been KILLed, while server Y missed the KILL
for that client.
6. Kill and K-Line requests
As previously mentioned, if an oper from another server contacts you and
requests a kill or a kline for a local client with a good reason, you can
usually trust this request. Opers depend on a trusting relationship. However,
since you're responsible for the kill or kline, it is not rude to ask for
proof. It depends on the oper making the request how thats interpreted, but
the way they respond to asking for proof tells more about them than about
you.
The more and longer you oper, how better you get to know the other opers.
You know who is honest, you'll know who are lying and deceiving. Before
you acquire this knowledge, you can merely rely on common sense and
instincts. You'll probably make mistakes occasionally, and thats nothing to
be ashamed of. Opers are - despite contrary believes - human.
Users occasionally will ask you to kill or kline a user/bot too. Some
requests are straight-forward and clear, others require you to be cautious. I
recommend to always investigate such requests, and when you're confident the
request is valid, issue the kill or kline.
7. Happy birthday!
It is a custom on EFnet to birthday /kill opers of whom it is his/her
birthday. Not all opers like this, but typically those opers don't let
others know about their birthday. You'll notice that the KILLS say a lot
about who likes who and who is friends with who. Whether you want to
participate, is entirely up to you.
8. Security
As with any privilege, you have to handle it cautiously and responsibly.
Be sure that your o/O line doesn't get compromised! Oper only from secure
hosts. You and only you should know your password. Don't share your oper
account, and make your oper password a UNIQUE one. If your o/O line gets
compromised, nasty things may/will happen. Imagine an oper with crosskill
capabilities who's operline gets 'hacked'... the results are often
disastrous and you will lose respect and trust from others. It can cause
your oper privileges to be revoked, or even the server to be (temporarily)
delinked.
9. Know who your friends are
As an oper you will get a lot of users that want to be 'friends' with you.
Users offer you free* access to their *nix servers, ops in channels,
unlimited leech access to the biggest and fastest warez sites *gasp* and
more. They want favors in return. They say they don't but they truly want
something in return. They -expect- something in return. You could either
don't respond to such offers, or use them. The last option creates an even
more distorted image of opers and doesn't do any good for the user <-> oper
relationship. Your *real* friends are usually the persons who were your
friends _before_ you acquired the extra privileges.
10. The TCM Bot
A TCM bot can be a valuable tool for opers. It keeps record of all connected
clients, flags clients with multiple connections and has all sorts of other
useful commands. There are three different kind of TCM's in use on EFnet,
being OOMon, TCM-Dianora and TCM-Hybrid. Every one of them requires you to
log in to be able to access the privileged commands. On OOMon you DCC chat
the TCM bot and do '.auth yournick yourpass' where yournick is your oper
name in your o/O line. In TCM-Dianora and TCM-Hybrid you register with:
'.register yourpass', where yourpass is your password ;)
All TCM commands start with a period. If you forget the period, the text goes
into the 'partyline', where it is echoed to all connected opers.
Resources : http://toast.blackened.com/oomon/help
http://www.db.net/~db/tcm.html
11. Services
A recent addition to EFNet is Channel Fixer, aka ChanFix. This is an
automated service that re-ops clients on opless channels. There are a few
restrictions. First, the channel has to be of significant size for ChanFix
to store it in its database. Second, it only logs static addresses.
How does it work? Periodically it stores information about the channel state
in its database, for every channel in there. On every 'run', a channel
operator gets one point. These scores make a top-5 of 'most frequent opped
clients'. When a channel becomes opless, ChanFix will join and op the top-5
opped clients CURRENTLY IN THE CHANNEL.
Chanfix can be invoked manually by server administrators. /msg ChanFix
chanfix #channel is the command to do it. ChanFix will join, and treat the
channel as if it were opless. It lowers TS by one (resulting in a deop of
the entire channel) and re-ops the top-5 clients currently in the channel.
The Channel Fixer won't log or actively fix channels when there's a split of
significant size. Needless to say, the chanfix command must be used with
caution.
12. G-Lines
Oh yes! A G-Line section. Currently, a part of EFNet (EU-EFnet) has G-Lines
enabled. This was decided by the EU admin community and is now mandatory
within EU-EFnet. In order for a G-Line to be activated, three opers from
three different servers need to issue the _exact_ same G-Line. The reason
is not counted.
G-Lines work best when the EU side of EFNet is not fragmented. G-Lines
will, however, propogate through a Hybrid 6 hub (but not a CSr hub) even
if the hub server has G-Lines disabled. This propogation allows two halves
of EU-EFnet to have concurrent G-Lines set even when split by US hub servers.
Questions / Comments / Suggestions are welcome.
You can e-mail me: dennisv@vuurwerk.nl
Best regards,
--
Dennis "Riedel" Vink ___~___ Email - dennisv@vuurwerk.nl
Unix System Administrator \ | / Phone - +31 23 5111111
Vuurwerk Internet '|.|' PGP - 0xD68A7AAB
And on the seventh day, He exited from append mode.
# $Id: operguide.txt,v 1.1 2002/08/13 14:35:22 fishwaldo Exp $

137
doc/opermyth.txt Normal file
View file

@ -0,0 +1,137 @@
Date: Thu, 30 Jul 1998 16:21:40-0700 (MST)
To: operlist@the-project.org
From: rayp@primenet.com (Ray Powers)
Subject: The myths of opers....
I've always wanted to write something like this.. Its half rant, half
fact, so bear with it. Hopefully it will be worth reading.
There's a lot of hate for opers for a lot of reasons. Some are directly
oper related (i.e. 99% of us are colossal assholes), some are directly
user related (i.e. 99% of you are raving lunatics), and some is just plain
misconceptions. I'd like to take a minute to talk about part three in
hopes of clearing a few things up. This will kind of be in a FAQ form,
maybe you'll like it, maybe not, but its worth a shot.
Q: What can an oper on EFnet do.
A: This is an EXACT list of what we can do:
1) /squit a server, separating it from the rest of the net
2) /die our server
3) /kill a user, this disconnects them from the server they are on
4) /kline a hostmask, this bans them from our server
5) /dline an ip, this bans them from our server, regardless of
hostmask
6) See all invisible users on our server
7) Mass Msg/CTCP/notice a hostmask
8) Mass Msg/CTCP/notice a server
9) See and send Operwall/wallops notices
That's it. We can see more server messages than you, but that's not the
point.. The point to be shown here is very simple, *none* of these things
have anything to do with channels. Which leads us to our next question.
Q: What can opers *NOT* do, but keep being asked to anyways?
A: We can *NOT*:
1) Enter a channel that is +i or +k without being invited or
having the key
2) See who is inside a +s channel
3) Op ourselves or op you on a channel (unless of course we are a
channel op for that channel)
4) Tell you what XXXX's new nick is since they changed it to hide
from you.
5) Deop someone for you on a channel (unless of course we are a
channel op for that channel)
Notice a trend, with the exception of 4, all of these are 100% channel
related. EFnet is made so that opers have *NO* power of channels, for
better or worse. If we don't help you with these requests, its not because
we won't, its because we are completely incapable doing so. On the other
hand....
Q: What can opers do, but won't?
A: This will be a bit differently done, because I figure I should explain
why opers don't do these things, when they may normally make sense.
1) Why won't they kill somebody who has stolen your nick.
EFnet has gone on the basis of nicks not being owned, which is
why there is no nickserv on EFnet. Of course we see opers kill
all the time for nicks, though, so it seems rather hypocrital,
doesn't it?
An oper who kills for his nick will tell you its because the
other person was a bot, was juping his nick, or was imitating an
oper. It may be true, but it really comes down to the same
feeling you get when your nick is taken "Hey! that's my name! I
don't want that person using my name!"
I personally, do not kill for nicks. If someone takes my nick,
they can have it. Let them get my several hundred messages a day.
:P But the problem with the oper is this: How does an oper know
that you are really the person that uses that nick, or are you
the guy that wants to nick jupe that nick out from the real guy?
Unless the oper knows you well, they don't.. And saying that
people generally tell the truth means you haven't been on EFnet
very long.
I would prefer to think I am one of the more well respected
people on the net and people still lie to me on a regular basis.
So, the oper is stuck refusing to help because he can't tell who
is who. Remember this line of reasoning, its going to be coming
up a lot. :P
2) Why won't they kill that guy nuking/smurfing/ping -f'ing me?
This one is simple. There is no way to prove that somebody is
doing any of these things to you from an opers point of view. All
logs are fakeable, and the oper has no way to firsthand prove its
happening. Your best bet in this situation is to log what you can
and complain loud and long to their ISPs.
3) Why won't they help me take my channel back?
There's a bunch of answers to this. First, it is popular
opinion at EFnet that channels are not owned, and therefore, if
you lose a channel, you should go make another one. Notice I
say popular instead of official, because EFnet has never had an
"official" policy on much of anything.
But more and more you see opers killing for takeovers, so why
are they helping their channels and not yours.
Well, first, let's say your channel was taken over, and is now
+smtinlk. How exactly is the oper supposed to find out who is
oped in the channel right now to mass kill them? Even if they do get
all the nicks, they have to somehow manage to kill them all in
one hit, or they'll all just op each other again and it will be
fruitless. Or worse, they could have it all set up, and some
other oper could kill them halfway through because they don't
like mass-kills and it would be all ruined.
Or, let's say the mass-kill goes off, then the channel is
opless and generally speaking, chaos begins. People start
mass-nuking or flooding the channel to clear it out, or just to
be annoying. And there's still a 50/50 chance that takeover
people will get the channel back on a split and we'll have to try
to do it all over again.
If you're about to ask why they don't split their server,
the answer is very simple: We are not about to screw up roughly
30,000 peoples chatting for your channel. Its rude. This of
course is all based on the fact that we can prove its taken over,
as per the conversation about nicks, we often can't.
4) But.. its obvious they took it from me! The topic says
"Ha ha, we took your channel Rick!" for Pete's sake! And
there's only One op, so you can kill him and get the channel
back immediately!
This one is a bit more complex, but its really a personal
call. That one op could be a rampant smurfpup with a penis so
tiny he has no choice but to rampantly smurf and synflood anyone
that gets in his way. This is popularly known on irc as SPS, or
Small Penis Syndrome. In this case, if the oper does help you
out, they could end up with their server being downed for a day
or two, and it really isn't worth it for your channel, no
offense.
Keep in mind that this is all spoken from the perspective of someone who
*DOES* help with channels when possible, but understands greatly the
reasons not to, and judges each situation very carefully.
That's the gist of the information I was trying to get across. If you
were cluefull enough to get on operlist, a lot of this may be common
knowledge to you, but sometimes its good to step back and see why opers do
what they do a lot of the time.
Hoping this is of value to SOMEONE....
Ray Powers
Monkster/MimePunk/PrimeMonk/PacMonk/MtgMonk/Ihavefartoomanynickstonickjupe

124
doc/resv.txt Normal file
View file

@ -0,0 +1,124 @@
/*
* doc/resv.txt - Overview of the resv system
* Lee Hardy <lee@leeh.co.uk>
*
* Copyright (C) 2001 Hybrid Development Team
*
* $Id: resv.txt,v 1.1 2002/08/13 14:35:23 fishwaldo Exp $
*/
RESV
-======-
- What is resv, and why was it coded?
Resv is a method of 'juping' or 'reserving' nicks and channels, to prevent
local clients using them. It is commonly used to block channels which
are home to abusers, and which attract DoS. It can also be used to stop
people pretending to be services, on a network that doesnt support them.
It was coded to replace the method in hybrid-6 of blocking channels and
nicks, and was implemented in a much cleaner way to make it faster.
The hybrid-6 method used to have to physically create channels, and
suffered flaws, resv does not.
- How can I create a resv?
There are two types of resv. 'permanent' and 'temporary'. Temporary
resv's will be erased when a server restarts (they will stay through a
rehash). Permanent resv's will stay through a restart.
Permanent resv's are added into ircd.conf. They should have the reason
for the resv, followed by the nicks and channels being resv'd. The
following would block the channel #services, the nick 'services' and any
nick ending in 'serv' (ie: chanserv)
resv {
reason="There are no services on this network";
channel="#services";
nick="services";
nick="*serv";
};
Temporary resv's can also block nicks, channels, and wildcard nicks.
Although only an admin may create a resv with a wildcard in.
Syntax: /quote resv <#channel|nick> :<reason>
So to resv #warez:
/quote resv #warez :No warez on this network.
To resv kiddie01:
/quote resv kiddie01 :Abuse
To resv clone*:
/quote resv clone* :clones
If a non admin does this, he will see:
-irc.leeh.co.uk- You must be an admin to perform a wildcard RESV
- How do I remove a resv?
If the resv is permanent, then the resv must be removed from ircd.conf,
then a /rehash.
If the resv is temporary, then use the unresv command:
Syntax: /quote unresv <#channel|nick>
- Can I make a resv on all servers?
No. In Hybrid resv's are local only. If a channel is full of abusers,
the solution is not to just block the channel, the abusers themselves
should be removed through /kline and /dline.
- How do I list resv's?
To list all current resv's:
/stats q
Which will give a reply like:
q #warez No warez *@*
Q services No services *@*
If the first letter is a 'q', then the resv is temporary, if the first
letter is a 'Q' then the resv is permanent (in ircd.conf).
- What does a client see if they try using a channel/nick that is resv'd?
They see the numeric 437 (ERR_UNAVAILRESOURCE)
Other networks (namely IRCNet) use this numeric on a split, to indicate
the channel cannot be joined, as such it is recognised by a lot of
clients.
- Can an oper see when someone tries to use a resv'd nick/channel?
No. When there is a valid reason for this, then possibly, but I honestly
dont see why anyone needs it.
- Can I resv a local channel?
Yes. It takes the same format as creating a resv on a normal channel:
/resv &clones :no clonebots!
- Do you support wildcard channel resv's?
No. This is mainly for speed reasons. When we are searching nicks, we
cannot just check if the nick, and the item in the list of resv'd nicks
are string equal, we have to check if they match, so we have to search a
full list. With channels however, we can search a hash table to see if an
entry exists, if it doesnt, then the channel isnt resv'd. We dont have to
search through all the channels.
Besides.. its legal for a channel to be called #*warez* anyway ;)
--
EOF

54
doc/server-version-info Normal file
View file

@ -0,0 +1,54 @@
Server VERSION Info
$Id: server-version-info,v 1.1 2002/08/13 14:35:23 fishwaldo Exp $
Copyright (c) 2001 by ircd-hybrid team
----------------------------------------------------------------------
Updated for Hybrid 7 (2000/12/28)
When you type /version, you will often see something like this:
hybrid-7beta7(20010803_2). irc.leeh.co.uk egGHIKMpTZp TS3ow
Ever wondered what those funny chars mean after the version number? Well
here they are:
+----------------------------+
| 'D' | DEBUGMODE |
|------+---------------------|
| 'e' | USE_EXCEPT |
|------+---------------------|
| 'g' | NO_FAKE_GLINES |
|------+---------------------|
| 'G' | GLINES |
|------+---------------------|
| 'H' | HUB |
|------+---------------------|
| 'I' | USE_INVEX |
|------+---------------------|
| 'K' | USE_KNOCK |
|------+---------------------|
| 'M' | IDLE_FROM_MSG |
|------+---------------------|
| 'p' | CRYPT_OPER_PASSWORD |
|------+---------------------|
| 'T' | IGNORE_BOGUS_TS |
|------+---------------------|
| 'Y' | USE_SYSLOG |
|------+---------------------|
| 'Z' | ZIPLINKS |
|------+---------------------|
| '6' | IPv6 |
|------+---------------------|
| | |
|------+---------------------|
| 'TS' | Supports TS |
|------+---------------------|
| '5' | TS Version 5 |
|------+---------------------|
| 'o' | TS Only |
|------+---------------------|
| 'w' | TS Warnings |
+----------------------------+

167
doc/serverhide.txt Normal file
View file

@ -0,0 +1,167 @@
Server Hide Reference
$Id: serverhide.txt,v 1.1 2002/08/13 14:35:23 fishwaldo Exp $
Copyright (c) 2001 by ircd-hybrid team
----------------------------------------------------------------------
Due to pressures from abusers, the Hybrid developers have created a set of
options to limit what users can and cannot do on the server. Each option
can be enabled or disabled at runtime.
This document describes the Hybrid 7 implementation of the server hiding
ideas originated by (and credited to) numerous people.
*
LINKS as a file: This option is always enabled. It will generate a
file at a certain interval, defined by the links_delay in ircd.conf,
that contains the current LINKS data. This data is sent to users
whenever a LINKS is requested. Opers will always see the current
server structure.
The file that the LINKS data is stored in is by default etc/links.txt.
The benefits of this are that transient splits will not be seen by
users issuing LINKS commands, and if a server is split, users can
still see what other servers are normally available.
*
Flattened LINKS: This option forces every server to look as if it is
connected to the local server. Users will see a flat LINKS tree.
The benefit to using LINKS flattening is that users cannot get
information on how servers are routed.
The flatten_links in the serverhide {} block in the ircd.conf controls
this feature.
As a side effect, all netsplit quit messages will appear to originate
from the local server.
+--------------------------------------------------------------------+
| Flattened LINKS is needed for any network that uses the hidden hub |
| option. See below for more details. |
+--------------------------------------------------------------------+
*
Hidden server option: This option will hide the server from a
flattened LINKS list on other servers. Opers will of course see the
true routing of the network.
This is controlled by the hidden option in ircd.conf.
+--------------------------------------------------------------------+
| Technically, this code is a hack. With this option enabled, the |
| server will prepend '(H) ' to the server info field when |
| connecting to other servers. Other servers must understand that |
| the (H) means hidden. |
+--------------------------------------------------------------------+
*
The allow_hidden option is needed to allow servers to use the hidden
server option described above.
*
The hide_servers option forces the server to not be shown when a user
issues WHOIS and other commands which may show what server a user is
on.
Local user counts, as normally displayed in LUSERS, USERS, and the 255
numeric, will be shown with the same values as the global counts.
Displaying it this way will help protect servers and avoid breaking
scripts that depend on the 265 and 266 numerics on connect.
To be effective, this option must be used network wide.
*
The disable_remote_commands option takes care of most of the remaining
issues. These include, for example, ADMIN some.hub.server, VERSION
someuser, and similar commands. A server with this option enabled will
only prevent local users from issuing remote commands. Remote users
will not be affected.
Remote WHOIS is not blocked. It is, however, restricted to only
querying WHOIS nick nick. The ircd will disregard the server parameter
and always use queried nick.
*
The disable_local_channels option will not allow users to join local
&channels. This option is a little extreme, taking away a lot of user
privilege. It was created to handle the possible hole in server hide
shown below.
*
All server modes appear to originate from the server you are using.
This feature is not tunable; and opers also do not see the real server
setting the mode.
Each item is briefly described in the serverhide {} block in ircd.conf.
----------------------------------------------------------------------
Questions and Answers
&channels and remote WHOIS
I brought this up a short while ago; and there are some holes in server
hide at the present time with local channels. The issue I raised, if a
user is known to be in a local channel, issuing WHOIS servera nick, WHOIS
serverb nick, etc. until the local channel is seen in the WHOIS data does
not exist. With disable_remote_commands enabled, the WHOIS is still sent
(in order to see idle time and the away message) but the server queried
will always be the server the user is on. The user can never use remote
WHOIS to determine the server a user is on.
If an abuser knows that a user is on a specific &channel, they could still
connect to each server until they find the server showing the user in the
local channel in a local WHOIS. The disable_local_channels option has been
created to handle this risk.
----------------------------------------------------------------------
Using Non-QS Compliant Hubs
The flattened LINKS option will, as a side effect, display all user QUIT's
due to network splits in the following format:
:user QUIT :your.server.name *.split
This works extremely well as long as all servers on your network are
compliant with the QS capability, which sends a single SQUIT to the
network when a server (or tree of servers) splits. All quit messages are
generated on the local server. Certain older servers do not have this
ability, and as such will generate their own quit messages for users who
left because of the split. This can cause leaks in the hub server names
and the structure of the network.
A quick example is the following network structure:
servA(Hyb7) --- hubA(nonQS) --- servB(not-important)
When servB splits from hubA, hubA will generate a QUIT command for every
user on servB (and anything behind servB). Since the QUIT message was not
created on your server, with server hiding enabled, the QUIT message will
contain the real server names.
The only way to prevent this leak on a network is to only use hubs
supporting the QS capability. Hybrid 6, Hybrid 7, and csircd all are
currently running daemons that support QS. Hybrid 5 and 2.8.21+CSr servers
do not support QS, and will leak server names (and therefore routing
information) on splits.
----------------------------------------------------------------------
Index
XXX - Fill me in with other questions and possible issues

113
doc/simple.conf Executable file
View file

@ -0,0 +1,113 @@
# Hybrid 7 minimal example configuration file
#
# $Id: simple.conf,v 1.1 2002/08/13 14:35:23 fishwaldo Exp $
#
# This is a basic ircd.conf that will get your server running with
# little modification. See the example.conf for more specific
# information.
#
# The serverinfo block sets up your server's name. Fields that may
# be set are the name, description, vhost, network_name, network_desc,
# and hub.
serverinfo {
name="irc.example.com";
description="Test IRC Server";
hub=no;
};
# The administrator block sets up the server administrator information,
# that is shown when a user issues the /ADMIN command. All three fields
# are required.
administrator {
description="Example, Inc Test IRC Server";
name="John Doe";
email="jdoe@example.com";
};
# Class blocks define the "privileges" that clients and servers get when they
# connect. Ping timing, sendQ size, and user limits are all controlled by
# classes. See example.conf for more information
# Note: to avoid having possible problems later, define class blocks
# before anything that uses them (auth, connect, operator)
class {
name="users";
ping_time=90;
number_per_ip=0;
max_number=200;
sendq=100000;
};
class {
name="opers";
ping_time=90;
number_per_ip=0;
max_number=10;
sendq=500000;
};
# Auth blocks define who can connect and what class they are put into.
auth {
user="*@*";
class="users";
};
# Operator blocks define who is able to use the OPER command and become IRC
# operators. The necessary fields are the user@host, oper nick name, and
# the password, encrypted with the mkpasswd program provided.
operator {
name="JohnDoe";
user="*@*.example.com";
password="yl9xlY019Bbfc";
class="opers";
};
# Listen blocks define what ports your server will listen to client and
# server connections on. ip is an optional field (Essential for virtual
# hosted machines.)
listen {
port=6667;
};
# Quarantine blocks deny certain nicknames from being used.
quarantine {
name="dcc-*";
reason="DCC bots are not permitted on this server";
};
quarantine {
name="LamestBot";
reason="You have to be kidding me!";
};
quarantine {
name="NickServ";
reason="There are no Nick Services on this Network";
};
# The general block contains most of the configurable options that were once
# in config.h. The most important ones are below. For the rest, please see
# NOTE TO DEVELOPERS: Do we set defaults for the variables in the general
# block? If so, then I can leave out most of the things
# in here and make it simpler to configure. If not,
# please let me know so I can document things clearly
general {
# Control nick flooding
anti_nick_flood=yes;
max_nick_time=20;
max_nick_changes=5;
# Show extra warnings when servers connections cannot succeed
# because of no "N" line (a misconfigured connect block)
warn_no_nline=yes;
};
# There are many more configurable options. See example.conf for the rest

Some files were not shown because too many files have changed in this diff Show more