diff options
author | asmodai <asmodai@FreeBSD.org> | 2000-05-26 07:17:19 +0000 |
---|---|---|
committer | asmodai <asmodai@FreeBSD.org> | 2000-05-26 07:17:19 +0000 |
commit | 5ebe58808117d06535d3a3d3ad1de3245fd51505 (patch) | |
tree | 1f43a32dfadca54b81b0c684b2440f827779dde9 /contrib/bind | |
parent | 961b97d43458f3c57241940cabebb3bedf7e4c00 (diff) | |
parent | 3f83b2963e3f1302f6507d3968aa3bfc93d7472d (diff) | |
download | FreeBSD-src-5ebe58808117d06535d3a3d3ad1de3245fd51505.zip FreeBSD-src-5ebe58808117d06535d3a3d3ad1de3245fd51505.tar.gz |
This commit was generated by cvs2svn to compensate for changes in r60940,
which included commits to RCS files with non-trunk default branches.
Diffstat (limited to 'contrib/bind')
96 files changed, 2892 insertions, 1589 deletions
diff --git a/contrib/bind/CHANGES b/contrib/bind/CHANGES index f98fb18..d7c1144 100644 --- a/contrib/bind/CHANGES +++ b/contrib/bind/CHANGES @@ -1,3 +1,283 @@ + --- 8.2.3-T5B (RC3) released --- + +1006. [port] Windows/NT does not have fchown(). + +1005. [bug] RD was sometimes left set, inappropriately. + +1004. [bug] cached NXT's were corrupted. + +1003. [bug] correction to #997. + +1002. [bug] file descriptor leak in res_nclose(). + +1001. [port] some builds were too fast. + + --- 8.2.3-T4B (RC2) released --- + +1000. [bug] #996 was wrongly implemented; replacement fix. + + --- 8.2.3-T3B released --- + + 999. [support] named now makes an effort to create its files with + ownership as specified by -u and -g command options. + + 998. [support] show version number in NOTIFY log messages. + + 997. [support] forwarders are now used in order by measured RTT. + + 996. [protocol] if answering ixfr with full zone, used qtype axfr. + + 995. [bug] "dig -b" was broken due to missing switch "break;" + + 994. [bug] named-xfer did not handle empty question sections. + + 993. [bug] TSIG AXFR was completely broken in DiG. + + 992. [bug] OPTION_USE_IXFR and OPTION_MAINTAIN_IXFR_BASE had + non-single-bit flag values in src/bin/named/ns_defs.h. + + 991. [protocol] send A6 glue records in xfr. + + 990. [bug] we could loose track of a bottom of zone cut is the + write buffer filled up at just the correct moment. + + 989. [bug] apply to "fetch-glue no;" to notify processing. need + to add A records that would be found this way w/ + also-notify. + + 988. [support] report expired zones when detected in maintainence + pass. + + 987. [feature] "ndc reconfig -noexpired" skip attempts to load + expired zoned when reconfiguring. + + 986. [bug] pushlev only needs to be called for axfr/zxfr not ixfr. + + --- 8.2.3-T2B released --- + + 985. [support] remove "view" command from nslookup (it used mktemp()). + + 984. [bug] always restart processing query from scratch if we + have chased a CNAME as we might still have the answer + in the cache once the CNAME has been resolved. + + 983. [support] "notify from non-master server" is now debug, not info. + + 982. [bug] rollback the compression pointers array when a + RRset/RR does not fit. + + 981. [port] decunix: typedef (u_)int#m_t + + 980. [bug] mishandled memget failure w/ TCP connections. + + 979. [bug] we were failing to call ns_stopxfrs() before calling + purge_zone() in some cases. + + 978. [port] sco50: setsockopt(SO_REUSEADDR) fails on unix domain + sockets + + 977. [bug] we should be returning notimpl for update forwarding + rather than refused. a client receiving refused + should terminate the update attempt. notimpl should + just cause the client to skip to the next server. + + 976. [bug] some stats weren't getting incremented, & added a few. + + 975. [support] SLAVE_FORWARD is now redundant and has been removed. + + 974. [port] ultrix with vendor's y2k patch explicitly desupported. + + 973. [bug] some field names added in #935 conflicted with macros. + + 972. [support] restore heartbeat notifies. + + 971. [bug] out of order updates in log. + + 970. [port] solaris: add ipv6 interface scanning support. + + 969. [bug] post process a zone load to remove any non-glue at + or below bottom of zone. + + 968. [bug] TSIGs failed to verify if the key name was compressed. + + 967. [bug] zones signed by the BIND 9 signer failed to load. + + --- 8.2.3-T1A released --- + + 966. [bug] nslookup and dig misprinted root zone in $ORIGIN. + + 965. [feature] dig's command line input buffer was rather small. + + 964. [bug] make res_nsearch() behave like res_search() of olde. + + 963. [bug] res_debug::do_section() can no longer spin all VM. + + 962. [bug] another almost-complete rewrite of IXFR from kjd (462) + + 961. [bug] acl "none" now fails to match but doesn't end search. + + 960. [bug] more hesiod library fixes from danny. + + 959. [doc] christos fixed several man page typos and brainos. + + 958. [bug] getnameinfo() should accept experimental/multicast. + + 957. [port] ultrix again. "cd" now presumed to be silent again. + + 956. [bug] multiline was not being cleared correctly. + + 955. [bug] explicit TTL on SOA records were being replaced with + soa minimum. + + 954. [bug] cannot load a signed root zone. + + 953. [bug] memory overrun in set_zone_ixfr_file(). + + 952. [bug] errs was not being correctly adjusted if the included + master file did not exist in db_load(). + + 951. [bug] contrib/dns_signer/signer: write_trim_name + array bounds write error. + + 950. [bug] hesiod: ctx->res was not being initalised. + + 949. [port] aix32: add prand_conf.h and define WCOREDUMP + + 948. [bug] fixed logic error in a number of expressions causing + res_ninit() not to be called when it should be. + + 947. [bug] sanity check in dst_read_key() wasn't. + + 946. [port] freebsd: threaded library support. + + 945. [bug] wrong file name logged in ixfr_have_log(). + + 944. [doc] add forwarders to zone types master/slave/stub in + named.conf man page. + + 943. [bug] raise CNAME and OTHER / multiple CNAME logging to + warning. + + 942. [bug] bad referrals logged for forwarders. + + 941. [bug] lame server detection wasn't checking for SOA record. + + 940. [clarity] unapproved -> denied in log messages. + + 939. [bug] reload_master and purgeandload should write the zone + if it has been updated. + + 938. [bug] update and ixfr logs could get corrupted. fseek() + before ftell() on fopen(, "a+") file. + + 937. [support] allow parallel makes to work. + + 936. [protocol] add preliminary A6 glue recognition in ns_req. + + 935. [cleanup] res_nsend() segmented into multiple functions for + readability. also fixed two file descriptor leaks. + CAN_RECONNECT is gone, keep one socket per nameserver. + + 934. [bug] Perror and Aerror where incorrect if DEBUG is not + defined. + + 933. [port] cygwin port added + + 932. [port] sco42 does not have unix domain sockets or gethostid. + + 931. [bug] eventlib was not handling unix domain sockets + correctly. + + 930. [bug] we wern't using all the potential compression pointers + in the question section. + + 929. [bug] we were accepting updates (adds) with illegal ttls. + + 928. [bug] if we manage to get a illegal ttl stored, print it + unsigened. + + 927. [port] hpux: (11.* 10.30) Makefile.set.gcc + + 926. [port] hpux10: gcc needs -D_HPUX_SOURCE and -fPIC + + 925. [protocol] when a slave loads it should notify others (RFC 1996). + + 924. [port] sunos solaris: #define NEED_SECURE_DIRECTORY to + secure the directory containing unix domain socket + rather than the socket itself. + + 923. [support] shutup "make clean" about missing threaded directories. + + 922. [bug] removing an cached zone file then performing a + "ndc reload zone" should force a zone transfer. + + 921. [bug] nsupdate: listuprec was not being initalised. + + 920. [port] aix4: Makefile.set.gcc + aix4: __P was being defined by <net/radix.h> + + 919 [port] linux: remove one level of symbolic linkage when + performing make links on port/linux/include + + 918. [bug] update prerequisite could match w/ wildcard. + + 917. [port] irix: make the current IRIX release (6.5) work by + not patching res_debug.c. see INSTALL if you have + problems with 6.3. + + 916. [bug] removing / changing a zone type could result in + Z_NOTIFY being cleared / tested against the wrong zone. + + 915. [bug] evNewWaitList() was not maintaining the prev chain. + + 914. [bug] signal EWOULDBLOCK if EV_POLL'ing with no timers. + + 913. [bug] input could get lost on the server side of a ctl sock. + + 912. [bug] nsupdate now allows explicit 0 TTL's on added RR's. + + 911. [bug] gethostbyname() should not return duplicate addresses. + + 910. [bug] address-sorting logic was exiting early. + + 909. [bug] dig wasn't respecting the +ti and +ret arguments. + + 908. [contrib] Tony Stoneley sent us an updated misc/makezones. + + 907. [port] winnt fixes from Larry at Nortel. + + 906. [bug] res_findzonecut() failed if the NS referred to a CNAME. + + 905. [doc] Minor fix to doc/man/Makefile for getnameinfo + + 904. [bug] bin/host wasn't looking up MX records if no + -t flags were passed to it. + + --- 8.2.2-P6 released --- + + 903. [bug] divide by zero bug when querying for SIG records from + a secure zone. + + 902. [support] don't attempt to set q_fzone if we won't be using it. + + 901. [support] delay notify timer setting until all zones have been + loaded. + + 900. [port] hpux10 fix call to bison; sco call bison consistenly. + + 899. [bug] dynamically allocate buffer used to display RR rather + than uses a fixed sized one. grow as needed. + + 898. [bug] if truncation caused no RR's to appear in the answer we + mis-classified the answer on a NODATA. + + 897. [support] descriptors used by named should not be inherited by + named-xfer. + + 896. [contrib] add contrib/adm/adm-nxt, an exploit for the NXT bug + in 8.2 and 8.2.1. as before, we do not recommend its + use, and we do recommend that you run the latest BIND. + --- 8.2.2-P5 released --- 895. [port] minor NT build and documentation improvements. diff --git a/contrib/bind/INSTALL b/contrib/bind/INSTALL index 165f529..6307f2b 100644 --- a/contrib/bind/INSTALL +++ b/contrib/bind/INSTALL @@ -1,23 +1,25 @@ Systems it is known to compile and run on: BSD/OS 3.1, 4.0.1 - FreeBSD 3.1, 3.2, 3.3 + FreeBSD 3.3, 3.4 RH Linux 5.2 (don't use "make links" when building, though) Debian GNU/Linux 2.2.9 ("unreleased") Digital UNIX 3.2C, 4.0, 5.0 NetBSD/i386 1.3.2, 1.4 SunOS 5.6 (Solaris 2.6), SunOS 5.7 (Solaris 7) SCO UnixWare 7.0, 7.0.1, 7.1 + IRIX 6.5 Systems it has been known in the past to compile and run on: AIX 4.x A/UX 3.1.1 - Digital ULTRIX 4.5 + Digital ULTRIX 4.5 (without Compaq's Y2K kit installed) HP MPE HP-UX 9.x, 10.20 IRIX 5.3, 6.2, 6.4 LynxOS + FreeBSD 3.1, 3.2 NetBSD 1.2, 1.3 OpenBSD 2.1 QNX @@ -139,6 +141,12 @@ Operating System Notes The kit should compile even if you have intalled the KAME IPv6 kit. + IRIX + build problems have been reported w/ IRIX 6.3, res_debug.c + and #include <stdlib.h>. You may need to comment out + the #include <stdlib.h> and declare + "void *malloc(size_t size)" to get named to compile on 6.3. + Linux "make links" and "make stdlinks" cause problems on diff --git a/contrib/bind/Makefile b/contrib/bind/Makefile index d771aab..5df7fdc 100644 --- a/contrib/bind/Makefile +++ b/contrib/bind/Makefile @@ -1,4 +1,4 @@ -## Copyright (c) 1996,1999 by Internet Software Consortium, Inc. +## Copyright (c) 1996,1999 by Internet Software Consortium. ## ## Permission to use, copy, modify, and distribute this software for any ## purpose with or without fee is hereby granted, provided that the above @@ -13,55 +13,56 @@ ## ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS ## SOFTWARE. -# $Id: Makefile,v 1.9 1999/11/05 04:52:54 vixie Exp $ +# $Id: Makefile,v 8.51 1999/11/06 03:24:02 vixie Exp $ -# This is just for making distributions. For the real Makefile, cd src. +TOP= +SUBDIRS= include port lib bin -all clean depend: FRC - @echo go to the ./src directory, you cannot make '"'$@'"' here. - @false +SH=sh -tar: bind-doc.tar.gz bind-src.tar.gz bind-contrib.tar.gz +default: all -pgp: bind-doc.tar.gz.asc bind-src.tar.gz.asc bind-contrib.tar.gz.asc +all clean depend install distclean:: FRC + @set -e; \ + version=`cat ${TOP}Version`; \ + systype=`${SH} ${TOP}port/systype ${TOP}.systype`; \ + if [ $$systype = "unknown" ]; then \ + echo "There is no BIND port for this system in this kit."; \ + else \ + settings=`${SH} ${TOP}port/settings ${TOP}.settings \ + < ${TOP}port/$$systype/Makefile.set`; \ + PATH=`pwd`/port/$$systype/bin:$$PATH; export PATH; \ + for x in ${SUBDIRS}; do \ + ( cd $$x; pwd; \ + eval "${MAKE} $$settings ${MARGS} SYSTYPE=$$systype \ + VER=$$version \ + $@"; \ + ); \ + done \ + fi -bind-doc.tar.gz: Makefile - cd doc/bog; make clean file.psf file.lst - cd doc/man; make clean all - cd doc/man; make MANROFF="groff -t" OUT_EXT=psf clean all - tar cf - Makefile doc | gzip > bind-doc.tar.gz - cd doc/man; make clean - cd doc/man; make MANROFF="groff -t" OUT_EXT=psf clean +clean distclean:: + rm -f .systype .settings -bind-src.tar.gz: Makefile - cd src; make distclean - cd src/bin/nslookup; make commands.c - cd src/bin/named; make ns_parser.c - tar cf - Makefile src | gzip > bind-src.tar.gz +links: FRC + @set -e; mkdir ${DST}; cd ${DST}; pwd; ln -s ${SRC} SRC; \ + ln -s SRC/Version .; cp SRC/Makefile .; chmod +w Makefile; \ + systype=`${SH} SRC/port/systype`; \ + for x in ${SUBDIRS} ; do \ + ( mkdir $$x; cd $$x; pwd; ln -s ../SRC/$$x SRC; \ + cp SRC/Makefile Makefile; chmod +w Makefile; \ + ${MAKE} ${MARGS} SYSTYPE=$$systype links; \ + ); \ + done -bind-contrib.tar.gz: Makefile - tar cf - Makefile contrib | gzip > bind-contrib.tar.gz +stdlinks: FRC + if [ ! -d /var/obj ]; then \ + mkdir /var/obj; \ + fi + ${MAKE} ${MARGS} SRC=`pwd` DST=/var/obj/bind links -bind-doc.tar.gz.asc: bind-doc.tar.gz - rm -f bind-doc.tar.gz.asc - pgp -u pgpkey@isc.org -sba bind-doc.tar.gz - -bind-src.tar.gz.asc: bind-src.tar.gz - rm -f bind-src.tar.gz.asc - pgp -u pgpkey@isc.org -sba bind-src.tar.gz - -bind-contrib.tar.gz.asc: bind-contrib.tar.gz - rm -f bind-contrib.tar.gz.asc - pgp -u pgpkey@isc.org -sba bind-contrib.tar.gz - -noesw: src/Version src/lib/Makefile src/lib/dst/Makefile \ - src/lib/cylink/. src/lib/dnssafe/. - perl -pi.BAK -e 's/$$/-NOESW/' src/Version - perl -pi.BAK -e 's/ cylink dnssafe//' src/lib/Makefile - perl -pi.BAK -e 's:-I../cylink::' src/lib/dst/Makefile - perl -pi.BAK -e 's:-I../dnssafe::' src/lib/dst/Makefile - perl -pi.BAK -e 's/-DCYLINK_DSS//' src/lib/dst/Makefile - perl -pi.BAK -e 's/-DDNSSAFE//' src/lib/dst/Makefile - rm -rf src/lib/cylink src/lib/dnssafe +uplinks: FRC + @set -e; systype=`${SH} ${TOP}port/systype`; pwd=`pwd`; \ + ${MAKE} ${MARGS} SRC=../`basename $$pwd` "DST=../$$systype" links FRC: diff --git a/contrib/bind/README b/contrib/bind/README index 10a3f3b..65f9664 100644 --- a/contrib/bind/README +++ b/contrib/bind/README @@ -1,5 +1,5 @@ -This is the source portion of BIND version 8.2.2, Patchlevel 5. Its -companions are "doc" and "contrib" so you are probably not missing anything. +This is the source portion of BIND version 8.2.3-T2B. Its companions +are "doc" and "contrib" so you are probably not missing anything. See the CHANGES file for a detailed listing of all changes. See the INSTALL file for information on building and installing BIND. @@ -208,6 +208,6 @@ To Support the Effort The Internet Software Consortium has also commissioned a DHCP server implementation, has taken over official support/release of the INN - system, and supports the Kerberos Version 5 effort at MIT. You can - learn more about the ISC's goals and accomplishments from the web page - at <URL:http://www.isc.org/>. + system, and has supported the Kerberos Version 5 effort at MIT. You + can learn more about the ISC's goals and accomplishments from the web + page at <URL:http://www.isc.org/>. diff --git a/contrib/bind/SUPPORT b/contrib/bind/SUPPORT index 1f12ba8..5172918 100644 --- a/contrib/bind/SUPPORT +++ b/contrib/bind/SUPPORT @@ -1,10 +1,9 @@ -> The Internet Software Consortium now offers support agreements for ISC -> software. Under these programs, organizations using BIND, DHCP or INN -> from ISC can obtain a range of on call assistance, bug fixes, training and -> consultation services. These programs are documented on our web page at: -> -> http://www.isc.org/support.html -> -> Discussion about programs to meet your needs is welcome at -> clientservices@isc.org. Please forward your questions there or call us at -> +1 650 779-7018 to speak with the Director of Client Services. +The Internet Software Consortium offers, through certified providers, support, +training, and consulting for BIND and DHCP. These programs are documented on +our web page at: + + http://www.isc.org/support.html + +Discussion about programs to meet your needs is welcome at sales@isc.org. +Please forward your questions there or call us at +1 650 779-7018 to speak +with the Director of Client Services. diff --git a/contrib/bind/Version b/contrib/bind/Version index b14fd71..f8403c5 100644 --- a/contrib/bind/Version +++ b/contrib/bind/Version @@ -1 +1 @@ -8.2.2-P5-NOESW +8.2.3-T5B diff --git a/contrib/bind/bin/dig/dig.c b/contrib/bind/bin/dig/dig.c index 4e75c13..8d5f5be 100644 --- a/contrib/bind/bin/dig/dig.c +++ b/contrib/bind/bin/dig/dig.c @@ -1,5 +1,5 @@ #ifndef lint -static const char rcsid[] = "$Id: dig.c,v 8.36 1999/11/05 05:05:14 vixie Exp $"; +static const char rcsid[] = "$Id: dig.c,v 8.41 2000/04/20 07:36:04 vixie Exp $"; #endif /* @@ -184,8 +184,8 @@ static const char rcsid[] = "$Id: dig.c,v 8.36 1999/11/05 05:05:14 vixie Exp $"; /* Global. */ -#define VERSION 82 -#define VSTRING "8.2" +#define VERSION 83 +#define VSTRING "8.3" #define PRF_DEF 0x2ff9 #define PRF_MIN 0xA930 @@ -270,14 +270,14 @@ main(int argc, char **argv) { ns_type xfr = ns_t_invalid; int bytes_out, bytes_in; - char cmd[256]; + char cmd[512]; char domain[MAXDNAME]; char msg[120], *msgptr; char **vtmp; char *args[DIG_MAXARGS]; char **ax; int once = 1, dofile = 0; /* batch -vs- interactive control */ - char fileq[100]; + char fileq[384]; int fp; int wait=0, delay; int envset=0, envsave=0; @@ -357,8 +357,10 @@ main(int argc, char **argv) { while ((dofile && fgets(fileq, sizeof fileq, qfp) != NULL) || (!dofile && once--)) { - if (*fileq == '\n' || *fileq == '#' || *fileq==';') - continue; /* ignore blank lines & comments */ + if (*fileq == '\n' || *fileq == '#' || *fileq==';') { + printf("%s", fileq); /* echo but otherwise ignore */ + continue; /* blank lines and comments */ + } /* * "Sticky" requests that before current parsing args @@ -512,7 +514,8 @@ main(int argc, char **argv) { ";; bad -b addr\n"); exit(1); } - } + } + break; case 'k': /* -k keydir:keyname */ @@ -946,7 +949,7 @@ where: server,\n\ fputs("\ notes: defname and search don't work; use fully-qualified names.\n\ this is DiG version " VSTRING "\n\ - $Id: dig.c,v 8.36 1999/11/05 05:05:14 vixie Exp $\n\ + $Id: dig.c,v 8.41 2000/04/20 07:36:04 vixie Exp $\n\ ", stderr); } @@ -1104,6 +1107,7 @@ res_re_init() { static char localdomain[] = "LOCALDOMAIN"; u_long pfcode = res.pfcode, options = res.options; unsigned ndots = res.ndots; + int retrans = res.retrans, retry = res.retry; char *buf; /* @@ -1116,6 +1120,8 @@ res_re_init() { res.pfcode = pfcode; res.options = options; res.ndots = ndots; + res.retrans = retrans; + res.retry = retry; } /* @@ -1185,7 +1191,7 @@ printZone(ns_type xfr, const char *zone, const struct sockaddr_in *sin, u_char *newmsg; int newmsglen; ns_tcp_tsig_state tsig_state; - int tsig_ret; + int tsig_ret, tsig_required, tsig_present; switch (xfr) { case ns_t_axfr: @@ -1403,18 +1409,6 @@ printZone(ns_type xfr, const char *zone, const struct sockaddr_in *sin, break; } - /* - * Verify the TSIG - */ - - if (key) { - tsig_ret = ns_verify_tcp(answer, &len, &tsig_state, 1); - if (tsig_ret == 0) - printf("; TSIG ok\n"); - else - printf("; TSIG invalid\n"); - } - result = print_axfr(stdout, answer, len); if (result != 0) { error = ERR_PRINTING; @@ -1475,6 +1469,30 @@ printZone(ns_type xfr, const char *zone, const struct sockaddr_in *sin, break; } } + + /* + * Verify the TSIG + */ + + if (key) { + if (ns_find_tsig(answer, answer + len) != NULL) + tsig_present = 1; + else + tsig_present = 0; + if (numAnswers == 1 || soacnt > 1) + tsig_required = 1; + else + tsig_required = 0; + tsig_ret = ns_verify_tcp(answer, &len, &tsig_state, + tsig_required); + if (tsig_ret == 0) { + if (tsig_present) + printf("; TSIG ok\n"); + } + else + printf("; TSIG invalid\n"); + } + } printf(";; Received %d answer%s (%d record%s).\n", @@ -1570,8 +1588,12 @@ print_axfr(FILE *file, const u_char *msg, size_t msglen) { } name = ns_rr_name(rr); if (origin[0] == '\0' && name[0] != '\0') { - fprintf(file, "$ORIGIN %s.\n", name); - strcpy(origin, name); + if (strcmp(name, ".") != 0) + strcpy(origin, name); + fprintf(file, "$ORIGIN %s.\n", origin); + if (strcmp(name, ".") == 0) + strcpy(origin, name); + strcpy(name_ctx, "@"); } if (ns_sprintrr(&handle, &rr, name_ctx, origin, buf, sizeof buf) < 0) { diff --git a/contrib/bind/bin/host/host.c b/contrib/bind/bin/host/host.c index bcfbe02..1a66b8b 100644 --- a/contrib/bind/bin/host/host.c +++ b/contrib/bind/bin/host/host.c @@ -1,5 +1,5 @@ #ifndef lint -static const char rcsid[] = "$Id: host.c,v 8.34 1999/11/11 19:39:10 cyarnell Exp $"; +static const char rcsid[] = "$Id: host.c,v 8.36 2000/01/25 00:20:21 cyarnell Exp $"; #endif /* not lint */ /* @@ -171,7 +171,7 @@ static char *cname = NULL; static const char *progname = "amnesia"; static int getclass = ns_c_in, verbose = 0, list = 0; static int server_specified = 0; -static int gettype; +static int gettype = 0; static char getdomain[NS_MAXDNAME]; /* Forward. */ @@ -270,7 +270,7 @@ main(int argc, char **argv) { /*NOTREACHED*/ } } - if (gettype == 0) { + if ((gettype == 0) && (sigchase)) { if (verbose) printf ("Forcing `-t a' for signature trace.\n"); gettype = ns_t_a; diff --git a/contrib/bind/bin/irpd/Makefile b/contrib/bind/bin/irpd/Makefile index 6f94d63..4d2c0fc 100644 --- a/contrib/bind/bin/irpd/Makefile +++ b/contrib/bind/bin/irpd/Makefile @@ -13,7 +13,7 @@ ## ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS ## SOFTWARE. -# $Id: Makefile,v 1.3 1999/02/22 02:47:55 vixie Exp $ +# $Id: Makefile,v 1.4 2000/05/09 07:02:22 vixie Exp $ DESTDIR= CC= cc @@ -68,7 +68,7 @@ tmp_version.c: version.c Makefile ../Makefile ${SRCS} ${HDRS} (u=$${USER-root} d=`pwd` h=`${HOSTNAMECMD}` t=`date`; \ sed -e "s|%WHEN%|$${t}|" -e "s|%VERSION%|"${VER}"|" \ -e "s|%WHOANDWHERE%|$${u}@$${h}:$${d}|" \ - < version.c > tmp_version.c) + < version.c > tmp_version.c); sleep 1 distclean: clean diff --git a/contrib/bind/bin/irpd/irpd.c b/contrib/bind/bin/irpd/irpd.c index a2b13cb..4a94d2c 100644 --- a/contrib/bind/bin/irpd/irpd.c +++ b/contrib/bind/bin/irpd/irpd.c @@ -37,7 +37,7 @@ seem to be so for getnetbyaddr #endif #if defined(LIBC_SCCS) && !defined(lint) -static const char rcsid[] = "$Id: irpd.c,v 1.7 1999/10/13 16:26:23 vixie Exp $"; +static const char rcsid[] = "$Id: irpd.c,v 1.8 2000/02/04 08:28:27 vixie Exp $"; #endif /* LIBC_SCCS and not lint */ /* Imports. */ @@ -329,7 +329,9 @@ int main(int argc, char **argv) { struct ctl_sctx *ctx; struct sockaddr *addr; +#ifndef NO_SOCKADDR_UN struct sockaddr_un uaddr; +#endif struct sockaddr_in iaddr; log_channel chan; short port = IRPD_PORT; @@ -358,11 +360,13 @@ main(int argc, char **argv) { } break; +#ifndef NO_SOCKADDR_UN case 'u': sockname = optarg; addr = (struct sockaddr *)&uaddr; socksize = sizeof uaddr; break; +#endif case 'h': case '?': @@ -374,7 +378,6 @@ main(int argc, char **argv) { argc -= optind; argv += optind; - memset(&uaddr, 0, sizeof uaddr); memset(&iaddr, 0, sizeof iaddr); #ifdef HAVE_SA_LEN @@ -384,17 +387,21 @@ main(int argc, char **argv) { iaddr.sin_port = htons(IRPD_PORT); iaddr.sin_addr.s_addr = htonl(INADDR_ANY); - uaddr.sun_family = AF_UNIX; - strncpy(uaddr.sun_path, sockname, sizeof uaddr.sun_path); +#ifndef NO_SOCKADDR_UN + memset(&uaddr, 0, sizeof uaddr); + if (addr == (struct sockaddr *)&uaddr) { + uaddr.sun_family = AF_UNIX; + strncpy(uaddr.sun_path, sockname, sizeof uaddr.sun_path); #ifdef HAVE_SA_LEN - uaddr.sun_len = SUN_LEN(&uaddr); + uaddr.sun_len = SUN_LEN(&uaddr); #endif - if (addr == (struct sockaddr *)&uaddr) socksize = SUN_LEN(&uaddr); - /* XXX what if this file is not currently a socket? */ - unlink(sockname); + /* XXX what if this file is not currently a socket? */ + unlink(sockname); + } +#endif evCreate(&ev); diff --git a/contrib/bind/bin/named/db_defs.h b/contrib/bind/bin/named/db_defs.h index 9fe2021..6fad285 100644 --- a/contrib/bind/bin/named/db_defs.h +++ b/contrib/bind/bin/named/db_defs.h @@ -1,6 +1,6 @@ /* * from db.h 4.16 (Berkeley) 6/1/90 - * $Id: db_defs.h,v 8.36 1999/08/26 18:42:32 vixie Exp $ + * $Id: db_defs.h,v 8.38 2000/04/21 06:54:01 vixie Exp $ */ /* @@ -57,7 +57,7 @@ */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -307,3 +307,7 @@ struct db_rrset { if (((x)->d_rcnt)-- == 0) \ ns_panic(ns_log_db, 1, "d_rcnt-- == 0"); \ } while (0) + +#define ISVALIDGLUE(xdp) ((xdp)->d_type == T_NS || (xdp)->d_type == T_A \ + || (xdp)->d_type == T_AAAA || (xdp)->d_type == ns_t_a6) + diff --git a/contrib/bind/bin/named/db_dump.c b/contrib/bind/bin/named/db_dump.c index 75a59b7..10acb8c 100644 --- a/contrib/bind/bin/named/db_dump.c +++ b/contrib/bind/bin/named/db_dump.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)db_dump.c 4.33 (Berkeley) 3/3/91"; -static const char rcsid[] = "$Id: db_dump.c,v 8.40 1999/10/13 16:39:01 vixie Exp $"; +static const char rcsid[] = "$Id: db_dump.c,v 8.43 2000/04/21 06:54:01 vixie Exp $"; #endif /* not lint */ /* @@ -82,7 +82,7 @@ static const char rcsid[] = "$Id: db_dump.c,v 8.40 1999/10/13 16:39:01 vixie Exp */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -144,6 +144,8 @@ doadump() fprintf(fp, "; Dumped at %s", ctimel(tt.tv_sec)); if (zones != NULL && nzones != 0) zt_dump(fp); + if (fwddata != NULL && fwddata_count != 0) + fwd_dump(fp); fputs( "; Note: Cr=(auth,answer,addtnl,cache) tag only shown for non-auth RR's\n", fp); @@ -202,6 +204,18 @@ zt_dump(FILE *fp) { fprintf(fp, ";; --zone table--\n"); return (0); } +int +fwd_dump(FILE *fp) { + int i; + fprintf(fp, ";; ++forwarders table++\n"); + for (i=0;i<fwddata_count;i++) { + fprintf(fp,"; %s rtt=%d\n", + inet_ntoa(fwddata[i]->fwdaddr.sin_addr), + fwddata[i]->nsdata->d_nstime); + } + fprintf(fp, ";; --forwarders table--\n"); + return (0); +} int db_dump(struct hashbuf *htp, FILE *fp, int zone, char *origin) { @@ -276,9 +290,9 @@ db_dump(struct hashbuf *htp, FILE *fp, int zone, char *origin) { fprintf(fp, "%d\t", (int)(dp->d_ttl - tt.tv_sec)); } else if (dp->d_ttl != USE_MINIMUM) - fprintf(fp, "%d\t", (int)dp->d_ttl); + fprintf(fp, "%u\t", dp->d_ttl); else - fprintf(fp, "%d\t", + fprintf(fp, "%u\t", zones[dp->d_zone].z_minimum); fprintf(fp, "%s\t%s\t", p_class(dp->d_class), diff --git a/contrib/bind/bin/named/db_func.h b/contrib/bind/bin/named/db_func.h index 9ba5299..cb83beb 100644 --- a/contrib/bind/bin/named/db_func.h +++ b/contrib/bind/bin/named/db_func.h @@ -52,7 +52,7 @@ */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -90,7 +90,7 @@ /* db_proc.h - prototypes for functions in db_*.c * - * $Id: db_func.h,v 8.40 1999/10/07 08:24:06 vixie Exp $ + * $Id: db_func.h,v 8.42 2000/04/21 06:54:02 vixie Exp $ */ /* ++from db_update.c++ */ @@ -101,7 +101,7 @@ extern int db_update(const char *name, int flags, struct hashbuf *htp, struct sockaddr_in from), - db_cmp(const struct databuf *, const struct databuf *), + db_cmp(const struct databuf *, const struct databuf *), findMyZone(struct namebuf *np, int class); void fixttl(struct databuf *dp); /* --from db_update.c-- */ @@ -187,7 +187,7 @@ extern int match(struct databuf *, int, int), /* --from db_lookup.c-- */ /* ++from db_ixfr.c++ */ -struct ns_updrec * ixfr_get_change_list(struct zoneinfo *, u_int32_t, +extern ns_deltalist * ixfr_get_change_list(struct zoneinfo *, u_int32_t, u_int32_t); int ixfr_have_log(struct zoneinfo *, u_int32_t, u_int32_t); diff --git a/contrib/bind/bin/named/db_glob.h b/contrib/bind/bin/named/db_glob.h index 3d11739..cfd7abb 100644 --- a/contrib/bind/bin/named/db_glob.h +++ b/contrib/bind/bin/named/db_glob.h @@ -1,6 +1,6 @@ /* * from db.h 4.16 (Berkeley) 6/1/90 - * $Id: db_glob.h,v 8.12 1999/08/08 21:10:01 vixie Exp $ + * $Id: db_glob.h,v 8.14 2000/04/21 06:54:02 vixie Exp $ */ /* @@ -57,7 +57,7 @@ */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -95,6 +95,7 @@ DECL struct hashbuf *fcachetab INIT(NULL); /* state of ns_reload() and ns_reconfig(). */ DECL int reloading INIT(0); DECL int reconfiging INIT(0); +DECL int noexpired INIT(0); DECL const int hashsizes[] #ifdef MAIN_PROGRAM diff --git a/contrib/bind/bin/named/db_glue.c b/contrib/bind/bin/named/db_glue.c index f1fae69..8c48465 100644 --- a/contrib/bind/bin/named/db_glue.c +++ b/contrib/bind/bin/named/db_glue.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)db_glue.c 4.4 (Berkeley) 6/1/90"; -static const char rcsid[] = "$Id: db_glue.c,v 8.39 1999/10/15 19:48:57 vixie Exp $"; +static const char rcsid[] = "$Id: db_glue.c,v 8.40 2000/04/21 06:54:02 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: db_glue.c,v 8.39 1999/10/15 19:48:57 vixie Exp */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/db_ixfr.c b/contrib/bind/bin/named/db_ixfr.c index a009f4d..7a50618 100644 --- a/contrib/bind/bin/named/db_ixfr.c +++ b/contrib/bind/bin/named/db_ixfr.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) -static char rcsid[] = "$Id: db_ixfr.c,v 8.18 1999/10/15 19:48:57 vixie Exp $"; -#endif /* not lint */ +static char rcsid[] = "$Id: db_ixfr.c,v 8.20 2000/02/29 05:15:03 vixie Exp $"; +#endif /* * Portions Copyright (c) 1999 by Check Point Software Technologies, Inc. @@ -51,81 +51,137 @@ static char rcsid[] = "$Id: db_ixfr.c,v 8.18 1999/10/15 19:48:57 vixie Exp $ #include <isc/eventlib.h> #include <isc/logging.h> +#include <isc/memcluster.h> #include "port_after.h" #include "named.h" -#define DBIXFR_ERROR -1 -#define DBIXFR_FOUND_RR 2 -#define DBIXFR_END 3 +#define DBIXFR_ERROR (-1) +#define DBIXFR_FOUND_RR 2 +#define DBIXFR_END 3 -static int ixfr_getrr(struct zoneinfo *, FILE *, const char *, char *, - ns_updrec **, u_int32_t *, u_int32_t *); +static int ixfr_getdelta(struct zoneinfo *, FILE *, const char *, char *, + ns_updque *, u_int32_t *, u_int32_t *); -ns_updrec * +ns_deltalist * ixfr_get_change_list(struct zoneinfo *zp, u_int32_t from_serial, u_int32_t to_serial) { - FILE * fp; + FILE * fp = NULL; u_int32_t old_serial, new_serial; char origin[MAXDNAME]; - struct namebuf *np, *listnp, *finlistnp; - LIST(ns_updrec) listuprec; - int ret, mode; + ns_deltalist *dlhead = NULL; + int ret; ns_updrec *uprec; + ns_delta *dl; if (SEQ_GT(from_serial, to_serial)) return (NULL); - listnp = finlistnp = NULL; - INIT_LIST(listuprec); + + dlhead = memget(sizeof(*dlhead)); + if (dlhead == NULL) + return (NULL); + INIT_LIST(*dlhead); + if ((fp = fopen(zp->z_ixfr_base, "r")) == NULL) { ns_warning(ns_log_db, "%s: %s", zp->z_ixfr_base, strerror(errno)); - return (NULL); + goto cleanup; } strcpy(origin, zp->z_origin); lineno = 1; - np = NULL; - mode = 0; old_serial = new_serial = 0; + for (;;) { - ret = ixfr_getrr(zp, fp, zp->z_ixfr_base, origin, &uprec, - &old_serial, &new_serial); + dl = memget(sizeof *dl); + if (dl == NULL) { + ns_warning(ns_log_db, + "ixfr_get_change_list: out of memory"); + goto cleanup; + } + INIT_LINK(dl, d_link); + INIT_LIST(dl->d_changes); + ret = ixfr_getdelta(zp, fp, zp->z_ixfr_base, origin, &dl->d_changes, + &old_serial, &new_serial); switch (ret) { case DBIXFR_ERROR: - (void) my_fclose(fp); - ns_warning(ns_log_db, "Logical error in %s line %d", - zp->z_ixfr_base, lineno); - return (NULL); + ns_warning(ns_log_db, "Logical error in %s: unlinking", + zp->z_ixfr_base); + unlink(zp->z_ixfr_base); + goto cleanup; + case DBIXFR_FOUND_RR: - if (EMPTY(listuprec)) { + ns_debug(ns_log_default, 4, "ixfr_getdelta DBIXFR_FOUND_RR (%s)", + zp->z_origin); + if (EMPTY(*dlhead)) { /* skip updates prior to the one we want */ - if (uprec->r_zone != from_serial) { - while (uprec != NULL) { - ns_updrec *prev; + uprec = HEAD(dl->d_changes); + INSIST(uprec != NULL); + if ((uprec->r_zone < from_serial) || + (uprec->r_zone > to_serial)) + { + while ((uprec = HEAD(dl->d_changes)) != NULL) { + UNLINK(dl->d_changes, uprec, r_link); if (uprec->r_dp != NULL) - db_freedata(uprec->r_dp); + db_freedata(uprec->r_dp); uprec->r_dp = NULL; - prev = PREV(uprec, r_link); res_freeupdrec(uprec); - uprec = prev; } + memput(dl, sizeof *dl); break; } + else if (uprec->r_zone > from_serial) { + /* missed the boat */ + ns_debug(ns_log_default, 3, + "ixfr_getdelta first SOA is %d, asked for %d (%s)", + uprec->r_zone, + from_serial, + zp->z_origin); + goto cleanup; + } } - APPEND(listuprec, uprec, r_link); - /* continue; */ + ns_debug(ns_log_default, 4, + "adding to change list (%s)", + zp->z_origin); + APPEND(*dlhead, dl, d_link); break; + case DBIXFR_END: + ns_debug(ns_log_default, 4, + "ixfr_getdelta DBIXFR_END (%s)", + zp->z_origin); (void) my_fclose(fp); - return (HEAD(listuprec)); + memput(dl, sizeof *dl); + return (dlhead); + default: (void) my_fclose(fp); + if (dl != NULL) + memput(dl, sizeof *dl); return (NULL); } } + + cleanup: + if (fp != NULL) + (void) my_fclose(fp); + + while ((dl = HEAD(*dlhead)) != NULL) { + UNLINK(*dlhead, dl, d_link); + while ((uprec = HEAD(dl->d_changes)) != NULL) { + UNLINK(dl->d_changes, uprec, r_link); + + if (uprec->r_dp != NULL) + db_freedata(uprec->r_dp); + uprec->r_dp = NULL; + res_freeupdrec(uprec); + } + memput(dl, sizeof *dl); + } + memput(dlhead, sizeof *dlhead); + return (NULL); } /* @@ -137,7 +193,7 @@ ixfr_get_change_list(struct zoneinfo *zp, * * returns: * 0 = serial number is up to date - * 1 = transision is possible + * 1 = transmission is possible * -1 = error while opening the ixfr transaction log * -2 = error in parameters * -3 = logical error in the history file @@ -147,14 +203,17 @@ ixfr_have_log(struct zoneinfo *zp, u_int32_t from_serial, u_int32_t to_serial) { FILE *fp; u_int32_t old_serial = 0, new_serial = 0; + u_int32_t last_serial = 0; + u_int32_t first_serial = 0; char buf[BUFSIZ]; char *cp; struct stat st; int nonempty_lineno = -1, prev_pktdone = 0, cont = 0, inside_next = 0; int err; + int first = 0; + int rval = 0; int id, rcode = NOERROR; - if (SEQ_GT(from_serial, to_serial)) return (-2); if (from_serial == to_serial) @@ -162,6 +221,10 @@ ixfr_have_log(struct zoneinfo *zp, u_int32_t from_serial, u_int32_t to_serial) /* If there is no log file, just return. */ if (zp->z_ixfr_base == NULL || zp->z_updatelog == NULL) return (-1); + if (zp->z_serial_ixfr_start > 0) { + if (from_serial >= zp->z_serial_ixfr_start) + return (1); + } if (stat(zp->z_ixfr_base, &st) < 0) { if (errno != ENOENT) ns_error(ns_log_db, @@ -176,17 +239,18 @@ ixfr_have_log(struct zoneinfo *zp, u_int32_t from_serial, u_int32_t to_serial) } if (fgets(buf, sizeof(buf), fp) == NULL) { ns_error(ns_log_update, "fgets() from %s failed: %s", - zp->z_updatelog, strerror(errno)); + zp->z_ixfr_base, strerror(errno)); fclose(fp); return (-1); } if (strcmp(buf, LogSignature) != 0) { ns_error(ns_log_update, "invalid log file %s", - zp->z_updatelog); + zp->z_ixfr_base); fclose(fp); return (-3); } lineno = 1; + first = 1; for (;;) { if (getword(buf, sizeof buf, fp, 0)) { nonempty_lineno = lineno; @@ -214,12 +278,13 @@ ixfr_have_log(struct zoneinfo *zp, u_int32_t from_serial, u_int32_t to_serial) if (cp != NULL) lineno++; if (sscanf((char *) cp, "%u", &old_serial)) { + if (first == 1) { + first = 0; + first_serial = old_serial; + } + last_serial = old_serial; if (from_serial >= old_serial) { - fclose(fp); - return (1); - } else { - fclose(fp); - return (-1); + rval = 1; } } prev_pktdone = 1; @@ -232,14 +297,16 @@ ixfr_have_log(struct zoneinfo *zp, u_int32_t from_serial, u_int32_t to_serial) if (cp == NULL || sscanf((char *) cp, "from %u to %u", &old_serial, &new_serial) != 2) { - fclose(fp); - return (-3); + rval = -3; + break; } else if (from_serial >= old_serial) { - fclose(fp); - return (1); + if (first == 1) { + first = 0; + first_serial = old_serial; + } + last_serial = old_serial; + rval = 1; } - fclose(fp); - return (-1); } if (prev_pktdone) { prev_pktdone = 0; @@ -248,7 +315,19 @@ ixfr_have_log(struct zoneinfo *zp, u_int32_t from_serial, u_int32_t to_serial) } } fclose(fp); - return (0); + if (last_serial +1 < zp->z_serial) { + ns_warning(ns_log_db, + "%s: File Deleted. Found gap between serial:" + " %d and current serial: %d", + zp->z_ixfr_base, last_serial, zp->z_serial); + (void) unlink(zp->z_ixfr_base); + rval = -3; + } + if (from_serial < first_serial || from_serial > last_serial) + rval = -3; + if (rval == 1) + zp->z_serial_ixfr_start = first_serial; + return (rval); } /* from db_load.c */ @@ -278,12 +357,7 @@ static struct map m_opcode[] = { #define M_TYPE_CNT m_type_cnt /* - * int - * ixfr_getrr(struct zoneinfo *zp, FILE *fp, - * const char *filename, char *origin, struct namebuf **np, - * u_int32_t *old_serial, u_int32_t *new_serial) - * - * read a line from the historic of a zone. + * read a line from the history of a zone. * * returns: * @@ -292,8 +366,8 @@ static struct map m_opcode[] = { * DBIXFR_END = end of file */ static int -ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, - ns_updrec **uprec, u_int32_t *old_serial, +ixfr_getdelta(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, + ns_updque *listuprec, u_int32_t *old_serial, u_int32_t *new_serial) { static int read_soa, read_ns, rrcount; @@ -305,7 +379,7 @@ ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, u_int32_t serial, ttl; int nonempty_lineno = -1, prev_pktdone = 0, cont = 0, inside_next = 0; - int id, rcode = NOERROR; + int id; int i, c, section, opcode, matches, zonenum, err, multiline; int type, class; u_int32_t n; @@ -316,7 +390,6 @@ ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, struct in_addr ina; struct sockaddr_in empty_from; int datasize; - ns_updque listuprec; ns_updrec * rrecp; u_long l; @@ -325,7 +398,6 @@ ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, err = 0; transport = primary_trans; lineno = 1; - INIT_LIST(listuprec); for (;;) { if (!getword(buf, sizeof buf, fp, 0)) { if (lineno == (nonempty_lineno + 1) && !(feof(fp))) { @@ -337,11 +409,10 @@ ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, } /* * Empty line or EOF. - * - * Marks completion of current update packet. */ + if (feof(fp)) + break; inside_next = 0; - prev_pktdone = 1; cont = 1; } else { nonempty_lineno = lineno; @@ -349,15 +420,12 @@ ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, if (!strcasecmp(buf, "[DYNAMIC_UPDATE]") || !strcasecmp(buf, "[IXFR_UPDATE]")) { - err = 0; - rcode = NOERROR; cp = fgets(buf, sizeof buf, fp); if (cp != NULL) lineno++; if (cp == NULL || !sscanf((char *) cp, "id %d", &id)) id = -1; inside_next = 1; - prev_pktdone = 1; cont = 1; } else if (!strcasecmp(buf, "[INCR_SERIAL]")) { /* XXXRTH not enough error checking here */ @@ -380,14 +448,11 @@ ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, lineno++; } if (prev_pktdone) { - if (!EMPTY(listuprec)) { + if (!EMPTY(*listuprec)) { n++; - *uprec = TAIL(listuprec); return (DBIXFR_FOUND_RR); } prev_pktdone = 0; - if (feof(fp)) - break; } if (cont) { cont = 0; @@ -800,9 +865,7 @@ ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, ns_debug(ns_log_update, 1, "merge of update id %d failed due to error at line %d", id, lineno); - memset(&empty_from, 0, sizeof empty_from); - free_rrecp(&listuprec, rcode, empty_from); - continue; + return (DBIXFR_ERROR); } rrecp = res_mkupdrec(section, dname, class, type, ttl); if (section != S_ZONE) { @@ -822,7 +885,7 @@ ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, ns_updrec *arp; int foundmatch; - arp = TAIL(listuprec); + arp = TAIL(*listuprec); foundmatch = 0; while (arp) { if (arp->r_section == S_UPDATE && @@ -837,7 +900,7 @@ ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, db_cmp(arp->r_dp, dp) == 0) { db_freedata(dp); db_freedata(arp->r_dp); - UNLINK(listuprec, arp, r_link); + UNLINK(*listuprec, arp, r_link); res_freeupdrec(arp); res_freeupdrec(rrecp); foundmatch = 1; @@ -849,7 +912,7 @@ ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, continue; } - APPEND(listuprec, rrecp, r_link); + APPEND(*listuprec, rrecp, r_link); /* Override zone number with current zone serial number */ rrecp->r_zone = serial; } @@ -859,3 +922,4 @@ ixfr_getrr(struct zoneinfo *zp, FILE *fp, const char *filename, char *origin, return (DBIXFR_END); } + diff --git a/contrib/bind/bin/named/db_load.c b/contrib/bind/bin/named/db_load.c index 9b6fedb..2d6a6e5 100644 --- a/contrib/bind/bin/named/db_load.c +++ b/contrib/bind/bin/named/db_load.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)db_load.c 4.38 (Berkeley) 3/2/91"; -static const char rcsid[] = "$Id: db_load.c,v 8.97 1999/10/30 03:21:35 vixie Exp $"; +static const char rcsid[] = "$Id: db_load.c,v 8.103 2000/04/21 06:54:02 vixie Exp $"; #endif /* not lint */ /* @@ -82,7 +82,7 @@ static const char rcsid[] = "$Id: db_load.c,v 8.97 1999/10/30 03:21:35 vixie Exp */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -267,6 +267,8 @@ db_load(const char *filename, const char *in_origin, switch (zp->z_type) { case Z_PRIMARY: + /* Any updates should be saved before we attempt to reload. */ + INSIST((zp->z_flags & (Z_NEED_DUMP|Z_NEED_SOAUPDATE)) == 0); case Z_HINT: transport = primary_trans; break; @@ -292,6 +294,7 @@ db_load(const char *filename, const char *in_origin, default_warn = 1; clev = nlabels(in_origin); filenames = NULL; + zp->z_minimum = USE_MINIMUM; } ttl = default_ttl; @@ -358,7 +361,8 @@ db_load(const char *filename, const char *in_origin, endline(fp); } didinclude = 1; - errs += db_load(buf, tmporigin, zp, domain, ISNOTIXFR); + i = db_load(buf, tmporigin, zp, domain, ISNOTIXFR); + errs += (i == -1) ? 1 : i; continue; case ORIGIN: @@ -742,7 +746,7 @@ db_load(const char *filename, const char *in_origin, zp->z_minimum = 0; } else zp->z_minimum = n; - if (default_ttl == USE_MINIMUM) + if (ttl == USE_MINIMUM) ttl = n; n = cp - (char *)data; if (multiline) { @@ -750,6 +754,7 @@ db_load(const char *filename, const char *in_origin, buf[1] = '\0'; if (buf[0] != ')') ERRTO("SOA \")\""); + multiline = 0; endline(fp); } read_soa++; @@ -971,7 +976,10 @@ db_load(const char *filename, const char *in_origin, case ns_t_cert: case ns_t_sig: { char *errmsg = NULL; - int ret = parse_sec_rdata(buf, sizeof(buf), 0, + int ret; + if (ttl == USE_MINIMUM) /* no ttl set */ + ttl = 0; + ret = parse_sec_rdata(buf, sizeof(buf), 0, data, sizeof(data), fp, zp, domain, ttl, type, domain_ctx, @@ -1022,6 +1030,8 @@ db_load(const char *filename, const char *in_origin, zp->z_origin); continue; } + if (ttl == USE_MINIMUM) /* no ttl set */ + ttl = 0; dp = savedata(class, type, (u_int32_t)ttl, (u_char *)data, (int)n); dp->d_zone = zp - zones; @@ -1083,6 +1093,9 @@ db_load(const char *filename, const char *in_origin, zp->z_origin, filename, msg); } } + errs += purge_nonglue(zp->z_origin, + (dataflags & DB_F_HINT) ? fcachetab : + hashtab, zp->z_class); while (filenames) { fn = filenames; filenames = filenames->next; @@ -1115,8 +1128,8 @@ db_load(const char *filename, const char *in_origin, void db_err(int err, char *domain, int type, const char *filename, int lineno) { if (filename != NULL && err == CNAMEANDOTHER) - ns_notice(ns_log_load, "%s:%d:%s: CNAME and OTHER data error", - filename, lineno, domain); + ns_warning(ns_log_load, "%s:%d:%s: CNAME and OTHER data error", + filename, lineno, domain); if (err != DATAEXISTS) ns_debug(ns_log_load, 1, "update failed %s %d", domain, type); @@ -2078,7 +2091,8 @@ parse_sig_rr(char *buf, int buf_len, u_char *data, int data_size, if (!getmlword(buf, my_buf_size, fp, 0)) ERRTO("Missing label count"); la = wordtouint32(buf); - if (0 == la || wordtouint32_error || 255 <= la) + if (wordtouint32_error || 255 <= la || + (0 == la && *domain != '\0')) ERRTO("Bad label count number"); data[i] = (u_char) la; i++; diff --git a/contrib/bind/bin/named/db_lookup.c b/contrib/bind/bin/named/db_lookup.c index 400523e..00b3d8d 100644 --- a/contrib/bind/bin/named/db_lookup.c +++ b/contrib/bind/bin/named/db_lookup.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)db_lookup.c 4.18 (Berkeley) 3/21/91"; -static const char rcsid[] = "$Id: db_lookup.c,v 8.24 1999/10/15 19:48:58 vixie Exp $"; +static const char rcsid[] = "$Id: db_lookup.c,v 8.26 2000/04/21 06:54:03 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: db_lookup.c,v 8.24 1999/10/15 19:48:58 vixie E */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -291,8 +291,18 @@ nxtlower(const char *name, struct databuf *dp) { int nxtmatch(const char *name, struct databuf *dp1, struct databuf *dp2) { int dp1_lower, dp2_lower; - - if (dp1->d_type != ns_t_nxt || dp2->d_type != ns_t_nxt) + int type1, type2; + + if (dp1->d_type == ns_t_sig) + type1 = SIG_COVERS(dp1); + else + type1 = dp1->d_type; + if (dp2->d_type == ns_t_sig) + type2 = SIG_COVERS(dp2); + else + type2 = dp2->d_type; + + if (type1 != ns_t_nxt || type2 != ns_t_nxt) return (0); dp1_lower = nxtlower(name, dp1); dp2_lower = nxtlower(name, dp2); diff --git a/contrib/bind/bin/named/db_save.c b/contrib/bind/bin/named/db_save.c index c4db46a..1fe0e73 100644 --- a/contrib/bind/bin/named/db_save.c +++ b/contrib/bind/bin/named/db_save.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)db_save.c 4.16 (Berkeley) 3/21/91"; -static const char rcsid[] = "$Id: db_save.c,v 8.26 1999/10/13 16:39:02 vixie Exp $"; +static const char rcsid[] = "$Id: db_save.c,v 8.27 2000/04/21 06:54:03 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: db_save.c,v 8.26 1999/10/13 16:39:02 vixie Exp */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/db_sec.c b/contrib/bind/bin/named/db_sec.c index bb31fae..2ed4a4c 100644 --- a/contrib/bind/bin/named/db_sec.c +++ b/contrib/bind/bin/named/db_sec.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: db_sec.c,v 8.30 1999/10/15 21:06:49 vixie Exp $"; +static const char rcsid[] = "$Id: db_sec.c,v 8.31 2000/04/21 06:54:04 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: db_sec.c,v 8.30 1999/10/15 21:06:49 vixie Exp */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/db_tsig.c b/contrib/bind/bin/named/db_tsig.c index d95031d..e8e81f9 100644 --- a/contrib/bind/bin/named/db_tsig.c +++ b/contrib/bind/bin/named/db_tsig.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: db_tsig.c,v 8.5 1999/10/15 19:48:59 vixie Exp $"; +static const char rcsid[] = "$Id: db_tsig.c,v 8.6 2000/04/21 06:54:04 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: db_tsig.c,v 8.5 1999/10/15 19:48:59 vixie Exp */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/db_update.c b/contrib/bind/bin/named/db_update.c index ea0176e..3bd9838 100644 --- a/contrib/bind/bin/named/db_update.c +++ b/contrib/bind/bin/named/db_update.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)db_update.c 4.28 (Berkeley) 3/21/91"; -static const char rcsid[] = "$Id: db_update.c,v 8.39 1999/10/15 19:48:59 vixie Exp $"; +static const char rcsid[] = "$Id: db_update.c,v 8.42 2000/04/21 06:54:04 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: db_update.c,v 8.39 1999/10/15 19:48:59 vixie E */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -169,10 +169,6 @@ findMyZone(struct namebuf *np, int class) { return (DB_Z_CACHE); } - -#define ISVALIDGLUE(xdp) ((xdp)->d_type == T_NS || (xdp)->d_type == T_A \ - || (xdp)->d_type == T_AAAA) - /* int * db_update(name, odp, newdp, savedpp, flags, htp, from) * update data base node at `name'. `flags' controls the action. @@ -591,9 +587,9 @@ db_update(const char *name, if ((flags & DB_REPLACE) == 0 && zones[dp->d_zone].z_type == Z_PRIMARY) { - ns_info(ns_log_db, + ns_warning(ns_log_db, "%s has multiple CNAMES", - name); + name); return (CNAMEANDOTHER); } else goto delete; diff --git a/contrib/bind/bin/named/named.h b/contrib/bind/bin/named/named.h index 18f4ac4..e9e95fa 100644 --- a/contrib/bind/bin/named/named.h +++ b/contrib/bind/bin/named/named.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -16,7 +16,7 @@ */ /* - * $Id: named.h,v 8.25 1999/10/13 18:00:19 vixie Exp $ + * $Id: named.h,v 8.27 2000/04/21 06:54:04 vixie Exp $ */ /* Options. Change them at your peril. */ @@ -30,7 +30,6 @@ #define QRYLOG #define YPKLUDGE #define RENICE -#define SLAVE_FORWARD #define BIND_IXFR #define BIND_NOTIFY #define BIND_UPDATE diff --git a/contrib/bind/bin/named/ns_config.c b/contrib/bind/bin/named/ns_config.c index 67bffbd..670e288 100644 --- a/contrib/bind/bin/named/ns_config.c +++ b/contrib/bind/bin/named/ns_config.c @@ -1,9 +1,9 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ns_config.c,v 8.104 1999/11/08 23:09:42 vixie Exp $"; +static const char rcsid[] = "$Id: ns_config.c,v 8.114 2000/04/23 02:18:58 vixie Exp $"; #endif /* not lint */ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -431,7 +431,6 @@ begin_zone(char *name, int class) { zp->z_origin = name; zp->z_class = class; zp->z_checknames = not_set; - zp->z_log_size_ixfr = 0; if (server_options->flags & OPTION_MAINTAIN_IXFR_BASE) zp->z_maintain_ixfr_base = 1; else @@ -478,7 +477,6 @@ update_zone_info(struct zoneinfo *zp, struct zoneinfo *new_zp) { new_zp->z_origin = NULL; zp->z_maintain_ixfr_base = new_zp->z_maintain_ixfr_base; zp->z_max_log_size_ixfr = new_zp->z_max_log_size_ixfr; - zp->z_log_size_ixfr = new_zp->z_log_size_ixfr; zp->z_class = new_zp->z_class; zp->z_type = new_zp->z_type; zp->z_checknames = new_zp->z_checknames; @@ -557,6 +555,7 @@ update_zone_info(struct zoneinfo *zp, struct zoneinfo *new_zp) { /* File has changed, or hasn't been loaded yet. */ if (zp->z_source) { freestr(zp->z_source); + ns_stopxfrs(zp); purge_zone(zp->z_origin, fcachetab, zp->z_class); } zp->z_source = new_zp->z_source; @@ -684,7 +683,8 @@ update_zone_info(struct zoneinfo *zp, struct zoneinfo *new_zp) { zp->z_ixfr_tmp = new_zp->z_ixfr_tmp; new_zp->z_ixfr_tmp = NULL; - if ((zp->z_flags & Z_AUTH) == 0) + if ((!noexpired || ((zp->z_flags & Z_EXPIRED) == 0)) && + ((zp->z_flags & Z_AUTH) == 0)) zoneinit(zp); else { /* @@ -833,7 +833,7 @@ set_zone_ixfr_file(zone_config zh, char *filename) { return (0); zp->z_ixfr_base = filename; if (zp->z_ixfr_tmp == NULL) { - int len = strlen(zp->z_ixfr_base) + (sizeof ".tmp" - 1); + int len = strlen(zp->z_ixfr_base) + (sizeof ".tmp"); char *str = (char *) memget(len); sprintf(str, "%s.tmp", zp->z_ixfr_base); @@ -1450,6 +1450,7 @@ write_open(char *filename) { S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH|S_IWOTH); if (fd < 0) return (NULL); + (void) fchown(fd, user_id, group_id); stream = fdopen(fd, "w"); if (stream == NULL) (void)close(fd); @@ -2067,7 +2068,7 @@ ip_match_addr_or_key(ip_match_list iml, struct in_addr address, if (indirect) { ret = ip_match_addr_or_key(ime->u.indirect.list, address, key); - if (ret >= 0) { + if (ret > 0) { if (ime->flags & IP_MATCH_NEGATE) ret = (ret) ? 0 : 1; return (ret); @@ -2246,7 +2247,79 @@ ip_match_is_none(ip_match_list iml) { return (0); } +/* + * find_forwarder finds the fwddata structure for an address, + * allocating one if we can't find one already existing. + */ + +static struct fwddata * +find_forwarder(struct in_addr address) +{ + struct fwddata *fdp; + struct databuf *ns, *nsdata; + register int i; + + for (i=0;i<fwddata_count; i++) { + fdp=fwddata[i]; + if (memcmp(&fdp->fwdaddr.sin_addr,&address,sizeof(address))==0) { + fdp->ref_count++; + return fdp; + } + } + fdp = (struct fwddata *)memget(sizeof(struct fwddata)); + if (!fdp) + panic("memget failed in find_forwarder", NULL); + fdp->fwdaddr.sin_family = AF_INET; + fdp->fwdaddr.sin_addr = address; + fdp->fwdaddr.sin_port = ns_port; + ns = fdp->ns = (struct databuf *)memget(sizeof(*ns)); + if (!ns) + panic("memget failed in find_forwarder", NULL); + memset(ns,0,sizeof(*ns)); + nsdata = fdp->nsdata = (struct databuf *)memget(sizeof(*nsdata)); + if (!nsdata) + panic("memget failed in find_forwarder", NULL); + memset(nsdata,0,sizeof(*nsdata)); + ns->d_type = T_NS; + ns->d_class = C_IN; + ns->d_rcnt=1; + nsdata->d_type = T_A; + nsdata->d_class = C_IN; + nsdata->d_nstime = 1 + (int)(25.0*rand()/(RAND_MAX + 1.0)); + nsdata->d_rcnt=1; + fdp->ref_count=1; + + i=0; + if (fwddata == NULL) { + fwddata = memget(sizeof *fwddata); + if (fwddata == NULL) + i = 1; + } else { + register size_t size; + register struct fwddata **an_tmp; + size = fwddata_count * sizeof *fwddata; + an_tmp = memget(size + sizeof *fwddata); + if (an_tmp == NULL) { + i = 1; + } else { + memcpy(an_tmp, fwddata, size); + memput(fwddata, size); + fwddata = an_tmp; + } + } + + if (i == 0) { + fwddata[fwddata_count] = fdp; + fwddata_count++; + } else { + ns_warning(ns_log_config, + "forwarder add failed (memget) [%s]", + inet_ntoa(address)); + } + + return fdp; +} /* * Forwarder glue * @@ -2257,25 +2330,25 @@ ip_match_is_none(ip_match_list iml) { static void add_forwarder(struct fwdinfo **fipp, struct in_addr address) { struct fwdinfo *fip = *fipp, *ftp = NULL; + struct fwddata *fdp; + +#ifdef FWD_LOOP + if (aIsUs(address)) { + ns_error(ns_log_config, "forwarder '%s' ignored, my address", + inet_ntoa(address)); + return; + } +#endif /* FWD_LOOP */ /* On multiple forwarder lines, move to end of the list. */ while (fip != NULL && fip->next != NULL) fip = fip->next; + fdp = find_forwarder(address); ftp = (struct fwdinfo *)memget(sizeof(struct fwdinfo)); if (!ftp) panic("memget failed in add_forwarder", NULL); - ftp->fwdaddr.sin_family = AF_INET; - ftp->fwdaddr.sin_addr = address; - ftp->fwdaddr.sin_port = ns_port; -#ifdef FWD_LOOP - if (aIsUs(ftp->fwdaddr.sin_addr)) { - ns_error(ns_log_config, "forwarder '%s' ignored, my address", - inet_ntoa(address)); - memput(ftp, sizeof *ftp); - return; - } -#endif /* FWD_LOOP */ + ftp->fwddata = fdp; ftp->next = NULL; if (fip == NULL) *fipp = ftp; /* First time only */ @@ -2346,10 +2419,6 @@ add_global_also_notify(options op, struct in_addr address) { void add_global_forwarder(options op, struct in_addr address) { -#ifdef SLAVE_FORWARD - struct fwdinfo *fip; - int forward_count; -#endif INSIST(op != NULL); @@ -2357,20 +2426,6 @@ add_global_forwarder(options op, struct in_addr address) { inet_ntoa(address)); add_forwarder(&op->fwdtab, address); - -#ifdef SLAVE_FORWARD - /* - ** Set the slave retry time to 60 seconds total divided - ** between each forwarder - */ - for (forward_count = 0, fip = op->fwdtab; fip != NULL; fip = fip->next) - forward_count++; - if (forward_count != 0) { - slave_retry = (int) (60 / forward_count); - if(slave_retry <= 0) - slave_retry = 1; - } -#endif } void @@ -2405,6 +2460,12 @@ free_forwarders(struct fwdinfo *fwdtab) { for (ftp = fwdtab; ftp != NULL; ftp = fnext) { fnext = ftp->next; + if (!--ftp->fwddata->ref_count) { + memput(ftp->fwddata->ns, sizeof *ftp->fwddata->ns); + memput(ftp->fwddata->nsdata, + sizeof *ftp->fwddata->nsdata); + memput(ftp->fwddata,sizeof *ftp->fwddata); + } memput(ftp, sizeof *ftp); } fwdtab = NULL; @@ -2911,16 +2972,19 @@ init_default_log_channels() { 0, ULONG_MAX); if (debug_channel == NULL || log_inc_references(debug_channel) < 0) ns_panic(ns_log_config, 0, "couldn't create debug_channel"); + log_set_file_owner(debug_channel, user_id, group_id); stderr_channel = log_new_file_channel(0, log_info, NULL, stderr, 0, ULONG_MAX); if (stderr_channel == NULL || log_inc_references(stderr_channel) < 0) ns_panic(ns_log_config, 0, "couldn't create stderr_channel"); + log_set_file_owner(stderr_channel, user_id, group_id); null_channel = log_new_file_channel(LOG_CHANNEL_OFF, log_info, _PATH_DEVNULL, NULL, 0, ULONG_MAX); if (null_channel == NULL || log_inc_references(null_channel) < 0) ns_panic(ns_log_config, 0, "couldn't create null_channel"); + log_set_file_owner(null_channel, user_id, group_id); } static void @@ -3057,4 +3121,6 @@ load_configuration(const char *filename) { initial_configuration = 0; loading = 0; + /* release queued notifies */ + notify_afterload(); } diff --git a/contrib/bind/bin/named/ns_ctl.c b/contrib/bind/bin/named/ns_ctl.c index 259093b..66cb862 100644 --- a/contrib/bind/bin/named/ns_ctl.c +++ b/contrib/bind/bin/named/ns_ctl.c @@ -1,9 +1,9 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ns_ctl.c,v 8.28 1999/10/13 16:39:04 vixie Exp $"; +static const char rcsid[] = "$Id: ns_ctl.c,v 8.34 2000/04/21 06:54:05 vixie Exp $"; #endif /* not lint */ /* - * Copyright (c) 1997-1999 by Internet Software Consortium. + * Copyright (c) 1997-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -68,12 +68,14 @@ struct control { struct sockaddr_in in; ip_match_list allow; } v_inet; +#ifndef NO_SOCKADDR_UN struct { struct sockaddr_un un; mode_t mode; uid_t owner; gid_t group; } v_unix; +#endif } var; }; @@ -150,7 +152,7 @@ static struct ctl_verb verbs[] = { { "stop", verb_stop, "stop"}, { "exec", verb_exec, "exec"}, { "reload", verb_reload, "reload [zone] ..."}, - { "reconfig", verb_reconfig, "reconfig (just sees new/gone zones)"}, + { "reconfig", verb_reconfig, "reconfig [-noexpired] (just sees new/gone zones)"}, { "dumpdb", verb_dumpdb, "dumpdb"}, { "stats", verb_stats, "stats"}, { "trace", verb_trace, "trace [level]"}, @@ -177,7 +179,29 @@ ns_ctl_shutdown(void) { void ns_ctl_defaults(controls *list) { +#ifdef NO_SOCKADDR_UN + struct in_addr saddr; + ip_match_list iml; + ip_match_element ime; + + /* + * If the operating system does not support local domain sockets, + * connect with ndc on 127.0.0.1, port 101, and only allow + * connections from 127.0.0.1. + */ + saddr.s_addr = htonl (INADDR_LOOPBACK); + iml = new_ip_match_list(); + ime = new_ip_match_pattern(saddr, 32); + add_to_ip_match_list(iml, ime); + + ns_ctl_add(list, ns_ctl_new_inet(saddr, htons (101), iml)); +#else +#ifdef NEED_SECURE_DIRECTORY + ns_ctl_add(list, ns_ctl_new_unix(_PATH_NDCSOCK, 0700, 0, 0)); +#else ns_ctl_add(list, ns_ctl_new_unix(_PATH_NDCSOCK, 0600, 0, 0)); +#endif +#endif /*NO_SOCKADDR_UN*/ } void @@ -200,6 +224,7 @@ ns_ctl_new_inet(struct in_addr saddr, u_int sport, ip_match_list allow) { return (new); } +#ifndef NO_SOCKADDR_UN control ns_ctl_new_unix(char *path, mode_t mode, uid_t owner, gid_t group) { control new = new_control(); @@ -215,6 +240,7 @@ ns_ctl_new_unix(char *path, mode_t mode, uid_t owner, gid_t group) { new->var.v_unix.group = group; return (new); } +#endif void ns_ctl_install(controls *new) { @@ -288,6 +314,7 @@ free_control(controls *list, control this) { this->var.v_inet.allow = NULL; } break; +#ifndef NO_SOCKADDR_UN case t_unix: /* XXX Race condition. */ if (was_live && @@ -297,6 +324,7 @@ free_control(controls *list, control this) { unlink(this->var.v_unix.un.sun_path); } break; +#endif default: panic("impossible type in free_control", NULL); /* NOTREACHED */ @@ -333,6 +361,7 @@ match_control(control l, control r) { r->var.v_inet.in.sin_addr.s_addr) match = 0; break; +#ifndef NO_SOCKADDR_UN case t_unix: if (l->var.v_unix.un.sun_family != r->var.v_unix.un.sun_family || @@ -340,6 +369,7 @@ match_control(control l, control r) { r->var.v_unix.un.sun_path) != 0) match = 0; break; +#endif default: panic("impossible type in match_control", NULL); /* NOTREACHED */ @@ -370,6 +400,7 @@ propagate_changes(const control diff, control base) { diff->var.v_inet.allow = NULL; need_install++; break; +#ifndef NO_SOCKADDR_UN case t_unix: if (base->var.v_unix.mode != diff->var.v_unix.mode) { base->var.v_unix.mode = diff->var.v_unix.mode; @@ -384,6 +415,7 @@ propagate_changes(const control diff, control base) { need_install++; } break; +#endif default: panic("impossible type in ns_ctl::propagate_changes", NULL); /* NOTREACHED */ @@ -398,9 +430,11 @@ install(control ctl) { case t_inet: install_inet(ctl); break; +#ifndef NO_SOCKADDR_UN case t_unix: install_unix(ctl); break; +#endif default: panic("impossible type in ns_ctl::install", NULL); /* NOTREACHED */ @@ -416,6 +450,7 @@ install_inet(control ctl) { } } +#ifndef NO_SOCKADDR_UN /* * Unattach an old unix domain socket if it exists. */ @@ -478,6 +513,35 @@ unattach(control ctl) { static void install_unix(control ctl) { + char *path; +#ifdef NEED_SECURE_DIRECTORY + char *slash; + + path = savestr(ctl->var.v_unix.un.sun_path, 1); + + slash = strrchr(path, '/'); + if (slash != NULL) { + if (slash != path) + *slash = '\0'; + else { + freestr(path); + path = savestr("/", 1); + } + } else { + freestr(path); + path = savestr(".", 1); + } + if (mkdir(path, ctl->var.v_unix.mode) < 0) { + if (errno != EEXIST) { + ns_warning(ns_log_config, + "unix control \"%s\" mkdir failed: %s", + path, strerror(errno)); + } + } +#else + path = ctl->var.v_unix.un.sun_path; +#endif + if (ctl->sctx == NULL) { unattach(ctl); ctl->sctx = mksrvr(ctl, @@ -486,15 +550,13 @@ install_unix(control ctl) { } if (ctl->sctx != NULL) { /* XXX Race condition. */ - if (chmod(ctl->var.v_unix.un.sun_path, - ctl->var.v_unix.mode) < 0) { + if (chmod(path, ctl->var.v_unix.mode) < 0) { ns_warning(ns_log_config, "chmod(\"%s\", 0%03o): %s", ctl->var.v_unix.un.sun_path, ctl->var.v_unix.mode, strerror(errno)); } - if (chown(ctl->var.v_unix.un.sun_path, - ctl->var.v_unix.owner, + if (chown(path, ctl->var.v_unix.owner, ctl->var.v_unix.group) < 0) { ns_warning(ns_log_config, "chown(\"%s\", %d, %d): %s", ctl->var.v_unix.un.sun_path, @@ -503,7 +565,11 @@ install_unix(control ctl) { strerror(errno)); } } +#ifdef NEED_SECURE_DIRECTORY + freestr(path); +#endif } +#endif static void logger(enum ctl_severity ctlsev, const char *format, ...) { @@ -747,6 +813,8 @@ verb_reload(struct ctl_sctx *ctl, struct ctl_sess *sess, case z_slave: case z_stub: ns_stopxfrs(zp); + if (zonefile_changed_p(zp)) + zp->z_serial = 0; /* force xfer */ addxfer(zp); code = 251; msg = "Slave transfer queued."; @@ -770,7 +838,10 @@ verb_reconfig(struct ctl_sctx *ctl, struct ctl_sess *sess, const struct ctl_verb *verb, const char *rest, u_int respflags, void *respctx, void *uctx) { - ns_need(main_need_reconfig); + if (strcmp(rest, "-noexpired") != 0) + ns_need(main_need_reconfig); + else + ns_need(main_need_noexpired); ctl_response(sess, 250, "Reconfig initiated.", 0, NULL, NULL, NULL, NULL, 0); } diff --git a/contrib/bind/bin/named/ns_defs.h b/contrib/bind/bin/named/ns_defs.h index 801e5a9..56b50fe 100644 --- a/contrib/bind/bin/named/ns_defs.h +++ b/contrib/bind/bin/named/ns_defs.h @@ -1,6 +1,6 @@ /* * from ns.h 4.33 (Berkeley) 8/23/90 - * $Id: ns_defs.h,v 8.89 1999/10/07 08:24:08 vixie Exp $ + * $Id: ns_defs.h,v 8.96 2000/04/21 06:54:06 vixie Exp $ */ /* @@ -57,7 +57,7 @@ */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -165,7 +165,9 @@ typedef enum need { main_need_debug, /* use_desired_debug() needed. */ main_need_restart, /* exec() needed. */ main_need_reap, /* need to reap dead children */ - main_need_num /* number of needs, used for array bound. */ + main_need_noexpired, /* ns_reconfig() needed w/ noexpired set */ + main_need_num, /* number of needs, used for array bound. */ + main_need_tick /* tick every second to poll for cleanup (NT)*/ } main_need; /* What global options are set? */ @@ -181,13 +183,13 @@ typedef enum need { * CNAME RRs */ #define OPTION_HOSTSTATS 0x0080 /* Maintain per-host statistics? */ #define OPTION_DEALLOC_ON_EXIT 0x0100 /* Deallocate everything on exit? */ -#define OPTION_USE_IXFR 0x0110 /* Use by delault ixfr in zone transfer */ -#define OPTION_MAINTAIN_IXFR_BASE 0x0120 #define OPTION_NODIALUP 0x0200 /* Turn off dialup support */ #define OPTION_NORFC2308_TYPE1 0x0400 /* Prevent type1 respones (RFC 2308) * to cached negative respones */ #define OPTION_USE_ID_POOL 0x0800 /* Use the memory hogging query ID */ #define OPTION_TREAT_CR_AS_SPACE 0x1000 /* Treat CR in zone files as space */ +#define OPTION_USE_IXFR 0x2000 /* Use by delault ixfr in zone transfer */ +#define OPTION_MAINTAIN_IXFR_BASE 0x4000 /* Part of IXFR file name logic. */ #define DEFAULT_OPTION_FLAGS (OPTION_NODIALUP|OPTION_NONAUTH_NXDOMAIN|\ OPTION_USE_ID_POOL|OPTION_NORFC2308_TYPE1) @@ -306,7 +308,8 @@ typedef struct ztimer_info { int type; } *ztimer_info; -/* these fields are ordered to maintain word-alignment; +/* + * These fields are ordered to maintain word-alignment; * be careful about changing them. */ struct zoneinfo { @@ -359,9 +362,9 @@ struct zoneinfo { enum zdialup z_dialup; /* secondaries over a dialup link */ char *z_ixfr_base; /* where to find the history of the zone */ char *z_ixfr_tmp; /* tmp file for the ixfr */ - int z_maintain_ixfr_base; - int z_log_size_ixfr; - int z_max_log_size_ixfr; + int z_maintain_ixfr_base; + long z_max_log_size_ixfr; + u_int32_t z_serial_ixfr_start; evTimerID z_timer; /* maintenance timer */ ztimer_info z_timerinfo; /* UAP associated with timer */ time_t z_nextmaint; /* time of next maintenance */ @@ -410,6 +413,7 @@ enum zonetype { z_nil, z_master, z_slave, z_hint, z_stub, z_forward, #define Z_NEED_QSERIAL 0x00020000 /* we need to re-call qserial() */ #define Z_PARENT_RELOAD 0x00040000 /* we need to reload this as parent */ #define Z_FORWARD_SET 0x00080000 /* has forwarders been set */ +#define Z_EXPIRED 0x00100000 /* expire timer has gone off */ /* named_xfer exit codes */ #define XFER_UPTODATE 0 /* zone is up-to-date */ @@ -507,6 +511,14 @@ struct fdlist { }; #endif + +typedef struct ns_delta { + LINK(struct ns_delta) d_link; + ns_updque d_changes; +} ns_delta; + +typedef LIST(ns_delta) ns_deltalist; + typedef struct _interface { int dfd, /* Datagram file descriptor */ sfd; /* Stream file descriptor. */ @@ -570,7 +582,7 @@ struct qstream { u_int zone; /* zone being XFR'd. */ union { struct namebuf *axfr; /* top np of an AXFR. */ - struct ns_updrec *ixfr; /* top udp of an IXFR. */ + ns_deltalist *ixfr; /* top udp of an IXFR. */ } top; int ixfr_zone; u_int32_t serial; /* serial number requested in IXFR */ @@ -602,16 +614,23 @@ struct qstream { #define STREAM_CONNECT_EV 0x08 #define STREAM_DONE_CLOSE 0x10 #define STREAM_AXFR 0x20 -#define STREAM_AXFRIXFR 0x22 +#define STREAM_AXFRIXFR 0x40 #define ALLOW_NETS 0x0001 #define ALLOW_HOSTS 0x0002 #define ALLOW_ALL (ALLOW_NETS | ALLOW_HOSTS) +struct fwddata { + struct sockaddr_in + fwdaddr; /* address of NS */ + struct databuf *ns; /* databuf for NS record */ + struct databuf *nsdata; /* databuf for server address */ + int ref_count; /* how many users of this */ +}; + struct fwdinfo { struct fwdinfo *next; - struct sockaddr_in - fwdaddr; + struct fwddata *fwddata; }; enum nameserStats { nssRcvdR, /* sent us an answer */ @@ -639,6 +658,10 @@ enum nameserStats { nssRcvdR, /* sent us an answer */ nssSentFErr, /* sent them a FORMERR */ nssSentNaAns, /* sent them a non autoritative answer */ nssSentNXD, /* sent them a negative response */ + nssRcvdUQ, /* sent us an unapproved query */ + nssRcvdURQ, /* sent us an unapproved recursive query */ + nssRcvdUXFR, /* sent us an unapproved AXFR or IXFR */ + nssRcvdUUpd, /* sent us an unapproved update */ nssLast }; struct nameser { diff --git a/contrib/bind/bin/named/ns_forw.c b/contrib/bind/bin/named/ns_forw.c index 3a4e488..beb919c 100644 --- a/contrib/bind/bin/named/ns_forw.c +++ b/contrib/bind/bin/named/ns_forw.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)ns_forw.c 4.32 (Berkeley) 3/3/91"; -static const char rcsid[] = "$Id: ns_forw.c,v 8.68 1999/10/13 16:39:07 vixie Exp $"; +static const char rcsid[] = "$Id: ns_forw.c,v 8.75 2000/05/09 07:12:58 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: ns_forw.c,v 8.68 1999/10/13 16:39:07 vixie Exp */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -160,7 +160,7 @@ ns_forw(struct databuf *nsp[], u_char *msg, int msglen, } } - qp = qnew(dname, class, type); + qp = qnew(dname, class, type, 1); getname(np, tmpdomain, sizeof tmpdomain); qp->q_domain = savestr(tmpdomain, 1); qp->q_from = from; /* nslookup wants to know this */ @@ -208,11 +208,6 @@ ns_forw(struct databuf *nsp[], u_char *msg, int msglen, hp->rd = (qp->q_addr[0].forwarder ? 1 : 0); qp->q_addr[0].stime = tt; -#ifdef SLAVE_FORWARD - if (NS_ZOPTION_P(qp->q_fzone, OPTION_FORWARD_ONLY)) - schedretry(qp, (time_t)slave_retry); - else -#endif /* SLAVE_FORWARD */ schedretry(qp, retrytime(qp)); nsa = Q_NEXTADDR(qp, 0); @@ -288,8 +283,7 @@ ns_forw(struct databuf *nsp[], u_char *msg, int msglen, hp = (HEADER *) qp->q_msg; } - if (NS_OPTION_P(OPTION_HOSTSTATS)) - nameserIncr(from.sin_addr, nssRcvdFwdQ); + nameserIncr(from.sin_addr, nssRcvdFwdQ); nameserIncr(nsa->sin_addr, nssSentFwdQ); if (qpp) *qpp = qp; @@ -470,7 +464,7 @@ nslookup(struct databuf *nsp[], struct qinfo *qp, lame_ns = potential_ns = 0; naddr = n = qp->q_naddr; curtime = (u_long) tt.tv_sec; - while ((nsdp = *nsp++) != NULL) { + while ((nsdp = *nsp++) != NULL && n < NSMAX) { class = nsdp->d_class; dname = (char *)nsdp->d_data; ns_debug(ns_log_default, 3, @@ -668,7 +662,7 @@ nslookup(struct databuf *nsp[], struct qinfo *qp, n++; if (n >= NSMAX) - goto out; + break; skipaddr: (void)NULL; } @@ -703,8 +697,11 @@ nslookup(struct databuf *nsp[], struct qinfo *qp, DRCNTINC(qp->q_addr[i].nsdata); DRCNTINC(qp->q_addr[i].ns); } - if (n > 1) { - qsort((char *)qp->q_addr, n, sizeof(struct qserv), + /* Just sort the NS RR's we added, since the forwarders may + * be ahead of us (naddr > 0) + */ + if (n > naddr) { + qsort((char *)(qp->q_addr+naddr), n-naddr, sizeof(struct qserv), (int (*)(const void *, const void *))qcomp); } return (n - naddr); @@ -761,51 +758,51 @@ nslookup(struct databuf *nsp[], struct qinfo *qp, * RTT delta deemed to be significant, in milliseconds. With the current * definition of RTTROUND it must be a power of 2. */ -#define NOISE 128 /* milliseconds; 0.128 seconds */ +#define NOISE 64 -#define sign(x) (((x) < 0) ? -1 : ((x) > 0) ? 1 : 0) #define RTTROUND(rtt) (((rtt) + (NOISE >> 1)) & ~(NOISE - 1)) int qcomp(struct qserv *qs1, struct qserv *qs2) { - int pos1, pos2, pdiff; - u_long rtt1, rtt2; - long tdiff; + u_int rtt1, rtt2, rttr1, rttr2; - if ((!qs1->nsdata) || (!qs2->nsdata)) - return 0; - rtt1 = qs1->nsdata->d_nstime; - rtt2 = qs2->nsdata->d_nstime; + if (qs1->nsdata == NULL || qs2->nsdata == NULL) { + rtt1 = 0; + rttr1 = 0; + rtt2 = 0; + rttr2 = 0; + } else { + rtt1 = qs1->nsdata->d_nstime; + rttr1 = RTTROUND(rtt1); + rtt2 = qs2->nsdata->d_nstime; + rttr2 = RTTROUND(rtt2); + } #ifdef DEBUG if (debug >= 10) { - char a1[sizeof "255.255.255.255"], - a2[sizeof "255.255.255.255"]; + char t[sizeof "255.255.255.255"]; - strcpy(a1, inet_ntoa(qs1->ns_addr.sin_addr)); - strcpy(a2, inet_ntoa(qs2->ns_addr.sin_addr)); + strcpy(t, inet_ntoa(qs1->ns_addr.sin_addr)); ns_debug(ns_log_default, 10, "qcomp(%s, %s) %lu (%lu) - %lu (%lu) = %lu", - a1, a2, - rtt1, RTTROUND(rtt1), - rtt2, RTTROUND(rtt2), - rtt1 - rtt2); + t, inet_ntoa(qs2->ns_addr.sin_addr), + rtt1, rttr1, rtt2, rttr2, rtt1 - rtt2); } #endif - if (RTTROUND(rtt1) == RTTROUND(rtt2)) { + if (rttr1 == rttr2) { + int pos1, pos2, pdiff; + pos1 = distance_of_address(server_options->topology, qs1->ns_addr.sin_addr); pos2 = distance_of_address(server_options->topology, qs2->ns_addr.sin_addr); pdiff = pos1 - pos2; ns_debug(ns_log_default, 10, "\tpos1=%d, pos2=%d", pos1, pos2); - if (pdiff) + if (pdiff != 0) return (pdiff); } - tdiff = rtt1 - rtt2; - return (sign(tdiff)); + return (rtt1 - rtt2); } -#undef sign #undef RTTROUND /* @@ -1076,11 +1073,6 @@ retry(struct qinfo *qp) { schedretry(qp, (time_t) 0); return; } -#ifdef SLAVE_FORWARD - if (NS_ZOPTION_P(qp->q_fzone, OPTION_FORWARD_ONLY)) - schedretry(qp, (time_t)slave_retry); - else -#endif /* SLAVE_FORWARD */ schedretry(qp, retrytime(qp)); } @@ -1140,7 +1132,7 @@ qfindid(u_int16_t id) { } struct qinfo * -qnew(const char *name, int class, int type) { +qnew(const char *name, int class, int type, int forward) { struct qinfo *qp; const char *s; int escape = 0; @@ -1160,7 +1152,8 @@ qnew(const char *name, int class, int type) { qp->q_type = (u_int16_t)type; qp->q_flags = 0; s = name; - for (;;) { /* find forwarding zone, if any */ + qp->q_fzone = NULL; + for (;forward;) { /* find forwarding zone, if any */ if ((qp->q_fzone = find_zone(s, class)) != NULL && (qp->q_fzone->z_flags & Z_FORWARD_SET) != 0) break; @@ -1250,15 +1243,15 @@ nsfwdadd(struct qinfo *qp, struct fwdinfo *fwd) { struct qserv *qs; n = qp->q_naddr; - while (fwd != NULL && n < MAXNS) { + while (fwd != NULL && n < NSMAX) { qs = qp->q_addr; for (i = 0; i < (u_int)n; i++, qs++) if (ina_equal(qs->ns_addr.sin_addr, - fwd->fwdaddr.sin_addr)) + fwd->fwddata->fwdaddr.sin_addr)) goto nextfwd; - qs->ns_addr = fwd->fwdaddr; - qs->ns = NULL; - qs->nsdata = NULL; + qs->ns_addr = fwd->fwddata->fwdaddr; + qs->ns = fwd->fwddata->ns; + qs->nsdata = fwd->fwddata->nsdata; qs->forwarder = 1; qs->nretry = 0; n++; @@ -1266,4 +1259,14 @@ nsfwdadd(struct qinfo *qp, struct fwdinfo *fwd) { fwd = fwd->next; } qp->q_naddr = n; + + /* Update the refcounts before the sort. */ + for (i = 0; i < (u_int)n; i++) { + DRCNTINC(qp->q_addr[i].nsdata); + DRCNTINC(qp->q_addr[i].ns); + } + if (n > 1) { + qsort((char *)qp->q_addr, n, sizeof(struct qserv), + (int (*)(const void *, const void *))qcomp); + } } diff --git a/contrib/bind/bin/named/ns_func.h b/contrib/bind/bin/named/ns_func.h index 88c181ca..760266d 100644 --- a/contrib/bind/bin/named/ns_func.h +++ b/contrib/bind/bin/named/ns_func.h @@ -52,7 +52,7 @@ */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -90,7 +90,7 @@ /* ns_func.h - declarations for ns_*.c's externally visible functions * - * $Id: ns_func.h,v 8.90 1999/10/11 18:22:20 vixie Exp $ + * $Id: ns_func.h,v 8.96 2000/04/21 06:54:06 vixie Exp $ */ /* ++from ns_glue.c++ */ @@ -146,7 +146,9 @@ int movefile(const char *, const char *); /* ++from ns_notify.c++ */ #ifdef BIND_NOTIFY void ns_notify(const char *, ns_class, ns_type); +void notify_afterload(void); void ns_unnotify(void); +void ns_stopnotify(const char *, ns_class); #endif /* --from ns_notify.c-- */ @@ -254,7 +256,7 @@ extern void schedretry(struct qinfo *, time_t), freeComplaints(void), nsfwdadd(struct qinfo *, struct fwdinfo *); extern struct qinfo *qfindid(u_int16_t), - *qnew(const char *, int, int); + *qnew(const char *, int, int, int); /* --from ns_forw.c-- */ /* ++from ns_main.c++ */ @@ -302,7 +304,8 @@ extern void zone_maint(struct zoneinfo *), addxfer(struct zoneinfo *), ns_zreload(void), ns_reload(void), - ns_reconfig(void); + ns_reconfig(void), + ns_noexpired(void); #if 0 extern int reload_all_unsafe(void); #endif @@ -318,6 +321,8 @@ extern void ns_heartbeat(evContext ctx, void *uap, extern void make_new_zones(void); extern void free_zone(struct zoneinfo *); extern struct zoneinfo *find_auth_zone(const char *, ns_class); +extern int purge_nonglue(const char *dname, struct hashbuf *htp, + int class); /* --from ns_maint.c-- */ /* ++from ns_sort.c++ */ @@ -416,7 +421,7 @@ void free_rrset_order_list(rrset_order_list); void set_global_boolean_option(options, int, int); listen_info_list new_listen_info_list(void); void free_listen_info_list(listen_info_list); -void add_listen_on(options, u_int16_t, ip_match_list); +void add_listen_on(options, u_short, ip_match_list); FILE * write_open(char *filename); void update_pid_file(void); void set_options(options, int); diff --git a/contrib/bind/bin/named/ns_glob.h b/contrib/bind/bin/named/ns_glob.h index b977f7b..af0ea30 100644 --- a/contrib/bind/bin/named/ns_glob.h +++ b/contrib/bind/bin/named/ns_glob.h @@ -1,6 +1,6 @@ /* * from ns.h 4.33 (Berkeley) 8/23/90 - * $Id: ns_glob.h,v 8.51 1999/10/15 21:53:32 vixie Exp $ + * $Id: ns_glob.h,v 8.54 2000/04/21 06:54:07 vixie Exp $ */ /* @@ -57,7 +57,7 @@ */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -156,17 +156,17 @@ DECL u_char *dnptrs[40]; DECL u_char **dnptrs_end INIT(dnptrs + sizeof dnptrs / sizeof(u_char*)); + /* data about all forwarders */ +DECL struct fwddata **fwddata; + /* how many forwarders are there in fwddata? */ +DECL int fwddata_count; + /* number of names in addinfo */ DECL int addcount; /* name of cache file */ DECL const char *cache_file; -#ifdef SLAVE_FORWARD - /* retry time when a slave */ -DECL int slave_retry INIT(4); -#endif - #ifdef BIND_UPDATE DECL const char * LogSignature INIT(";BIND LOG V8\n"); DECL const char * DumpSignature INIT(";BIND DUMP V8\n"); diff --git a/contrib/bind/bin/named/ns_glue.c b/contrib/bind/bin/named/ns_glue.c index 4b7972c..9c40dde 100644 --- a/contrib/bind/bin/named/ns_glue.c +++ b/contrib/bind/bin/named/ns_glue.c @@ -1,9 +1,9 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ns_glue.c,v 8.14 1999/10/19 02:06:26 gson Exp $"; +static const char rcsid[] = "$Id: ns_glue.c,v 8.16 2000/04/21 06:50:18 vixie Exp $"; #endif /* not lint */ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium, Inc. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -73,15 +73,13 @@ ina_put(struct in_addr ina, u_char *data) { } /* - * XXX: sin_ntoa() should probably be in libc. + * IP address to presentation format. */ const char * sin_ntoa(struct sockaddr_in sin) { static char ret[sizeof "[111.222.333.444].55555"]; - sprintf(ret, "[%s].%u", - inet_ntoa(sin.sin_addr), - ntohs(sin.sin_port)); + sprintf(ret, "[%s].%u", inet_ntoa(sin.sin_addr), ntohs(sin.sin_port)); return (ret); } @@ -180,7 +178,7 @@ ns_assertion_failed(char *file, int line, assertion_type type, char *cond, } /* - * XXX This is for compatibility and will eventually be removed. + * XXX This is for compatibility and should eventually be removed. */ void panic(const char *msg, const void *arg) { @@ -192,7 +190,7 @@ panic(const char *msg, const void *arg) { * Note: the root label is not included in the count. */ int -nlabels (const char *dname) { +nlabels(const char *dname) { int count, i, found, escaped; const char *tmpdname, *end_tmpdname; int tmpdnamelen, c; @@ -215,9 +213,8 @@ nlabels (const char *dname) { escaped = 0; else escaped = 1; - } else { + } else break; - } if (!escaped) tmpdnamelen--; } @@ -244,8 +241,7 @@ nlabels (const char *dname) { } } - ns_debug(ns_log_default, 12, "nlabels of \"%s\" -> %d", dname, - count); + ns_debug(ns_log_default, 12, "nlabels of \"%s\" -> %d", dname, count); return (count); } @@ -448,3 +444,20 @@ movefile(const char *oldname, const char *newname) { return (rename(oldname, newname)); } #endif + +#ifdef ultrix +/* + * Some library routines in libc need to be able to see the res_send + * and res_close symbols with out __ prefix otherwise we get multiply + * defined symbol errors when linking named. + */ + +#undef res_send +int res_send(const u_char *buf, int buflen, u_char *ans, int anssiz) { + return __res_send(buf, buflen, ans, anssiz); +} +#undef _res_close +void _res_close(void) { + __res_close(); +} +#endif diff --git a/contrib/bind/bin/named/ns_init.c b/contrib/bind/bin/named/ns_init.c index cc95ce6..66242a4 100644 --- a/contrib/bind/bin/named/ns_init.c +++ b/contrib/bind/bin/named/ns_init.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)ns_init.c 4.38 (Berkeley) 3/21/91"; -static const char rcsid[] = "$Id: ns_init.c,v 8.63 1999/10/15 19:49:04 vixie Exp $"; +static const char rcsid[] = "$Id: ns_init.c,v 8.68 2000/04/21 06:54:07 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: ns_init.c,v 8.63 1999/10/15 19:49:04 vixie Exp */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -245,7 +245,7 @@ zoneinit(struct zoneinfo *zp) { } } else { zp->z_flags |= Z_AUTH; - zp->z_flags &= ~Z_NEED_RELOAD; + zp->z_flags &= ~(Z_NEED_RELOAD|Z_EXPIRED); ns_refreshtime(zp, tt.tv_sec); sched_zone_maint(zp); } @@ -285,6 +285,7 @@ do_reload(const char *domain, int type, int class, int mark) { /* * Clean up any leftover data. */ + ns_stopxfrs(zp); purge_zone(domain, hashtab, class); /* @@ -328,6 +329,20 @@ do_reload(const char *domain, int type, int class, int mark) { void purgeandload(struct zoneinfo *zp) { + +#ifdef BIND_UPDATE + /* + * A dynamic zone might have changed, so we + * need to dump it before removing it. + */ + if (zp->z_type == Z_PRIMARY && + (zp->z_flags & Z_DYNAMIC) != 0 && + ((zp->z_flags & Z_NEED_SOAUPDATE) != 0 || + (zp->z_flags & Z_NEED_DUMP) != 0)) + (void) zonedump(zp, ISNOTIXFR); +#endif + ns_stopxfrs(zp); + if (zp->z_type == Z_HINT) purge_zone(zp->z_origin, fcachetab, zp->z_class); else diff --git a/contrib/bind/bin/named/ns_ixfr.c b/contrib/bind/bin/named/ns_ixfr.c index 76dbe6e..693dc6f 100644 --- a/contrib/bind/bin/named/ns_ixfr.c +++ b/contrib/bind/bin/named/ns_ixfr.c @@ -1,5 +1,5 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ns_ixfr.c,v 8.17 1999/11/05 04:48:28 vixie Exp $"; +static const char rcsid[] = "$Id: ns_ixfr.c,v 8.19 2000/04/18 20:47:27 vixie Exp $"; #endif /* not lint */ /* @@ -58,7 +58,6 @@ static int sx_flush(struct qstream * qsp), sx_addrr(struct qstream * qsp, const char *dname, struct databuf * dp); -extern void sx_sendsoa(struct qstream * qsp); /* * u_char * sx_new_ixfrmsg(msg) init the header of a message, reset the @@ -68,7 +67,6 @@ extern void sx_sendsoa(struct qstream * qsp); static void sx_new_ixfrmsg(struct qstream *qsp) { HEADER * hp = (HEADER *) qsp->xfr.msg; - ns_updrec * up; memset(hp, 0, HFIXEDSZ); hp->id = htons(qsp->xfr.id); @@ -94,7 +92,6 @@ sx_new_ixfrmsg(struct qstream *qsp) { qsp->xfr.ixfr_zone = qsp->xfr.zone; zp = &zones[qsp->xfr.zone]; - up = qsp->xfr.top.ixfr; n = dn_comp(zp->z_origin, qsp->xfr.cp, XFER_BUFSIZE - (qsp->xfr.cp - qsp->xfr.msg), NULL, NULL); qsp->xfr.cp += n; @@ -114,8 +111,11 @@ sx_new_ixfrmsg(struct qstream *qsp) { } /* - * int sx_flush(qsp) flush the intermediate buffer out to the stream IO - * system. return: passed through from sq_write(). + * int + * sx_flush(qsp) + * flush the intermediate buffer out to the stream IO system. + * return: + * passed through from sq_write(). */ static int sx_flush(struct qstream *qsp) { @@ -126,12 +126,34 @@ sx_flush(struct qstream *qsp) { fp_nquery(qsp->xfr.msg, qsp->xfr.cp - qsp->xfr.msg, log_get_stream(packet_channel)); #endif - ret = sq_write(qsp, qsp->xfr.msg, qsp->xfr.cp - qsp->xfr.msg); - if (ret >= 0) + if (qsp->xfr.tsig_state != NULL && qsp->xfr.tsig_skip == 0) { + int msglen = qsp->xfr.cp - qsp->xfr.msg; + + ns_sign_tcp(qsp->xfr.msg, &msglen, qsp->xfr.eom - qsp->xfr.msg, + NOERROR, qsp->xfr.tsig_state, + qsp->xfr.state == s_x_done); + + if (qsp->xfr.state == s_x_done) { + memput(qsp->xfr.tsig_state, sizeof(ns_tcp_tsig_state)); + qsp->xfr.tsig_state = NULL; + } + qsp->xfr.cp = qsp->xfr.msg + msglen; + + } + if (qsp->xfr.cp - qsp->xfr.msg > 0) + ret = sq_write(qsp, qsp->xfr.msg, qsp->xfr.cp - qsp->xfr.msg); + else { + ns_debug(ns_log_default, 3, " Flush negative number *********"); + ret = -1; + } + if (ret >= 0) { qsp->xfr.cp = NULL; + qsp->xfr.tsig_skip = 0; + } + else + qsp->xfr.tsig_skip = 1; return (ret); } - /* * int sx_addrr(qsp, name, dp) add name/dp's RR to the current assembly * message. if it won't fit, write current message out, renew the message, @@ -176,8 +198,9 @@ sx_send_ixfr(struct qstream *qsp) { struct zoneinfo *zp = NULL; struct databuf *soa_dp; struct databuf *old_soadp; - ns_updrec * rp; - ns_updrec * trp; + ns_delta *dp; + ns_updrec *rp; + ns_updrec *trp; int foundsoa; zp = &zones[qsp->xfr.zone]; @@ -193,6 +216,8 @@ sx_send_ixfr(struct qstream *qsp) { again: switch (qsp->xfr.state) { case s_x_firstsoa: + ns_debug(ns_log_default, 3, + "IXFR: s_x_firstsoa (%s)", zp->z_origin); /* * The current SOA has been emited already. * It would be cleaner if the first one was emited here... @@ -203,11 +228,15 @@ sx_send_ixfr(struct qstream *qsp) { qsp->xfr.state = s_x_deletesoa; /* FALLTHROUGH */ case s_x_deletesoa: - if (qsp->xfr.top.ixfr) { + ns_debug(ns_log_default, 3, + "IXFR: s_x_deletesoa (%s)", zp->z_origin); + dp = NULL; + if (qsp->xfr.top.ixfr != NULL && !EMPTY(*qsp->xfr.top.ixfr)) + dp = HEAD(*qsp->xfr.top.ixfr); + if (dp != NULL) { foundsoa = 0; - rp = qsp->xfr.top.ixfr; - while (PREV(rp, r_link) != NULL) - rp = PREV(rp, r_link); + + rp = HEAD(dp->d_changes); while (rp != NULL) { if (rp->r_opcode == DELETE && rp->r_dp != NULL && @@ -220,13 +249,12 @@ sx_send_ixfr(struct qstream *qsp) { foundsoa = 1; break; } - trp = rp; rp = NEXT(rp, r_link); } if (!foundsoa) { cp = (char *)findsoaserial(old_soadp->d_data); - PUTLONG(qsp->xfr.top.ixfr->r_zone, cp); + PUTLONG(HEAD(dp->d_changes)->r_zone, cp); if (sx_addrr(qsp, zp->z_origin, old_soadp) < 0) goto cleanup; @@ -235,15 +263,13 @@ sx_send_ixfr(struct qstream *qsp) { qsp->xfr.state = s_x_deleting; /* FALLTHROUGH */ case s_x_deleting: - if (qsp->xfr.top.ixfr) { - /* - * The order s important here. - * Go to start of this update via PREV(r_link) - * then extract all deletions. - */ - rp = qsp->xfr.top.ixfr; - while (PREV(rp, r_link) != NULL) - rp = PREV(rp, r_link); + ns_debug(ns_log_default, 3, + "IXFR: s_x_deleting (%s)", zp->z_origin); + dp = NULL; + if (qsp->xfr.top.ixfr != NULL && !EMPTY(*qsp->xfr.top.ixfr)) + dp = HEAD(*qsp->xfr.top.ixfr); + if (dp != NULL) { + rp = HEAD(dp->d_changes); while (rp != NULL) { if (rp->r_opcode == DELETE && rp->r_dp != NULL) { @@ -257,18 +283,20 @@ sx_send_ixfr(struct qstream *qsp) { db_freedata(rp->r_dp); rp->r_dp = NULL; } - trp = rp; rp = NEXT(rp, r_link); } } qsp->xfr.state = s_x_addsoa; /* FALLTHROUGH */ case s_x_addsoa: - if (qsp->xfr.top.ixfr) { + ns_debug(ns_log_default, 3, + "IXFR: s_x_addsoa (%s)", zp->z_origin); + dp = NULL; + if (qsp->xfr.top.ixfr != NULL && !EMPTY(*qsp->xfr.top.ixfr)) + dp = HEAD(*qsp->xfr.top.ixfr); + if (dp != NULL) { foundsoa = 0; - rp = qsp->xfr.top.ixfr; - while (PREV(rp, r_link) != NULL) - rp = PREV(rp, r_link); + rp = HEAD(dp->d_changes); while (rp != NULL) { if (rp->r_opcode == ADD && rp->r_dp != NULL && @@ -281,15 +309,13 @@ sx_send_ixfr(struct qstream *qsp) { foundsoa = 1; break; } - trp = rp; rp = NEXT(rp, r_link); } if (!foundsoa) { cp = (char *)findsoaserial(old_soadp->d_data); - if (NEXT(qsp->xfr.top.ixfr, r_link) != NULL) { - trp = qsp->xfr.top.ixfr; - PUTLONG(NEXT(trp, r_link)->r_zone, cp); + if (NEXT(dp, d_link) != NULL) { + PUTLONG(HEAD(dp->d_changes)->r_zone, cp); if (sx_addrr(qsp, zp->z_origin, old_soadp) < 0) goto cleanup; @@ -303,52 +329,77 @@ sx_send_ixfr(struct qstream *qsp) { qsp->xfr.state = s_x_adding; /* FALLTHROUGH */ case s_x_adding: - if (qsp->xfr.top.ixfr) { - /* see s_x_deleting */ - rp = qsp->xfr.top.ixfr; - while (PREV(rp, r_link) != NULL) - rp = PREV(rp, r_link); - while (rp != NULL) { - if (rp->r_opcode == ADD && - rp->r_dp != NULL && - rp->r_dp->d_type != T_SOA) { - if (sx_addrr(qsp, rp->r_dname, - rp->r_dp) < 0) - goto cleanup; - db_freedata(rp->r_dp); - rp->r_dp = NULL; + ns_debug(ns_log_default, 3, + "IXFR: s_x_adding (%s)", zp->z_origin); + dp = NULL; + if (qsp->xfr.top.ixfr != NULL && !EMPTY(*qsp->xfr.top.ixfr)) { + dp = HEAD(*qsp->xfr.top.ixfr); + if (dp != NULL) { + /* see s_x_deleting */ + rp = HEAD(dp->d_changes); + while (rp != NULL) { + if (rp->r_opcode == ADD && + rp->r_dp != NULL && + rp->r_dp->d_type != T_SOA) { + if (sx_addrr(qsp, rp->r_dname, + rp->r_dp) < 0) + goto cleanup; + db_freedata(rp->r_dp); + rp->r_dp = NULL; + } + rp = NEXT(rp, r_link); } - trp = rp; - rp = NEXT(rp, r_link); - } - /* move to next update */ - rp = qsp->xfr.top.ixfr; - qsp->xfr.top.ixfr = NEXT(rp, r_link); - PREV(rp, r_link) = NULL; - /* clean up old update */ - while (rp != NULL) { - trp = PREV(rp, r_link); - if (rp->r_dp != NULL) { - db_freedata(rp->r_dp); - rp->r_dp = NULL; + /* move to next update */ + UNLINK(*qsp->xfr.top.ixfr, dp, d_link); + + /* clean up old update */ + while ((rp = HEAD(dp->d_changes)) != NULL) { + UNLINK(dp->d_changes, rp, r_link); + if (rp->r_dp != NULL) { + db_freedata(rp->r_dp); + rp->r_dp = NULL; + } + res_freeupdrec(rp); + } + memput(dp, sizeof (*dp)); + if (HEAD(*qsp->xfr.top.ixfr) != NULL) { + qsp->xfr.state = s_x_deletesoa; + goto again; } - res_freeupdrec(rp); - rp = trp; } } qsp->xfr.state = s_x_lastsoa; /* FALLTHROUGH */ case s_x_lastsoa: - if (qsp->xfr.ixfr_zone != 0) { + ns_debug(ns_log_default, 3, + "IXFR: s_x_lastsoa (%s)", zp->z_origin); + if (qsp->xfr.ixfr_zone != 0) sx_addrr(qsp, zp->z_origin, soa_dp); - } break; } + ns_debug(ns_log_default, 3, "IXFR: flushing %s", zp->z_origin); qsp->xfr.state = s_x_done; sx_flush(qsp); sq_writeh(qsp, sq_flushw); cleanup: + if (qsp->xfr.top.ixfr != NULL) { + if(!EMPTY(*qsp->xfr.top.ixfr)) { + while ((dp = HEAD(*qsp->xfr.top.ixfr)) != NULL) { + UNLINK(*qsp->xfr.top.ixfr, dp, d_link); + while ((rp = HEAD(dp->d_changes)) != NULL) { + UNLINK(dp->d_changes, rp, r_link); + if (rp->r_dp != NULL) + db_freedata(rp->r_dp); + rp->r_dp = NULL; + res_freeupdrec(rp); + } + memput(dp, sizeof *dp); + } + } + memput(qsp->xfr.top.ixfr, sizeof *qsp->xfr.top.ixfr); + qsp->xfr.top.ixfr = NULL; + } memput(old_soadp, DATASIZE(old_soadp->d_size)); } @@ -358,9 +409,19 @@ sx_send_ixfr(struct qstream *qsp) { #endif -int ixfr_log_maint(struct zoneinfo *zp) { - int fd, rcount, wcount, rval; - int found = 0, seek = 0; +/* + * int ixfr_log_maint(struct zoneinfo *zp, int fast_trim) + * + * zp - pointer to the zone information + * fast_trim - is used to denote that this is not called on the regular + * maintaince cycle. + * + */ +int ixfr_log_maint(struct zoneinfo *zp, int fast_trim) { + int fd, rcount, wcount; + int found = 0; + int error = 0; + long seek = 0; FILE *to_fp, *from_fp, *db_fp; static char *tmpname; struct stat db_sb; @@ -369,50 +430,16 @@ int ixfr_log_maint(struct zoneinfo *zp) { ns_debug(ns_log_default, 3, "ixfr_log_maint(%s)", zp->z_origin); - tmpname = memget(strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1); - if (!tmpname) { - ns_warning(ns_log_default, "memget failed"); - return (-1); - } -#ifdef SHORT_FNAMES - filenamecpy(tmpname, zp->z_ixfr_base); -#else - (void) strcpy(tmpname, zp->z_ixfr_base); -#endif /* SHORT_FNAMES */ - - (void) strcat(tmpname, ".XXXXXX"); - if ((fd = mkstemp(tmpname)) == -1) { - ns_warning(ns_log_db, "can't make tmpfile (%s): %s", - strerror(errno)); - memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); - return (-1); - } - if ((to_fp = fdopen(fd, "r+")) == NULL) { - ns_warning(ns_log_db, "%s: %s", - tmpname, strerror(errno)); - (void) unlink(tmpname); - memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); - (void) close(fd); - return (-1); - } /* find out how big the zone db file is */ if ((db_fp = fopen(zp->z_source, "r")) == NULL) { ns_warning(ns_log_db, "%s: %s", zp->z_source, strerror(errno)); - (void) unlink(tmpname); - memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); - (void) my_fclose(to_fp); - (void) close(fd); return (-1); } if (fstat(fileno(db_fp), &db_sb) < 0) { ns_warning(ns_log_db, "%s: %s", zp->z_source, strerror(errno)); - (void) my_fclose(to_fp); (void) my_fclose(db_fp); - (void) close(fd); - (void) unlink(tmpname); - memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); return (-1); } (void) my_fclose(db_fp); @@ -421,39 +448,32 @@ int ixfr_log_maint(struct zoneinfo *zp) { db_sb.st_size); /* open up the zone ixfr log */ - if ((from_fp = fopen(zp->z_ixfr_base, "r")) == NULL) { + if ((from_fp = fopen(zp->z_ixfr_base, "r")) == NULL) { ns_warning(ns_log_db, "%s: %s", zp->z_ixfr_base, strerror(errno)); - (void) my_fclose(to_fp); - (void) close(fd); - (void) unlink(tmpname); - memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); return (-1); } if (fstat(fileno(from_fp), &sb) < 0) { ns_warning(ns_log_db, "%s: %s", zp->z_ixfr_base, strerror(errno)); - (void) my_fclose(to_fp); - (void) close(fd); - (void) unlink(tmpname); (void) my_fclose(from_fp); - memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); return (-1); } - ns_debug(ns_log_default, 3, "%s, size %d log_s %d max %d\n", + ns_debug(ns_log_default, 3, "%s, size %d max %d\n", zp->z_ixfr_base, sb.st_size, - zp->z_log_size_ixfr, zp->z_max_log_size_ixfr); if (zp->z_max_log_size_ixfr) { if (sb.st_size > zp->z_max_log_size_ixfr) - seek = sb.st_size - (zp->z_max_log_size_ixfr + (zp->z_max_log_size_ixfr *.10)); + seek = (signed)sb.st_size - + (signed)(zp->z_max_log_size_ixfr + + (zp->z_max_log_size_ixfr * .10) ); else seek = 0; } else { if (sb.st_size > (db_sb.st_size * .50)) - seek = sb.st_size - ((db_sb.st_size * .50) + seek = (signed)sb.st_size - (signed)((db_sb.st_size * .50) + ((db_sb.st_size * zp->z_max_log_size_ixfr) *.10)); else seek = 0; @@ -463,43 +483,58 @@ int ixfr_log_maint(struct zoneinfo *zp) { { ns_debug(ns_log_default, 3, "%s does not need to be reduced", zp->z_ixfr_base); - (void) my_fclose(to_fp); - (void) close(fd); - (void) unlink(tmpname); (void) my_fclose(from_fp); - memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); return (-1); } + if ((fast_trim) && seek < (zp->z_max_log_size_ixfr + 100000)) { + (void) my_fclose(from_fp); + return (0); + } + + tmpname = memget(strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1); + if (!tmpname) { + ns_warning(ns_log_default, "memget failed"); + return (-1); + } +#ifdef SHORT_FNAMES + filenamecpy(tmpname, zp->z_ixfr_base); +#else + (void) strcpy(tmpname, zp->z_ixfr_base); +#endif /* SHORT_FNAMES */ + + (void) strcat(tmpname, ".XXXXXX"); + if ((fd = mkstemp(tmpname)) == -1) { + ns_warning(ns_log_db, "can't make tmpfile (%s): %s", + strerror(errno)); + memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); + return (-1); + } + if ((to_fp = fdopen(fd, "r+")) == NULL) { + ns_warning(ns_log_db, "%s: %s", + tmpname, strerror(errno)); + (void) unlink(tmpname); + memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); + (void) close(fd); + return (-1); + } if (fgets(buf, sizeof(buf), from_fp) == NULL) { ns_error(ns_log_update, "fgets() from %s failed: %s", zp->z_ixfr_base, strerror(errno)); - (void) my_fclose(from_fp); - (void) my_fclose(to_fp); - (void) close(fd); - (void) unlink(tmpname); - memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); - return (-1); + error++; + goto clean_up; } if (strcmp(buf, LogSignature) != 0) { ns_error(ns_log_update, "invalid log file %s", zp->z_ixfr_base); - (void) my_fclose(from_fp); - (void) my_fclose(to_fp); - (void) close(fd); - (void) unlink(tmpname); - memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); - return (-3); + error++; + goto clean_up; } - if (fseek( from_fp, seek, 0) < 0) { - (void) my_fclose(from_fp); - (void) my_fclose(to_fp); - (void) close(fd); - (void) unlink(tmpname); - memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); - return (-1); + if (fseek( from_fp, seek, 0) < 0) { + error++; + goto clean_up; } found = 0; @@ -517,47 +552,61 @@ int ixfr_log_maint(struct zoneinfo *zp) { if (found) { ns_debug(ns_log_default, 1, "ixfr_log_maint(): found [END_DELTA]"); + fprintf(to_fp, "%s", LogSignature); + while ((rcount = fread(buf, sizeof(char), MAXBSIZE, from_fp)) > 0) { wcount = fwrite(buf, sizeof(char), rcount, to_fp); if (rcount != wcount || wcount == -1) { ns_warning(ns_log_default, "ixfr_log_maint: error in writting copy"); - rval = 1; break; } - } - if (rcount < 0) { - ns_warning(ns_log_default, "ixfr_log_maint: error in reading copy"); - rval = 1; } + if (rcount < 0) + ns_warning(ns_log_default, + "ixfr_log_maint: error in reading copy"); } + clean_up: (void) my_fclose(to_fp); (void) close(fd); (void) my_fclose(from_fp); - if (rename(tmpname, zp->z_ixfr_base) == -1) { - ns_warning(ns_log_default, "can not rename %s to %s :%s", - tmpname, zp->z_ixfr_base, strerror(errno)); + if (error == 0) { + if (rename(tmpname, zp->z_ixfr_base) == -1) { + ns_warning(ns_log_default, "can not rename %s to %s :%s", + tmpname, zp->z_ixfr_base, strerror(errno)); + } + if ((from_fp = fopen(zp->z_ixfr_base, "r")) == NULL) { + ns_warning(ns_log_db, "%s: %s", + zp->z_ixfr_base, strerror(errno)); + return (-1); + } + if (fstat(fileno(from_fp), &sb) < 0) { + ns_warning(ns_log_db, "%s: %s", + zp->z_ixfr_base, strerror(errno)); + (void) my_fclose(from_fp); + return (-1); + } + if (sb.st_size <= 0) + (void) unlink(zp->z_ixfr_base); + else if (chmod(zp->z_ixfr_base, 0644) < 0) + ns_error(ns_log_update, + "chmod(%s,%o) failed, pressing on: %s", + zp->z_source, sb.st_mode, + strerror(errno)); } (void) unlink(tmpname); memput(tmpname, (strlen(zp->z_ixfr_base) + sizeof(".XXXXXX") + 1)); - if ((from_fp = fopen(zp->z_ixfr_base, "r")) == NULL) { - ns_warning(ns_log_db, "%s: %s", - zp->z_ixfr_base, strerror(errno)); - return (-1); - } - if (fstat(fileno(from_fp), &sb) < 0) { - ns_warning(ns_log_db, "%s: %s", - zp->z_ixfr_base, strerror(errno)); - (void) my_fclose(from_fp); - return (-1); - } - if (sb.st_size <= 0) - (void) unlink(zp->z_ixfr_base); (void) my_fclose(from_fp); - ns_debug(ns_log_default, 3, "%s, size %d log_s %d max %d\n", + zp->z_serial_ixfr_start = 0; /* signal to read for lowest serial number */ + + ns_debug(ns_log_default, 3, "%s, size %d max %d\n", zp->z_ixfr_base, sb.st_size, - zp->z_log_size_ixfr, zp->z_max_log_size_ixfr); - return (0); + + if (error) + return(-1); + else + return (0); } + diff --git a/contrib/bind/bin/named/ns_lexer.c b/contrib/bind/bin/named/ns_lexer.c index 244d5f6..7110fe4 100644 --- a/contrib/bind/bin/named/ns_lexer.c +++ b/contrib/bind/bin/named/ns_lexer.c @@ -1,9 +1,9 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ns_lexer.c,v 8.19 1999/10/13 16:39:08 vixie Exp $"; +static const char rcsid[] = "$Id: ns_lexer.c,v 8.20 2000/04/21 06:54:07 vixie Exp $"; #endif /* not lint */ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/ns_lexer.h b/contrib/bind/bin/named/ns_lexer.h index 66c19f2..7a22b8e 100644 --- a/contrib/bind/bin/named/ns_lexer.h +++ b/contrib/bind/bin/named/ns_lexer.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/ns_main.c b/contrib/bind/bin/named/ns_main.c index 1377098..199190f 100644 --- a/contrib/bind/bin/named/ns_main.c +++ b/contrib/bind/bin/named/ns_main.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)ns_main.c 4.55 (Berkeley) 7/1/91"; -static const char rcsid[] = "$Id: ns_main.c,v 8.117 1999/11/08 23:01:38 vixie Exp $"; +static const char rcsid[] = "$Id: ns_main.c,v 8.125 2000/04/21 06:54:08 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: ns_main.c,v 8.117 1999/11/08 23:01:38 vixie Ex */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -146,7 +146,11 @@ static int iflist_dont_rescan = 0; static const int drbufsize = 32 * 1024, /* UDP rcv buf size */ dsbufsize = 48 * 1024, /* UDP snd buf size */ sbufsize = 16 * 1024, /* TCP snd buf size */ +#ifdef BROKEN_RECVFROM + nudptrans = 1, +#else nudptrans = 20, /* #/udps per select */ +#endif listenmax = 50; static u_int16_t nsid_state; @@ -318,8 +322,8 @@ main(int argc, char *argv[], char *envp[]) { break; case 'v': - fprintf(stderr, "%s\n", Version); - exit(1); + fprintf(stdout, "%s\n", Version); + exit(0); #ifdef CAN_CHANGE_ID case 'u': @@ -754,6 +758,10 @@ tcp_send(struct qinfo *qp) { sq_remove(sp); return (SERVFAIL); } + if (fcntl(sp->s_rfd, F_SETFD, 1) < 0) { + sq_remove(sp); + return (SERVFAIL); + } if (sq_openw(sp, qp->q_msglen + INT16SZ) == -1) { sq_remove(sp); return (SERVFAIL); @@ -785,7 +793,7 @@ tcp_send(struct qinfo *qp) { static void stream_send(evContext lev, void *uap, int fd, const void *la, int lalen, - const void *ra, int ralen) { + const void *ra, int ralen) { struct qstream *sp = uap; ns_debug(ns_log_default, 1, "stream_send"); @@ -890,7 +898,8 @@ stream_getlen(evContext lev, void *uap, int fd, int bytes) { } } - iov = evConsIovec(sp->s_buf, sp->s_size); + iov = evConsIovec(sp->s_buf, (sp->s_size <= sp->s_bufsize) ? + sp->s_size : sp->s_bufsize); if (evRead(lev, sp->s_rfd, &iov, 1, stream_getmsg, sp, &sp->evID_r) == -1) ns_panic(ns_log_default, 1, "evRead(fd %d): %s", @@ -1127,13 +1136,13 @@ getnetconf(int periodic_scan) { ifc.ifc_len = bufsiz; ifc.ifc_buf = buf; #ifdef IRIX_EMUL_IOCTL_SIOCGIFCONF - /* - * This is a fix for IRIX OS in which the call to ioctl with - * the flag SIOCGIFCONF may not return an entry for all the - * interfaces like most flavors of Unix. - */ - if (emul_ioctl(&ifc) >= 0) - break; + /* + * This is a fix for IRIX OS in which the call to ioctl with + * the flag SIOCGIFCONF may not return an entry for all the + * interfaces like most flavors of Unix. + */ + if (emul_ioctl(&ifc) >= 0) + break; #else if ((n = ioctl(s, SIOCGIFCONF, (char *)&ifc)) != -1) { /* @@ -1431,6 +1440,11 @@ opensocket_d(interface *ifp) { ns_notice(ns_log_default, "fcntl(dfd, F_DUPFD, 20): %s", strerror(errno)); #endif + if (fcntl(ifp->dfd, F_SETFD, 1) < 0) { + ns_error(ns_log_default, "F_SETFD: %s", strerror(errno)); + close(ifp->dfd); + return (-1); + } ns_debug(ns_log_default, 1, "ifp->addr %s d_dfd %d", sin_ntoa(nsa), ifp->dfd); if (setsockopt(ifp->dfd, SOL_SOCKET, SO_REUSEADDR, @@ -1516,6 +1530,11 @@ opensocket_s(interface *ifp) { ns_notice(ns_log_default, "fcntl(sfd, F_DUPFD, 20): %s", strerror(errno)); #endif + if (fcntl(ifp->sfd, F_SETFD, 1) < 0) { + ns_error(ns_log_default, "F_SETFD: %s", strerror(errno)); + close(ifp->sfd); + return (-1); + } if (setsockopt(ifp->sfd, SOL_SOCKET, SO_REUSEADDR, (char *)&on, sizeof on) != 0) { ns_notice(ns_log_default, "setsockopt(REUSEADDR): %s", @@ -1617,6 +1636,8 @@ opensocket_f() { strerror(errno)); if (ds > evHighestFD(ev)) ns_panic(ns_log_default, 1, "socket too high: %d", ds); + if (fcntl(ds, F_SETFD, 1) < 0) + ns_panic(ns_log_default, 1, "F_SETFD: %s", strerror(errno)); if (setsockopt(ds, SOL_SOCKET, SO_REUSEADDR, (char *)&on, sizeof on) != 0) { ns_notice(ns_log_default, "setsockopt(REUSEADDR): %s", @@ -1719,7 +1740,7 @@ sq_remove(struct qstream *qp) { INSIST_ERR(evDeselectFD(ev, qp->evID_w) != -1); if (qp->flags & STREAM_CONNECT_EV) INSIST_ERR(evCancelConn(ev, qp->evID_c) != -1); - if (qp->flags & STREAM_AXFR) + if (qp->flags & STREAM_AXFR || qp->flags & STREAM_AXFRIXFR) ns_freexfr(qp); (void) close(qp->s_rfd); if (qp == streamq) @@ -1945,7 +1966,7 @@ sq_done(struct qstream *sp) { sp->s_wbuf_send = sp->s_wbuf_free = NULL; sp->s_wbuf_end = sp->s_wbuf = NULL; } - if (sp->flags & STREAM_AXFR) + if (sp->flags & STREAM_AXFR || sp->flags & STREAM_AXFRIXFR) ns_freexfr(sp); sp->s_refcnt = 0; sp->s_time = tt.tv_sec; @@ -2340,7 +2361,7 @@ static const u_int16_t nsid_multiplier_table[] = { 10853, 1453, 18069, 21693, 30573, 36261, 37421, 42533 }; #define NSID_MULT_TABLE_SIZE \ - ((sizeof nsid_multiplier_table)/(sizeof nsid_multiplier_table[0])) + ((sizeof nsid_multiplier_table)/(sizeof nsid_multiplier_table[0])) void nsid_init(void) { @@ -2623,6 +2644,7 @@ init_needs(void) { handlers[main_need_debug] = use_desired_debug; handlers[main_need_restart] = ns_restart; handlers[main_need_reap] = reapchild; + handlers[main_need_noexpired] = ns_noexpired; } static void @@ -2703,18 +2725,18 @@ meminit(size_t init_max_size, size_t target_size) { void * memget_debug(size_t size, const char *file, int line) { - void *ptr; - ptr = __memget(size); - fprintf(stderr, "%s:%d: memget(%lu) -> %p\n", file, line, - (u_long)size, ptr); - return (ptr); + void *ptr; + ptr = __memget(size); + fprintf(stderr, "%s:%d: memget(%lu) -> %p\n", file, line, + (u_long)size, ptr); + return (ptr); } void memput_debug(void *ptr, size_t size, const char *file, int line) { - fprintf(stderr, "%s:%d: memput(%p, %lu)\n", file, line, ptr, - (u_long)size); - __memput(ptr, size); + fprintf(stderr, "%s:%d: memput(%p, %lu)\n", file, line, ptr, + (u_long)size); + __memput(ptr, size); } void diff --git a/contrib/bind/bin/named/ns_maint.c b/contrib/bind/bin/named/ns_maint.c index 69a8fc3..9b9e16e 100644 --- a/contrib/bind/bin/named/ns_maint.c +++ b/contrib/bind/bin/named/ns_maint.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)ns_maint.c 4.39 (Berkeley) 3/2/91"; -static const char rcsid[] = "$Id: ns_maint.c,v 8.95 1999/10/13 16:39:09 vixie Exp $"; +static const char rcsid[] = "$Id: ns_maint.c,v 8.103 2000/04/23 02:18:58 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: ns_maint.c,v 8.95 1999/10/13 16:39:09 vixie Ex */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -134,6 +134,8 @@ static void startxfer(struct zoneinfo *), abortxfer(struct zoneinfo *), tryxfer(void), purge_z_2(struct hashbuf *, int); +static int purge_nonglue_2(const char *, struct hashbuf *, + int, int); #ifndef HAVE_SPAWNXFER static pid_t spawnxfer(char **, struct zoneinfo *); @@ -178,10 +180,19 @@ zone_maint(struct zoneinfo *zp) { #endif if (zp->z_serial != 0 && ((zp->z_lastupdate+zp->z_expire) < (u_int32_t)tt.tv_sec)) { + if ((zp->z_flags & Z_NOTIFY) != 0) + ns_stopnotify(zp->z_origin, zp->z_class); /* calls purge_zone */ do_reload(zp->z_origin, zp->z_type, zp->z_class, 0); /* reset zone state */ + if (!haveComplained((u_long)zp, (u_long)stale)) { + ns_notice(ns_log_default, + "%s zone \"%s\" expired", + zoneTypeString(zp->z_type), + zp->z_origin); + } zp->z_flags &= ~Z_AUTH; + zp->z_flags |= Z_EXPIRED; zp->z_refresh = INIT_REFRESH; zp->z_retry = INIT_REFRESH; zp->z_serial = 0; @@ -247,9 +258,9 @@ zone_maint(struct zoneinfo *zp) { zp->z_dumptime = 0; (void)schedule_dump(zp); } - if (zp->z_maintain_ixfr_base) - ixfr_log_maint(zp); } + if (zp->z_maintain_ixfr_base) + ixfr_log_maint(zp); break; #endif /* BIND_UPDATE */ @@ -402,7 +413,7 @@ ns_cleancache(evContext ctx, void *uap, void ns_heartbeat(evContext ctx, void *uap, struct timespec due, - struct timespec inter) + struct timespec inter) { struct zoneinfo *zp; @@ -417,12 +428,9 @@ ns_heartbeat(evContext ctx, void *uap, struct timespec due, (zp->z_dialup == zdialup_use_default && NS_OPTION_P(OPTION_NODIALUP))) continue; -#ifdef BIND_NOTIFY - if ((zp->z_notify == znotify_no) || - ((zp->z_notify == znotify_use_default) && - NS_OPTION_P(OPTION_NONOTIFY))) - continue; -#endif + /* + * Perform the refresh query that was suppressed. + */ if ((zt == z_slave || zt == z_stub) && (zp->z_flags & (Z_NEED_RELOAD|Z_NEED_XFER|Z_QSERIAL|Z_XFER_RUNNING) @@ -432,6 +440,18 @@ ns_heartbeat(evContext ctx, void *uap, struct timespec due, *(zp->z_origin) ? zp->z_origin : "."); qserial_query(zp); } +#ifdef BIND_NOTIFY + /* + * Trigger a refresh query while the link is up by + * sending a notify. + */ + if (((zp->z_notify == znotify_yes) || + ((zp->z_notify == znotify_use_default) && + !NS_OPTION_P(OPTION_NONOTIFY))) && + (zt == z_master || zt == z_slave) && !loading && + ((zp->z_flags & Z_AUTH) != 0)) + ns_notify(zp->z_origin, zp->z_class, ns_t_soa); +#endif } } @@ -453,8 +473,10 @@ markUpToDate(struct zoneinfo *zp) { * but only if there were no errors * in the zone file. */ - if ((zp->z_flags & Z_DB_BAD) == 0) + if ((zp->z_flags & Z_DB_BAD) == 0) { zp->z_flags |= Z_AUTH; + zp->z_flags &= ~Z_EXPIRED; + } if (zp->z_source) { struct timeval t[2]; @@ -642,6 +664,7 @@ write_tsig_info(struct in_addr addr, char *name, int *fd, int creat_failed) { name); return(-1); } + (void) fchown(tsig_fd, user_id, group_id); } if (creat_failed != 0) return(-1); @@ -796,7 +819,7 @@ startxfer(struct zoneinfo *zp) { } *curr = '\0'; ns_debug(ns_log_xfer_in, 1, buffer); - } + } #endif /* DEBUG */ gettime(&tt); @@ -1066,6 +1089,8 @@ remove_zone(struct zoneinfo *zp, const char *verb) { (zp->z_flags & Z_NEED_DUMP) != 0)) (void) zonedump(zp, ISNOTIXFR); #endif + if ((zp->z_flags & Z_NOTIFY) != 0) + ns_stopnotify(zp->z_origin, zp->z_class); ns_stopxfrs(zp); do_reload(zp->z_origin, zp->z_type, zp->z_class, 1); ns_notice(ns_log_config, "%s zone \"%s\" (%s) %s", @@ -1078,6 +1103,145 @@ remove_zone(struct zoneinfo *zp, const char *verb) { free_zone(zp); } +int +purge_nonglue(const char *dname, struct hashbuf *htp, int class) { + const char *fname; + struct namebuf *np; + struct hashbuf *phtp = htp; + int root_zone = 0; + int errs = 0; + + ns_debug(ns_log_default, 1, "purge_zone(%s,%d)", dname, class); + if ((np = nlookup(dname, &phtp, &fname, 0)) && dname == fname && + !ns_wildcard(NAME(*np))) { + + if (*dname == '\0') + root_zone = 1; + + if (np->n_hash != NULL || root_zone) { + struct hashbuf *h; + + if (root_zone) + h = htp; + else + h = np->n_hash; + errs += purge_nonglue_2(dname, h, class, 0); + if (h->h_cnt == 0 && !root_zone) { + rm_hash(np->n_hash); + np->n_hash = NULL; + } + } + } + return (errs); +} + +static int +valid_glue(struct databuf *dp, char *name, int belowcut) { + + /* NS records are only valid glue at the zone cut */ + if (belowcut && dp->d_type == T_NS) + return(0); + + if (ISVALIDGLUE(dp)) /* T_NS/T_A/T_AAAA/T_A6 */ + return (1); + + if (belowcut) + return (0); + + /* Parent NXT record? */ + if (dp->d_type == T_NXT && !ns_samedomain((char*)dp->d_data, name) && + ns_samedomain((char*)dp->d_data, zones[dp->d_zone].z_origin)) + return (1); + + /* NOKEY is in parent zone otherwise child zone */ + if (dp->d_type == T_KEY && dp->d_size == 4 && + (dp->d_data[0] & 0xc6) == 0xc2) + return (1); + + /* NXT & KEY records may be signed */ + if (!belowcut && dp->d_type == T_SIG && + (SIG_COVERS(dp) == T_NXT || SIG_COVERS(dp) == T_KEY)) + return (1); + return (0); +} + +static int +purge_nonglue_2(const char *dname, struct hashbuf *htp, int class, + int belowcut) +{ + struct databuf *dp, *pdp; + struct namebuf *np, *pnp, *npn; + struct namebuf **npp, **nppend; + int errs = 0; + int zonecut; + char name[MAXDNAME]; + + nppend = htp->h_tab + htp->h_size; + for (npp = htp->h_tab; npp < nppend; npp++) { + for (pnp = NULL, np = *npp; np != NULL; np = npn) { + if (!bottom_of_zone(np->n_data, class)) { + zonecut = belowcut; + for (dp = np->n_data; dp != NULL; + dp = dp->d_next) { + if (match(dp, class, ns_t_ns)) { + zonecut = 1; + break; + } + } + getname(np, name, sizeof name); + for (pdp = NULL, dp = np->n_data; + dp != NULL; + (void)NULL) { + if (dp->d_class == class && + zonecut && + !valid_glue(dp, name, belowcut)) { + ns_error(ns_log_db, + "zone: %s/%s: non-glue record %s bottom of zone: %s/%s", + *dname ? dname : ".", + p_class(dp->d_class), + belowcut ? "below" : + "at", + *name ? name : ".", + p_type(dp->d_type)); + dp = rm_datum(dp, np, pdp, + NULL); + errs++; + } else { + pdp = dp; + dp = dp->d_next; + } + } + if (np->n_hash) { + /* + * call recursively to clean + * subdomains + */ + errs += purge_nonglue_2(dname, + np->n_hash, + class, + zonecut || + belowcut); + + /* if now empty, free it */ + if (np->n_hash->h_cnt == 0) { + rm_hash(np->n_hash); + np->n_hash = NULL; + } + } + } + + if (np->n_hash == NULL && np->n_data == NULL) { + npn = rm_name(np, npp, pnp); + htp->h_cnt--; + } else { + npn = np->n_next; + pnp = np; + } + } + } + return (errs); +} + void purge_zone(const char *dname, struct hashbuf *htp, int class) { const char *fname; @@ -1186,7 +1350,7 @@ bottom_of_zone(struct databuf *dp, int class) { ns_debug(ns_log_default, 3, "bottom_of_zone() == %d", ret); return (ret); } - + /* * Handle XFER limit for a nameserver. */ @@ -1295,7 +1459,7 @@ reapchild(void) { */ void endxfer() { - struct zoneinfo *zp; + struct zoneinfo *zp; int exitstatus, i; pid_t pid; WAIT_T status; @@ -1324,8 +1488,8 @@ endxfer() { if (WIFSIGNALED(status)) { if (WTERMSIG(status) != SIGKILL) { ns_notice(ns_log_default, - "named-xfer \"%s\" exited with signal %d", - zp->z_origin[0]?zp->z_origin:".", + "named-xfer \"%s\" exited with signal %d", + zp->z_origin[0]?zp->z_origin:".", WTERMSIG(status)); } ns_retrytime(zp, tt.tv_sec); @@ -1351,8 +1515,8 @@ endxfer() { break; case XFER_SUCCESSIXFR: + zp->z_flags |= Z_XFER_RUNNING; zp->z_xferpid = XFER_ISIXFR; - zp->z_log_size_ixfr++; ns_notice(ns_log_default, "IXFR Success %s", zp->z_ixfr_tmp); @@ -1374,6 +1538,8 @@ endxfer() { ns_notice(ns_log_default, "IXFR Merge failed %s", zp->z_ixfr_tmp); + zp->z_flags &= + ~(Z_XFER_RUNNING|Z_XFER_ABORTED|Z_XFER_GONE); break; case XFER_TIMEOUT: @@ -1436,7 +1602,7 @@ tryxfer() { zp = zones; } lastnzones = nzones; - + if (zp == zones) stopzp = &zones[nzones-1]; else @@ -1482,7 +1648,7 @@ tryxfer() { */ void loadxfer(void) { - struct zoneinfo *zp; + struct zoneinfo *zp; u_int32_t old_serial,new_serial; char *tmpnom; int isixfr; @@ -1512,11 +1678,12 @@ loadxfer(void) { if (!db_load(tmpnom, zp->z_origin, zp, NULL, isixfr)) { zp->z_flags |= Z_AUTH; + zp->z_flags &= ~Z_EXPIRED; if (isixfr == ISIXFR) { new_serial= zp ->z_serial; ns_warning(ns_log_db, "ISIXFR"); ns_warning(ns_log_db, "error in updating ixfr data base file %s from %s", zp -> z_ixfr_base, zp ->z_ixfr_tmp); - if (zonedump(zp,ISIXFR)<0) + if (zonedump(zp,ISIXFR)<0) ns_warning(ns_log_db, "error in write ixfr updates to zone file %s", zp ->z_source); } @@ -1578,6 +1745,16 @@ reload_master(struct zoneinfo *zp) { zp->z_flags &= ~Z_AUTH; ns_stopxfrs(zp); /* XXX what about parent zones? */ +#ifdef BIND_UPDATE + /* + * A dynamic zone might have changed, so we + * need to dump it before reloading it. + */ + if ((zp->z_flags & Z_DYNAMIC) != 0 && + ((zp->z_flags & Z_NEED_SOAUPDATE) != 0 || + (zp->z_flags & Z_NEED_DUMP) != 0)) + (void) zonedump(zp, ISNOTIXFR); +#endif purge_zone(zp->z_origin, hashtab, zp->z_class); ns_debug(ns_log_config, 1, "reloading zone"); #ifdef BIND_UPDATE @@ -1640,7 +1817,9 @@ ns_zreload(void) { */ void ns_reload(void) { - ns_notice(ns_log_default, "reloading nameserver"); + ns_notice(ns_log_default, "%s %snameserver", + (reconfiging != 0) ? "reconfiguring" : "reloading", + (noexpired == 1) ? "(-noexpired) " : ""); INSIST(reloading == 0); qflush(); @@ -1653,6 +1832,18 @@ ns_reload(void) { } /* + * Reload configuration, look for new or deleted zones, not changed ones + * also ignore expired zones. + */ +void +ns_noexpired(void) { + INSIST(noexpired == 0); + noexpired++; /* To ignore zones which are expired */ + ns_reconfig(); + noexpired--; +} + +/* * Reload configuration, look for new or deleted zones, not changed ones. */ void diff --git a/contrib/bind/bin/named/ns_ncache.c b/contrib/bind/bin/named/ns_ncache.c index 437072c..2b8bb6b 100644 --- a/contrib/bind/bin/named/ns_ncache.c +++ b/contrib/bind/bin/named/ns_ncache.c @@ -1,9 +1,9 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ns_ncache.c,v 8.26 1999/10/13 16:39:10 vixie Exp $"; +static const char rcsid[] = "$Id: ns_ncache.c,v 8.27 2000/04/21 06:54:09 vixie Exp $"; #endif /* not lint */ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/ns_notify.c b/contrib/bind/bin/named/ns_notify.c index ac03732e..0cf1e0a 100644 --- a/contrib/bind/bin/named/ns_notify.c +++ b/contrib/bind/bin/named/ns_notify.c @@ -1,9 +1,9 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ns_notify.c,v 8.4 1999/10/15 19:49:04 vixie Exp $"; +static const char rcsid[] = "$Id: ns_notify.c,v 8.10 2000/04/21 06:54:09 vixie Exp $"; #endif /* not lint */ /* - * Copyright (c) 1994-1999 by Internet Software Consortium. + * Copyright (c) 1994-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -78,6 +78,7 @@ static void notify_timer(evContext, void *, /* Local. */ static LIST(struct notify) pending_notifies; +static LIST(struct notify) loading_notifies; /* Public. */ @@ -100,6 +101,13 @@ ns_notify(const char *dname, ns_class class, ns_type type) { p_class(class), p_type(type)); return; } + if (ns_samename(dname, zp->z_origin) != 1) { + ns_warning(ns_log_notify, + "notify not called with top of zone (\"%s\" %s %s)", + (dname && *dname) ? dname : ".", + p_class(class), p_type(type)); + return; + } if ((zp->z_flags & Z_NOTIFY) != 0) { ns_info(ns_log_notify, "suppressing duplicate notify (\"%s\" %s %s)", @@ -123,6 +131,11 @@ ns_notify(const char *dname, ns_class class, ns_type type) { ni->type = type; evInitID(&ni->timer); + if (loading != 0) { + APPEND(loading_notifies, ni, link); + return; + } + /* Delay notification for from five seconds up to fifteen minutes. */ max_delay = MIN(nzones/5, 895); max_delay = MAX(max_delay, 25); @@ -146,6 +159,19 @@ ns_notify(const char *dname, ns_class class, ns_type type) { ni, zp, delay); } +void +notify_afterload() { + struct notify *ni; + + INSIST(loading == 0); + while ((ni = HEAD(loading_notifies)) != NULL) { + UNLINK(loading_notifies, ni, link); + ns_notify(ni->name, ni->class, ni->type); + freestr(ni->name); + memput(ni, sizeof *ni); + } +} + /* * ns_unnotify() * call this when all pending notifies are now considered junque. @@ -161,6 +187,25 @@ ns_unnotify(void) { } } +/* + * ns_stopnotify(const char *dname, ns_class class) + * stop notifies for this particular zone. + */ +void +ns_stopnotify(const char *dname, ns_class class) { + struct notify *ni; + + ni = HEAD(pending_notifies); + while (ni != NULL && + (ni->class != class || ns_samename(ni->name, dname) != 1)) + ni = NEXT(ni, link); + + if (ni != NULL) { + UNLINK(pending_notifies, ni, link); + free_notify(ni); + } +} + /* Private. */ /* @@ -171,6 +216,7 @@ ns_unnotify(void) { static void sysnotify(const char *dname, ns_class class, ns_type type) { const char *zname, *fname; + u_int32_t zserial; int nns, na, i; struct zoneinfo *zp; struct in_addr *also_addr; @@ -198,10 +244,9 @@ sysnotify(const char *dname, ns_class class, ns_type type) { return; } zname = zp->z_origin; + zserial = zp->z_serial; nns = na = 0; - if (zp->z_type == z_master) - sysnotify_slaves(dname, zname, class, type, - zp - zones, &nns, &na); + sysnotify_slaves(dname, zname, class, type, zp - zones, &nns, &na); /* * Handle any global or zone-specific also-notify clauses @@ -239,8 +284,8 @@ sysnotify(const char *dname, ns_class class, ns_type type) { if (nns != 0 || na != 0) ns_info(ns_log_notify, - "Sent NOTIFY for \"%s %s %s\" (%s); %d NS, %d A", - dname, p_class(class), p_type(type), zname, nns, na); + "Sent NOTIFY for \"%s %s %s %u\" (%s); %d NS, %d A", + dname, p_class(class), p_type(type), zserial, zname, nns, na); } static void @@ -328,7 +373,7 @@ sysnotify_ns(const char *dname, const char *aname, nss[nsc++] = ina; } /*next A*/ if (nsc == 0) { - if (!is_us) { + if (!is_us && !NS_OPTION_P(OPTION_NOFETCHGLUE)) { struct qinfo *qp; qp = sysquery(aname, class, ns_t_a, 0, 0, ns_port, @@ -349,7 +394,7 @@ free_notify(struct notify *ni) { INSIST(!LINKED(ni, link)); zp = find_auth_zone(ni->name, ni->class); - if (zp != NULL) { + if (zp != NULL && ns_samename(ni->name, zp->z_origin) == 1) { INSIST((zp->z_flags & Z_NOTIFY) != 0); zp->z_flags &= ~Z_NOTIFY; } diff --git a/contrib/bind/bin/named/ns_parser.y b/contrib/bind/bin/named/ns_parser.y index b381083..c987e2b 100644 --- a/contrib/bind/bin/named/ns_parser.y +++ b/contrib/bind/bin/named/ns_parser.y @@ -1,10 +1,10 @@ %{ #if !defined(lint) && !defined(SABER) -static char rcsid[] = "$Id: ns_parser.y,v 8.51 1999/11/12 05:29:18 vixie Exp $"; +static char rcsid[] = "$Id: ns_parser.y,v 8.55 2000/04/23 02:18:59 vixie Exp $"; #endif /* not lint */ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -376,8 +376,6 @@ option: /* Empty */ | T_HAS_OLD_CLIENTS yea_or_nay { set_global_boolean_option(current_options, - OPTION_MAINTAIN_IXFR_BASE, $2); - set_global_boolean_option(current_options, OPTION_NORFC2308_TYPE1, $2); set_global_boolean_option(current_options, OPTION_NONAUTH_NXDOMAIN, !$2); @@ -589,7 +587,9 @@ control: /* Empty */ } | T_UNIX L_QSTRING T_PERM L_NUMBER T_OWNER L_NUMBER T_GROUP L_NUMBER { +#ifndef NO_SOCKADDR_UN ns_ctl_add(¤t_controls, ns_ctl_new_unix($2, $4, $6, $8)); +#endif } | error ; @@ -960,6 +960,8 @@ logging_opt: T_CATEGORY category chan_name, NULL, chan_versions, chan_max_size); + log_set_file_owner(current_channel, + user_id, group_id); freestr(chan_name); chan_name = NULL; break; diff --git a/contrib/bind/bin/named/ns_parseutil.c b/contrib/bind/bin/named/ns_parseutil.c index 60b189a..4a26337 100644 --- a/contrib/bind/bin/named/ns_parseutil.c +++ b/contrib/bind/bin/named/ns_parseutil.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/ns_parseutil.h b/contrib/bind/bin/named/ns_parseutil.h index 78356f8..77fc878 100644 --- a/contrib/bind/bin/named/ns_parseutil.h +++ b/contrib/bind/bin/named/ns_parseutil.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/ns_req.c b/contrib/bind/bin/named/ns_req.c index d7ee0b5..5e1459c 100644 --- a/contrib/bind/bin/named/ns_req.c +++ b/contrib/bind/bin/named/ns_req.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)ns_req.c 4.47 (Berkeley) 7/1/91"; -static const char rcsid[] = "$Id: ns_req.c,v 8.104 1999/10/15 19:49:04 vixie Exp $"; +static const char rcsid[] = "$Id: ns_req.c,v 8.113 2000/04/21 06:54:11 vixie Exp $"; #endif /* not lint */ /* @@ -82,7 +82,7 @@ static const char rcsid[] = "$Id: ns_req.c,v 8.104 1999/10/15 19:49:04 vixie Exp */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -138,6 +138,7 @@ struct addinfo { u_int16_t a_class; /* class for data */ }; + #ifndef BIND_UPDATE enum req_action { Finish, Refuse, Return }; #endif @@ -184,7 +185,7 @@ ns_req(u_char *msg, int msglen, int buflen, struct qstream *qsp, #ifdef DEBUG if (debug > 3) { ns_debug(ns_log_packet, 3, "ns_req(from %s)", sin_ntoa(from)); - res_pquery(&res, msg, msglen, log_get_stream(packet_channel)); + fp_nquery(msg, msglen, log_get_stream(packet_channel)); } #endif msglen_orig = msglen; @@ -197,7 +198,13 @@ ns_req(u_char *msg, int msglen, int buflen, struct qstream *qsp, char buf[MAXDNAME]; has_tsig = 1; - ns_name_ntop(tsigstart, buf, sizeof(buf)); + n = dn_expand(msg, msg + msglen, tsigstart, buf, sizeof(buf)); + if (n < 0) { + ns_debug(ns_log_default, 1, + "ns_req: bad TSIG key name", + buf); + key = NULL; + } key = find_key(buf, NULL); if (key == NULL) { error = ns_r_badkey; @@ -515,7 +522,7 @@ req_notify(HEADER *hp, u_char **cpp, u_char *eom, u_char *msg, goto refuse; } if (findZonePri(zp, from) == -1) { - ns_info(ns_log_notify, + ns_debug(ns_log_notify, 1, "NOTIFY(SOA) from non-master server (zone %s), from %s", zp->z_origin, sin_ntoa(from)); goto refuse; @@ -556,6 +563,7 @@ req_notify(HEADER *hp, u_char **cpp, u_char *eom, u_char *msg, } #endif /*BIND_NOTIFY*/ + static enum req_action req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, int *buflenp, int *msglenp, u_char *msg, int dfd, int *ra, @@ -579,6 +587,9 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, struct databuf *dp; DST_KEY *in_key = (in_tsig != NULL) ? in_tsig->key : NULL; + + + nameserIncr(from.sin_addr, nssRcvdQ); nsp[0] = NULL; @@ -633,7 +644,7 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, } if (((ntohs(hp->nscount) != 0) && (type != ns_t_ixfr)) || - ((ntohs(hp->nscount) != 1) && (type == ns_t_ixfr))) + ((ntohs(hp->nscount) != 1) && (type == ns_t_ixfr))) { ns_debug(ns_log_default, 1, "FORMERR Query nscount wrong"); hp->rcode = ns_r_formerr; @@ -647,6 +658,8 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, * Process query. */ if (type == ns_t_ixfr) { + ns_info(ns_log_security, "Request %s from %s", + p_type(type), sin_ntoa(from)); hp->nscount = htons(0); hp->rd = 0; /* Force IXFR queries to be non recursive. */ n = dn_expand(msg, eom, *cpp, dnbuf2, sizeof dnbuf2); @@ -741,6 +754,11 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, np == NULL ? "missed" : "found", dname, fname, cname); + + ns_debug(ns_log_default, 1, "req: %s '%s' as '%s' (cname=%d)", + np == NULL ? "missed" : "found", + dname, fname, cname); + #ifdef YPKLUDGE /* Some braindamaged resolver software will not recognize internet addresses in dot notation and @@ -803,17 +821,21 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, if (SEQ_GT(serial_ixfr, zp->z_serial)) ixfr_found = 0; else { - ixfr_error = ixfr_have_log(zp, serial_ixfr, zp->z_serial); - if (ixfr_error < 0) { - ns_debug(ns_log_default, - 1, "ixfr_have_log(%d %d) failed %d", - serial_ixfr, zp->z_serial, ixfr_error); - ixfr_found = 0; - /* Refuse IXFR and send AXFR */ - type = ns_t_axfr; - } else - ixfr_found = 1; - } + ixfr_error = ixfr_have_log(zp, serial_ixfr, + zp->z_serial); + if (ixfr_error < 0) { + ns_info(ns_log_security, "No %s log from %d for \"%s\"", + p_type(type), serial_ixfr, *dname ? dname : "."); + ns_debug(ns_log_default, + 1, "ixfr_have_log(%d %d) failed %d", + serial_ixfr, zp->z_serial, ixfr_error); + ixfr_found = 0; /* Refuse IXFR and send AXFR */ + } else if (ixfr_error == 1) { + ixfr_found = 1; + } + } + ns_debug(ns_log_default, 1, "IXFR log lowest serial: %d", + zp->z_serial_ixfr_start); } /* * If recursion is turned on, we need to check recursion ACL @@ -889,8 +911,9 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, } } ns_notice(ns_log_security, - "unapproved query from %s for \"%s\"", + "denied query from %s for \"%s\"", sin_ntoa(from), *dname ? dname : "."); + nameserIncr(from.sin_addr, nssRcvdUQ); return (Refuse); } } else { @@ -908,9 +931,10 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, in_key)) { ns_notice(ns_log_security, - "unapproved %s from %s for \"%s\" (acl)", + "denied %s from %s for \"%s\" (acl)", p_type(type), sin_ntoa(from), *dname ? dname : "."); + nameserIncr(from.sin_addr, nssRcvdUXFR); return (Refuse); } @@ -918,9 +942,10 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, if (zp->z_type != z_master && zp->z_type != z_slave) { ns_notice(ns_log_security, - "unapproved %s from %s for \"%s\" (not master/slave)", + "denied %s from %s for \"%s\" (not master/slave)", p_type(type), sin_ntoa(from), *dname ? dname : "."); + nameserIncr(from.sin_addr, nssRcvdUXFR); return (Refuse); } @@ -928,9 +953,10 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, if ((zp->z_flags & Z_AUTH) == 0) { ns_notice(ns_log_security, - "unapproved %s from %s for \"%s\" (not authoritative)", + "denied %s from %s for \"%s\" (not authoritative)", p_type(type), sin_ntoa(from), *dname ? dname : "."); + nameserIncr(from.sin_addr, nssRcvdUXFR); return (Refuse); } @@ -938,14 +964,20 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, if (ns_samename(zp->z_origin, dname) != 1) { ns_notice(ns_log_security, - "unapproved %s from %s for \"%s\" (not zone top)", + "denied %s from %s for \"%s\" (not zone top)", p_type(type), sin_ntoa(from), *dname ? dname : "."); + nameserIncr(from.sin_addr, nssRcvdUXFR); return (Refuse); } - ns_info(ns_log_security, "approved %s from %s for \"%s\"", - p_type(type), sin_ntoa(from), *dname ? dname : "."); + if (type == ns_t_ixfr) { + ns_info(ns_log_security, "approved %s from %s for \"%s\"", + (ixfr_found) ? p_type(type) : "IXFR/AXFR", + sin_ntoa(from), *dname ? dname : "."); + } else + ns_info(ns_log_security, "approved %s from %s for \"%s\"", + p_type(type), sin_ntoa(from), *dname ? dname : "."); } /* @@ -1102,8 +1134,9 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, if (type == ns_t_ixfr) { hp->aa = 1; if ((SEQ_GT(serial_ixfr, zp->z_serial) || - serial_ixfr == zp->z_serial)) + serial_ixfr == zp->z_serial)) { return (Finish); + } } /* @@ -1204,8 +1237,9 @@ req_query(HEADER *hp, u_char **cpp, u_char *eom, struct qstream *qsp, if (!founddata && hp->rd && recursion_blocked_by_acl) { ns_notice(ns_log_security, - "unapproved recursive query from %s for %s", + "denied recursion for query from %s for %s", sin_ntoa(from), *dname ? dname : "."); + nameserIncr(from.sin_addr, nssRcvdURQ); } /* @@ -1591,11 +1625,11 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, } #endif if ((n = dn_comp(name, buf, buflen, comp_ptrs, edp)) < 0) - return (-1); + goto cleanup; cp = buf + n; buflen -= n; if (buflen < 0) - return (-1); + goto cleanup; PUTSHORT((u_int16_t)type, cp); PUTSHORT((u_int16_t)dp->d_class, cp); PUTLONG(ttl, cp); @@ -1608,7 +1642,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, case T_PTR: n = dn_comp((char *)dp->d_data, cp, buflen, comp_ptrs, edp); if (n < 0) - return (-1); + goto cleanup; PUTSHORT((u_int16_t)n, sp); cp += n; break; @@ -1618,7 +1652,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, /* Store domain name in answer */ n = dn_comp((char *)dp->d_data, cp, buflen, comp_ptrs, edp); if (n < 0) - return (-1); + goto cleanup; PUTSHORT((u_int16_t)n, sp); cp += n; if (doadd) { @@ -1634,15 +1668,15 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, cp1 = dp->d_data; n = dn_comp((char *)cp1, cp, buflen, comp_ptrs, edp); if (n < 0) - return (-1); + goto cleanup; cp += n; buflen -= type == T_SOA ? n + 5 * INT32SZ : n; if (buflen < 0) - return (-1); + goto cleanup; cp1 += strlen((char *)cp1) + 1; n = dn_comp((char *)cp1, cp, buflen, comp_ptrs, edp); if (n < 0) - return (-1); + goto cleanup; cp += n; if (type == T_SOA) { cp1 += strlen((char *)cp1) + 1; @@ -1670,7 +1704,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, /* copy order */ buflen -= INT16SZ; if (buflen < 0) - return (-1); + goto cleanup; memcpy(cp, cp1, INT16SZ); cp += INT16SZ; cp1 += INT16SZ; @@ -1680,7 +1714,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, /* copy preference */ buflen -= INT16SZ; if (buflen < 0) - return (-1); + goto cleanup; memcpy(cp, cp1, INT16SZ); cp += INT16SZ; cp1 += INT16SZ; @@ -1692,7 +1726,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, ns_debug(ns_log_default, 1, "size of n at flags = %d", n); buflen -= n + 1; if (buflen < 0) - return (-1); + goto cleanup; *cp++ = n; memcpy(cp, cp1, n); cp += n; @@ -1704,7 +1738,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, n = *cp1++; buflen -= n + 1; if (buflen < 0) - return (-1); + goto cleanup; *cp++ = n; memcpy(cp, cp1, n); cp += n; @@ -1716,7 +1750,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, n = *cp1++; buflen -= n + 1; if (buflen < 0) - return (-1); + goto cleanup; *cp++ = n; memcpy(cp, cp1, n); cp += n; @@ -1729,7 +1763,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, n = dn_comp((char *)cp1, cp, buflen, dnptrs, edp); ns_debug(ns_log_default, 1, "dn_comp's n = %u", n); if (n < 0) - return (-1); + goto cleanup; cp += n; /* save data length */ @@ -1747,7 +1781,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, cp1 = dp->d_data; if ((buflen -= INT16SZ) < 0) - return (-1); + goto cleanup; /* copy preference */ memcpy(cp, cp1, INT16SZ); @@ -1757,7 +1791,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, if (type == T_SRV) { buflen -= INT16SZ*2; if (buflen < 0) - return (-1); + goto cleanup; memcpy(cp, cp1, INT16SZ*2); cp += INT16SZ*2; cp1 += INT16SZ*2; @@ -1767,7 +1801,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, (type == ns_t_mx) ? comp_ptrs : NULL, (type == ns_t_mx) ? edp : NULL); if (n < 0) - return (-1); + goto cleanup; cp += n; /* save data length */ @@ -1781,7 +1815,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, cp1 = dp->d_data; if ((buflen -= INT16SZ) < 0) - return (-1); + goto cleanup; /* copy preference */ memcpy(cp, cp1, INT16SZ); @@ -1790,13 +1824,13 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, n = dn_comp((char *)cp1, cp, buflen, comp_ptrs, edp); if (n < 0) - return (-1); + goto cleanup; cp += n; buflen -= n; cp1 += strlen((char *)cp1) + 1; n = dn_comp((char *)cp1, cp, buflen, comp_ptrs, edp); if (n < 0) - return (-1); + goto cleanup; cp += n; /* save data length */ @@ -1811,7 +1845,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, /* first just copy over the type_covered, algorithm, */ /* labels, orig ttl, two timestamps, and the footprint */ if ((dp->d_size - 18) > buflen) - return (-1); /* out of room! */ + goto cleanup; /* out of room! */ memcpy(cp, cp1, 18); cp += 18; cp1 += 18; @@ -1820,7 +1854,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, /* then the signer's name */ n = dn_comp((char *)cp1, cp, buflen, NULL, NULL); if (n < 0) - return (-1); + goto cleanup; cp += n; buflen -= n; cp1 += strlen((char*)cp1)+1; @@ -1828,20 +1862,20 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, /* finally, we copy over the variable-length signature */ n = dp->d_size - (u_int16_t)((cp1 - dp->d_data)); if (n > buflen) - return (-1); /* out of room! */ + goto cleanup; /* out of room! */ memcpy(cp, cp1, n); cp += n; - /* save data length & return */ + /* save data length & return */ n = (u_int16_t)((cp - sp) - INT16SZ); - PUTSHORT((u_int16_t)n, sp); + PUTSHORT((u_int16_t)n, sp); break; case T_NXT: cp1 = dp->d_data; n = dn_comp((char *)cp1, cp, buflen, NULL, NULL); if (n < 0) - return (-1); + goto cleanup; cp += n; buflen -=n; @@ -1850,7 +1884,7 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, /* copy nxt bit map */ n = dp->d_size - (u_int16_t)((cp1 - dp->d_data)); if (n > buflen) - return (-1); /* out of room! */ + goto cleanup; /* out of room! */ memcpy(cp, cp1, n); cp += n; buflen -= n; @@ -1864,12 +1898,18 @@ make_rr(const char *name, struct databuf *dp, u_char *buf, if ((type == T_A || type == T_AAAA) && doadd) addname(name, name, type, T_KEY, dp->d_class); if (dp->d_size > buflen) - return (-1); + goto cleanup; memcpy(cp, dp->d_data, dp->d_size); PUTSHORT((u_int16_t)dp->d_size, sp); cp += dp->d_size; } return (cp - buf); + + cleanup: + /* Rollback RR. */ + ns_name_rollback(buf, (const u_char **)comp_ptrs, + (const u_char **)edp); + return (-1); } static void @@ -1965,7 +2005,9 @@ loop: !match(dp, (int)ap->a_class, T_A) && !match(dp, C_IN, T_A) && !match(dp, (int)ap->a_class, T_AAAA) && - !match(dp, C_IN, T_AAAA)) { + !match(dp, C_IN, T_AAAA) && + !match(dp, (int)ap->a_class, ns_t_a6) && + !match(dp, C_IN, ns_t_a6)) { continue; } if (ap->a_type == T_KEY && @@ -1993,6 +2035,10 @@ loop: ns_debug(ns_log_default, 5, "addinfo: not enough room, remaining msglen = %d", save_msglen); + /* Rollback RRset. */ + ns_name_rollback(save_cp, + (const u_char **)dnptrs, + (const u_char **)dnptrs_end); cp = save_cp; msglen = save_msglen; count = save_count; diff --git a/contrib/bind/bin/named/ns_resp.c b/contrib/bind/bin/named/ns_resp.c index d20b1ef..0646618 100644 --- a/contrib/bind/bin/named/ns_resp.c +++ b/contrib/bind/bin/named/ns_resp.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)ns_resp.c 4.65 (Berkeley) 3/3/91"; -static const char rcsid[] = "$Id: ns_resp.c,v 8.133 1999/11/05 04:40:57 vixie Exp $"; +static const char rcsid[] = "$Id: ns_resp.c,v 8.143 2000/05/09 07:38:38 vixie Exp $"; #endif /* not lint */ /* @@ -82,7 +82,7 @@ static const char rcsid[] = "$Id: ns_resp.c,v 8.133 1999/11/05 04:40:57 vixie Ex */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -148,7 +148,8 @@ static const char skipnameFailedAnswer[] = "skipname failed in answer", outofDataAFinal[] = "out of data after final pass", badNameFound[] = "found an invalid domain name", wrongQuestion[] = "answer to wrong question", - danglingCname[] = "dangling CNAME pointer"; + danglingCname[] = "dangling CNAME pointer", + nonRecursiveForwarder[]= "non-recursive forwarder"; struct db_list { struct db_list *db_next; @@ -463,20 +464,14 @@ ns_resp(u_char *msg, int msglen, struct sockaddr_in from, struct qstream *qsp) * XXX - should put this in STATS somewhere. */ for (fwd = NS_ZFWDTAB(qp->q_fzone); fwd; fwd = fwd->next) - if (ina_equal(fwd->fwdaddr.sin_addr, from.sin_addr)) + if (ina_equal(fwd->fwddata->fwdaddr.sin_addr, from.sin_addr)) break; /* - * XXX: note bad ambiguity here. if one of our forwarders is also - * a delegated server for some domain, then we will not update - * the RTT information on any replies we get from those servers. - * Workaround: disable recursion on authoritative servers so that - * the ambiguity does not arise. - */ /* - * If we weren't using a forwarder, find the qinfo pointer and update + * find the qinfo pointer and update * the rtt and fact that we have called on this server before. */ - if (fwd == NULL) { + { struct timeval *stp; for (n = 0, qs = qp->q_addr; (u_int)n < qp->q_naddr; n++, qs++) @@ -706,13 +701,15 @@ ns_resp(u_char *msg, int msglen, struct sockaddr_in from, struct qstream *qsp) /* * Non-authoritative, no answer, no error, with referral. */ - if (hp->rcode == NOERROR && !hp->aa && ancount == 0 && aucount > 0 + if (hp->rcode == NOERROR && !hp->tc && !hp->aa && + ancount == 0 && aucount > 0 #ifdef BIND_NOTIFY && hp->opcode != NS_NOTIFY_OP #endif ) { u_char *tp; - int type, class; + int type, class, dlen; + int foundns, foundsoa; #ifdef DEBUG if (debug > 0) res_pquery(&res, msg, msglen, @@ -723,23 +720,40 @@ ns_resp(u_char *msg, int msglen, struct sockaddr_in from, struct qstream *qsp) * we must be pointing at the authority section (aucount > 0). */ tp = cp; - n = dn_expand(msg, eom, tp, name, sizeof name); - if (n < 0) { - formerrmsg = expandFailedAuth; - goto formerr; - } - tp += n; - if (tp + 2 * INT16SZ > eom) { - formerrmsg = outofDataAuth; - goto formerr; - } - GETSHORT(type, tp); - GETSHORT(class, tp); - if (!ns_nameok(qp, name, class, NULL, response_trans, - ns_ownercontext(type, response_trans), - name, from.sin_addr)) { - formerrmsg = badNameFound; - goto refused; + foundns = foundsoa = 0; + for (i = 0 ; i < aucount ; i++) { + n = dn_expand(msg, eom, tp, name, sizeof name); + if (n < 0) { + formerrmsg = expandFailedAuth; + goto formerr; + } + tp += n; + if (tp + 3 * INT16SZ + INT32SZ > eom) { + formerrmsg = outofDataAuth; + goto formerr; + } + GETSHORT(type, tp); + GETSHORT(class, tp); + tp += INT32SZ; /* ttl */ + GETSHORT(dlen, tp); + if (!ns_nameok(qp, name, class, NULL, response_trans, + ns_ownercontext(type, response_trans), + name, from.sin_addr)) { + formerrmsg = badNameFound; + goto refused; + } + /* skip rest of record */ + if (tp + dlen > eom) { + formerrmsg = outofDataAuth; + goto formerr; + } + tp += dlen; + if (type == T_NS) { + strcpy(aname, name); + foundns = 1; + } + if (type == T_SOA) + foundsoa = 1; } /* @@ -751,11 +765,14 @@ ns_resp(u_char *msg, int msglen, struct sockaddr_in from, struct qstream *qsp) * classes tend to not have good strong delegation graphs). */ - if (type == T_NS && ns_samedomain(qp->q_domain, name)) { - nameserIncr(from.sin_addr, nssRcvdLDel); - mark_lame(qp, from); + if (foundns && !foundsoa && + ns_samedomain(qp->q_domain, aname)) { + if (fwd == NULL) { + nameserIncr(from.sin_addr, nssRcvdLDel); + mark_lame(qp, from); + } mark_bad(qp, from); - if (class == C_IN && + if (class == C_IN && fwd == NULL && !haveComplained(ina_ulong(from.sin_addr), nhash(qp->q_domain))) { char *learnt_from = learntFrom(qp, &from); @@ -768,6 +785,12 @@ ns_resp(u_char *msg, int msglen, struct sockaddr_in from, struct qstream *qsp) learnt_from); if (learnt_from != NULL) freestr(learnt_from); + } else if (fwd != NULL) { + if (!haveComplained(ina_ulong(from.sin_addr), + (u_long)nonRecursiveForwarder)) + ns_warning(ns_log_default, "%s: %s", + nonRecursiveForwarder, + sin_ntoa(from)); } fast_retry(qp, from); @@ -788,7 +811,7 @@ ns_resp(u_char *msg, int msglen, struct sockaddr_in from, struct qstream *qsp) /* -ve $ing non-existence of record, must handle non-authoritative * NOERRORs with c == 0. */ - if (!hp->aa && hp->rcode == NOERROR && c == 0) + if (!hp->aa && !hp->tc && hp->rcode == NOERROR && c == 0) goto return_msg; if (qp->q_flags & Q_SYSTEM) @@ -979,19 +1002,22 @@ tcp_retry: case T_SOA: if (!ns_samedomain(aname, name)) { ns_info(ns_log_resp_checks, - "bad referral (%s !< %s)", + "bad referral (%s !< %s) from %s", aname[0] ? aname : ".", - name[0] ? name : "."); + name[0] ? name : ".", + sin_ntoa(from)); db_freedata(dp); continue; - } else if (!ns_samedomain(name, + } else if (fwd == NULL && + !ns_samedomain(name, qp->q_domain)) { if (!externalcname) ns_info(ns_log_resp_checks, - "bad referral (%s !< %s)", + "bad referral (%s !< %s) from %s", name[0] ? name : ".", qp->q_domain[0] ? - qp->q_domain : "."); + qp->q_domain : ".", + sin_ntoa(from)); db_freedata(dp); continue; } @@ -1182,17 +1208,11 @@ tcp_retry: founddata = 0; dname = name; /* - * If restart==0 and ancount > 0, we should - * have some valid data because because the data in the answer - * section is owned by the query name and that passes the - * validation test by definition - * * XXX - the restart stuff doesn't work if any of the answer RRs * is not cacheable (TTL==0 or unknown RR type), since all of the * answer must pass through the cache and be re-assembled. */ - if ((forcecmsg && qp->q_cmsglen) || - ((!restart || !cname) && qp->q_cmsglen && ancount)) { + if (qp->q_cmsglen != 0) { ns_debug(ns_log_default, 1, "Cname second pass"); newmsglen = MIN(PACKETSZ, qp->q_cmsglen); memcpy(newmsg, qp->q_cmsg, newmsglen); @@ -1461,8 +1481,7 @@ tcp_retry: } else hp = (HEADER *) qp->q_msg; hp->id = qp->q_nsid = htons(nsid_next()); - if (qp->q_addr[0].forwarder) - hp->rd = 1; + hp->rd = (qp->q_addr[0].forwarder ? 1 : 0); unsched(qp); schedretry(qp, retrytime(qp)); nsa = Q_NEXTADDR(qp, 0); @@ -1560,6 +1579,11 @@ tcp_retry: return_msg: nameserIncr(from.sin_addr, nssRcvdFwdR); nameserIncr(qp->q_from.sin_addr, nssSentFwdR); + nameserIncr(qp->q_from.sin_addr, nssSentAns); + if (!hp->aa) + nameserIncr(qp->q_from.sin_addr, nssSentNaAns); + if (hp->rcode == NXDOMAIN) + nameserIncr(qp->q_from.sin_addr, nssSentNXD); /* The "standard" return code */ hp->qr = 1; hp->id = qp->q_id; @@ -2093,6 +2117,7 @@ rrextract(u_char *msg, int msglen, u_char *rrp, struct databuf **dpp, } memcpy(cp1, cp, n2); cp += n2; + cp1 += n2; /* compute size of data */ n = cp1 - (u_char *)data; @@ -2279,7 +2304,7 @@ sysquery(const char *dname, int class, int type, nsp[0] = NULL; ns_debug(ns_log_default, 3, "sysquery(%s, %d, %d, %#x, %d, %d)", dname, class, type, nss, nsc, ntohs(port)); - qp = qnew(dname, class, type); + qp = qnew(dname, class, type, (nss != NULL && nsc != 0) ? 0 : 1); if (nss != NULL && nsc != 0) np = NULL; @@ -3106,7 +3131,10 @@ finddata(struct namebuf *np, int class, int type, case cyclic_order: /* first we do the non-SIG records */ - choice = ((u_int)rand()>>3) % non_sig_count; + if (non_sig_count > 0) + choice = ((u_int)rand()>>3) % non_sig_count; + else + choice = 0; for (i = 0; i < non_sig_count ; i++) { dp = found[(i + choice) % non_sig_count]; if (foundcname != 0 && dp->d_type == T_CNAME) diff --git a/contrib/bind/bin/named/ns_signal.c b/contrib/bind/bin/named/ns_signal.c index 4c7c48a..8cc715b 100644 --- a/contrib/bind/bin/named/ns_signal.c +++ b/contrib/bind/bin/named/ns_signal.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)ns_main.c 4.55 (Berkeley) 7/1/91"; -static const char rcsid[] = "$Id: ns_signal.c,v 8.11 1999/10/13 16:39:12 vixie Exp $"; +static const char rcsid[] = "$Id: ns_signal.c,v 8.12 2000/04/21 06:54:12 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: ns_signal.c,v 8.11 1999/10/13 16:39:12 vixie E */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/ns_sort.c b/contrib/bind/bin/named/ns_sort.c index 25c74eb..3b3f31e 100644 --- a/contrib/bind/bin/named/ns_sort.c +++ b/contrib/bind/bin/named/ns_sort.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)ns_sort.c 4.10 (Berkeley) 3/3/91"; -static const char rcsid[] = "$Id: ns_sort.c,v 8.5 1999/10/13 16:39:12 vixie Exp $"; +static const char rcsid[] = "$Id: ns_sort.c,v 8.6 2000/04/21 06:54:13 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: ns_sort.c,v 8.5 1999/10/13 16:39:12 vixie Exp */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/ns_stats.c b/contrib/bind/bin/named/ns_stats.c index 44552ed..f04790b 100644 --- a/contrib/bind/bin/named/ns_stats.c +++ b/contrib/bind/bin/named/ns_stats.c @@ -1,6 +1,6 @@ #if !defined(lint) && !defined(SABER) static const char sccsid[] = "@(#)ns_stats.c 4.10 (Berkeley) 6/27/90"; -static const char rcsid[] = "$Id: ns_stats.c,v 8.27 1999/10/13 16:39:12 vixie Exp $"; +static const char rcsid[] = "$Id: ns_stats.c,v 8.30 2000/04/23 02:18:59 vixie Exp $"; #endif /* not lint */ /* @@ -57,7 +57,7 @@ static const char rcsid[] = "$Id: ns_stats.c,v 8.27 1999/10/13 16:39:12 vixie Ex */ /* - * Portions Copyright (c) 1996-1999 by Internet Software Consortium. + * Portions Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -122,6 +122,7 @@ ns_stats() { server_options->stats_filename); return; } + (void) fchown(fileno(f), user_id, group_id); fprintf(f, "+++ Statistics Dump +++ (%ld) %s", (long)timenow, checked_ctime(&timenow)); @@ -144,10 +145,11 @@ ns_stats() { /* Now do the memory statistics file */ if (!(f = fopen(server_options->memstats_filename, "a"))) { - ns_notice(ns_log_statistics, "cannot open memstat file, \"%s\"", + ns_notice(ns_log_statistics, "cannot open memstat file, \"%s\"", server_options->memstats_filename); return; } + (void) fchown(fileno(f), user_id, group_id); fprintf(f, "+++ Memory Statistics Dump +++ (%ld) %s", (long)timenow, checked_ctime(&timenow)); @@ -207,6 +209,10 @@ static const char *statNames[nssLast] = { "SFErr", /* sent them a FORMERR */ "SNaAns", /* sent them a non autoritative answer */ "SNXD", /* sent them a negative response */ + "RUQ", /* sent us an unapproved query */ + "RURQ", /* sent us an unapproved recursive query */ + "RUXFR", /* sent us an unapproved AXFR or IXFR */ + "RUUpd", /* sent us an unapproved update */ }; /* diff --git a/contrib/bind/bin/named/ns_udp.c b/contrib/bind/bin/named/ns_udp.c index 95f0438..23f4377 100644 --- a/contrib/bind/bin/named/ns_udp.c +++ b/contrib/bind/bin/named/ns_udp.c @@ -1,9 +1,9 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ns_udp.c,v 8.8 1999/10/13 16:39:13 vixie Exp $"; +static const char rcsid[] = "$Id: ns_udp.c,v 8.9 2000/04/21 06:54:13 vixie Exp $"; #endif /* not lint */ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above diff --git a/contrib/bind/bin/named/ns_update.c b/contrib/bind/bin/named/ns_update.c index 4f9817f..c7d8ad3 100644 --- a/contrib/bind/bin/named/ns_update.c +++ b/contrib/bind/bin/named/ns_update.c @@ -1,9 +1,9 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ns_update.c,v 8.68 1999/11/05 04:40:58 vixie Exp $"; +static const char rcsid[] = "$Id: ns_update.c,v 8.78 2000/04/23 02:19:00 vixie Exp $"; #endif /* not lint */ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -140,30 +140,45 @@ static int rdata_expand(const u_char *, const u_char *, const u_char *, static FILE * open_transaction_log(struct zoneinfo *zp) { - FILE *fp; - - fp = fopen(zp->z_updatelog, "a+"); + FILE *fp = fopen(zp->z_updatelog, "a+"); + if (fp == NULL) { ns_error(ns_log_update, "can't open %s: %s", zp->z_updatelog, strerror(errno)); return (NULL); } + (void) fchown(fileno(fp), user_id, group_id); + if (fseek(fp, 0L, SEEK_END) != 0) { + ns_error(ns_log_update, "can't fseek(%s, 0, SEEK_END)", + zp->z_updatelog); + fclose(fp); + return (NULL); + } if (ftell(fp) == 0L) { fprintf(fp, "%s", LogSignature); + zp->z_serial_ixfr_start = get_serial(zp); } + else + zp->z_serial_ixfr_start = 0; return (fp); } static FILE * open_ixfr_log(struct zoneinfo *zp) { - FILE *fp; - - fp = fopen(zp->z_ixfr_base, "a+"); + FILE *fp = fopen(zp->z_ixfr_base, "a+"); + if (fp == NULL) { ns_error(ns_log_update, "can't open %s: %s", zp->z_ixfr_base, strerror(errno)); return (NULL); } + (void) fchown(fileno(fp), user_id, group_id); + if (fseek(fp, 0L, SEEK_END) != 0) { + ns_error(ns_log_update, "can't fseek(%s, 0, SEEK_END)", + zp->z_ixfr_base); + fclose(fp); + return (NULL); + } if (ftell(fp) == 0L) { fprintf(fp, "%s", LogSignature); } @@ -425,16 +440,10 @@ schedule_soa_update(struct zoneinfo *zp, int numupdated) { */ zp->z_updatecnt += numupdated; if (zp->z_updatecnt >= zp->z_deferupdcnt) { - if (incr_serial(zp) < 0) { - ns_error(ns_log_update, - "error updating serial number for %s from %d", - zp->z_origin, zp->z_serial); - } else - return (0); - /* - * Note we continue scheduling if for some reason - * incr_serial fails. - */ + if (zp->z_soaincrtime > tt.tv_sec) { + zp->z_soaincrtime = tt.tv_sec; + return (1); + } } if (zp->z_soaincrintvl > 0) { @@ -655,8 +664,6 @@ process_prereq(ns_updrec *ur, int *rcodep, u_int16_t zclass) { *rcodep = FORMERR; return (0); } - htp = hashtab; - np = nlookup(dname, &htp, &fname, 0); if (np == NULL || fname != dname) { *rcodep = NXRRSET; return (0); @@ -880,6 +887,12 @@ prescan_update(ns_updrec *ur, int *rcodep, u_int16_t zclass) { *rcodep = FORMERR; return (0); } + if (ttl > MAXIMUM_TTL) { + ns_debug(ns_log_update, 1, + "prescan_update: invalid ttl (%u)", ttl); + *rcodep = FORMERR; + return (0); + } } else if (class == C_ANY) { if (ttl != 0 || rdp->d_size || (!ns_t_rr_p(type) && type != T_ANY)) @@ -1189,8 +1202,9 @@ req_update_private(HEADER *hp, u_char *cp, u_char *eom, u_char *msg, */ if (!ip_addr_or_key_allowed(zp->z_update_acl, from.sin_addr, in_key)) { - ns_notice(ns_log_security, "unapproved update from %s for %s", + ns_notice(ns_log_security, "denied update from %s for %s", sin_ntoa(from), *dname ? dname : "."); + nameserIncr(from.sin_addr, nssRcvdUUpd); return (Refuse); } @@ -1210,10 +1224,11 @@ req_update_private(HEADER *hp, u_char *cp, u_char *eom, u_char *msg, if (zp->z_type == Z_SECONDARY) { /* * XXX The code below is broken. - * Until fixed, we just refuse. + * Until fixed, we just return NOTIMPL. */ #if 1 - return (Refuse); + hp->rcode = ns_r_notimpl; + return (Finish); #else /* We are a slave for this zone, forward it to the master. */ for (cnt = 0; cnt < zp->z_addrcnt; cnt++) @@ -1236,12 +1251,12 @@ req_update_private(HEADER *hp, u_char *cp, u_char *eom, u_char *msg, eom -= tsig_len; free_nsp(nsp); switch (n) { - case FW_OK: - case FW_DUP: + case FW_OK: + case FW_DUP: return (Return); - case FW_NOSERVER: + case FW_NOSERVER: /* should not happen */ - case FW_SERVFAIL: + case FW_SERVFAIL: hp->rcode = SERVFAIL; return (Finish); } @@ -1324,7 +1339,7 @@ req_update_private(HEADER *hp, u_char *cp, u_char *eom, u_char *msg, rrecp->r_dp = dp; /* Append the current record to the end of list of records. */ APPEND(curupd, rrecp, r_link); - if (cp > eom) { + if (cp > eom) { ns_info(ns_log_update, "Malformed response from %s (overrun)", inet_ntoa(from.sin_addr)); @@ -2635,21 +2650,21 @@ merge_logs(struct zoneinfo *zp, char *logname) { } } else { /* section == S_UPDATE */ if (opcode == DELETE) { - ttl = 0; + ttl = 0; if (n == 0) { class = C_ANY; if (type == -1) type = T_ANY; - /* WTF? C_NONE or C_ANY _must_ be the case if - * we really are to delete this. If - * C_NONE is used, according to process_updates(), - * the class is gotten from the zone's class. - * This still isn't perfect, but it will at least - * work. - * - * Question: What is so special about the class - * of the update while we are deleting?? - */ + /* WTF? C_NONE or C_ANY _must_ be the case if + * we really are to delete this. If + * C_NONE is used, according to process_updates(), + * the class is gotten from the zone's class. + * This still isn't perfect, but it will at least + * work. + * + * Question: What is so special about the class + * of the update while we are deleting?? + */ } else /* if (zp->z_xferpid != XFER_ISIXFR) */ { class = C_NONE; } @@ -2794,22 +2809,22 @@ zonedump(struct zoneinfo *zp, int mode) { } if (mode == ISIXFR) { - if (movefile(tmp_name, zp->z_ixfr_tmp) < 0) { - ns_error(ns_log_update, "movefile(%s,%s) failed: %s :2", - tmp_name, zp->z_ixfr_tmp, strerror(errno)); - return (-1); - } + if (movefile(tmp_name, zp->z_ixfr_tmp) < 0) { + ns_error(ns_log_update, "movefile(%s,%s) failed: %s :2", + tmp_name, zp->z_ixfr_tmp, strerror(errno)); + return (-1); + } if (chmod(zp->z_source, 0644) < 0) ns_error(ns_log_update, "chmod(%s,%o) failed, pressing on: %s", zp->z_source, st.st_mode, strerror(errno)); - if (movefile(zp->z_ixfr_tmp, zp->z_source) < 0) { - ns_error(ns_log_update, "movefile(%s,%s) failed: %s :3", - zp->z_ixfr_tmp, zp->z_source, - strerror(errno)); - return (-1); - } + if (movefile(zp->z_ixfr_tmp, zp->z_source) < 0) { + ns_error(ns_log_update, "movefile(%s,%s) failed: %s :3", + zp->z_ixfr_tmp, zp->z_source, + strerror(errno)); + return (-1); + } st.st_mode &= ~WRITEABLE_MASK; if (chmod(zp->z_source, st.st_mode) < 0) ns_error(ns_log_update, @@ -2830,9 +2845,9 @@ zonedump(struct zoneinfo *zp, int mode) { } } else { if (movefile(tmp_name, zp->z_source) < 0) { - ns_error(ns_log_update, "movefile(%s,%s) failed: % s :6", tmp_name, zp->z_source, strerror(errno)); - return (-1); - } + ns_error(ns_log_update, "movefile(%s,%s) failed: % s :6", tmp_name, zp->z_source, strerror(errno)); + return (-1); + } } } else ns_debug(ns_log_update, 1, "zonedump: no zone to dump"); @@ -2844,15 +2859,15 @@ zonedump(struct zoneinfo *zp, int mode) { struct databuf * findzonesoa(struct zoneinfo *zp) { - struct hashbuf *htp; - struct namebuf *np; - struct databuf *dp; - const char *fname; + struct hashbuf *htp; + struct namebuf *np; + struct databuf *dp; + const char *fname; htp = hashtab; - np = nlookup(zp->z_origin, &htp, &fname, 0); - if (np == NULL || fname != zp->z_origin) - return (NULL); + np = nlookup(zp->z_origin, &htp, &fname, 0); + if (np == NULL || fname != zp->z_origin) + return (NULL); foreach_rr(dp, np, T_SOA, zp->z_class, zp - zones) return (dp); return (NULL); @@ -2933,7 +2948,7 @@ incr_serial(struct zoneinfo *zp) { unsigned char *cp; old_serial = get_serial(zp); - serial = old_serial + 1; + serial = old_serial + 1; if (serial == 0) serial = 1; set_serial(zp, serial); @@ -2991,7 +3006,7 @@ incr_serial(struct zoneinfo *zp) { void dynamic_about_to_exit(void) { - struct zoneinfo *zp; + struct zoneinfo *zp; ns_debug(ns_log_update, 1, "shutting down; dumping zones that need it"); diff --git a/contrib/bind/bin/named/ns_xfr.c b/contrib/bind/bin/named/ns_xfr.c index e25a536..f5cbdfa 100644 --- a/contrib/bind/bin/named/ns_xfr.c +++ b/contrib/bind/bin/named/ns_xfr.c @@ -1,9 +1,9 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ns_xfr.c,v 8.55 1999/10/13 16:39:13 vixie Exp $"; +static const char rcsid[] = "$Id: ns_xfr.c,v 8.62 2000/04/24 05:20:51 vixie Exp $"; #endif /* not lint */ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -79,7 +79,7 @@ ns_xfr(struct qstream *qsp, struct namebuf *znp, #ifdef SO_SNDLOWAT static const int sndlowat = XFER_BUFSIZE; #endif - ns_updrec *changes; + ns_deltalist *changes; switch (type) { case ns_t_axfr: /*FALLTHROUGH*/ @@ -123,6 +123,8 @@ ns_xfr(struct qstream *qsp, struct namebuf *znp, qsp->xfr.top.axfr = znp; qsp->xfr.zone = zone; qsp->xfr.class = class; + if (qsp->flags & STREAM_AXFRIXFR) + type = ns_t_axfr; qsp->xfr.type = type; qsp->xfr.id = id; qsp->xfr.opcode = opcode; @@ -186,25 +188,32 @@ ns_xfr(struct qstream *qsp, struct namebuf *znp, if (type == ns_t_ixfr) { changes = ixfr_get_change_list(&zones[zone], serial_ixfr, zones[zone].z_serial); - if (changes != NULL) - { + ixfr_log_maint(&zones[zone], 1); + if (changes != NULL) { qsp->xfr.serial = serial_ixfr; qsp->xfr.top.ixfr = changes; } - else - type = ns_t_axfr; - } + else { + qsp->xfr.top.ixfr = NULL; + goto abort; + } + } else { if (sx_pushlev(qsp, znp) < 0) { abort: (void) shutdown(qsp->s_rfd, 2); sq_remove(qsp); return; } - if (type != ns_t_ixfr) + } + if (type != ns_t_ixfr) { + ns_debug(ns_log_default, 3, "sq_writeh sx_sendsoa (%s)", + zones[zone].z_origin); (void) sq_writeh(qsp, sx_sendsoa); - else + } else { + ns_debug(ns_log_default, 3, "sq_writeh sx_send_ixfr (%s)", + zones[zone].z_origin); (void) sq_writeh(qsp, sx_send_ixfr); - + } } /* @@ -217,6 +226,8 @@ ns_stopxfrs(struct zoneinfo *zp) { struct qstream *this, *next; u_int zone = (u_int)(zp - zones); + ns_debug(ns_log_default, 3, "ns_stopxfrs (%s)", zp->z_origin); + for (this = streamq; this; this = next) { next = this->s_next; if (this->xfr.zone == zone) { @@ -234,19 +245,37 @@ ns_stopxfrs(struct zoneinfo *zp) { */ void ns_freexfr(struct qstream *qsp) { + ns_delta *dp; + ns_updrec *rp; + if (qsp->xfr.msg != NULL) { memput(qsp->xfr.msg, XFER_BUFSIZE); qsp->xfr.msg = NULL; } + if (qsp->xfr.type == ns_t_ixfr && qsp->xfr.top.ixfr != NULL) { + while ((dp = HEAD(*qsp->xfr.top.ixfr)) != NULL) { + UNLINK(*qsp->xfr.top.ixfr, dp, d_link); + while ((rp = HEAD(dp->d_changes)) != NULL) { + UNLINK(dp->d_changes, rp, r_link); + if (rp->r_dp != NULL) + db_freedata(rp->r_dp); + rp->r_dp = NULL; + res_freeupdrec(rp); + } + memput(dp, sizeof *dp); + } + memput(qsp->xfr.top.ixfr, sizeof *qsp->xfr.top.ixfr); + qsp->xfr.top.ixfr = NULL; + } while (qsp->xfr.lev) qsp->xfr.lev = sx_freelev(qsp->xfr.lev); zones[qsp->xfr.zone].z_numxfrs--; - qsp->flags &= ~STREAM_AXFR; + qsp->flags &= ~(STREAM_AXFR | STREAM_AXFRIXFR); } /* * u_char * - * renew_msg(msg) + * sx_newmsg(msg) * init the header of a message, reset the compression pointers, and * reset the write pointer to the first byte following the header. */ @@ -315,7 +344,7 @@ sx_flush(struct qstream *qsp) { * int * sx_addrr(qsp, name, dp) * add name/dp's RR to the current assembly message. if it won't fit, - * write current message out, renew the message, and then RR should fit. + * write current message out, renew the message, and then RR *must* fit. * return: * -1 = the sx_flush() failed so we could not queue the full message. * 0 = one way or another, everything is fine. @@ -339,18 +368,20 @@ sx_addrr(struct qstream *qsp, const char *dname, struct databuf *dp) { /* * Add question to first answer. */ - if (qsp->xfr.state == s_x_firstsoa && dp->d_type == T_SOA ) { - if ((qsp->xfr.type == ns_t_ixfr) || (qsp->flags & STREAM_AXFRIXFR)) { - n = dn_comp(dname, qsp->xfr.cp, qsp->xfr.eom - qsp->xfr.cp, - qsp->xfr.ptrs, edp); - if (n > 0 && (qsp->xfr.cp + n + INT16SZ * 2) <= qsp->xfr.eom) { - qsp->xfr.cp += n; - type = (qsp->xfr.type == ns_t_zxfr) ? - ns_t_axfr : qsp->xfr.type; - PUTSHORT((u_int16_t) type, qsp->xfr.cp); - PUTSHORT((u_int16_t) qsp->xfr.class, qsp->xfr.cp); - hp->qdcount = htons(ntohs(hp->qdcount) + 1); - } + if (qsp->xfr.state == s_x_firstsoa && dp->d_type == T_SOA) { + n = dn_comp(dname, qsp->xfr.cp, qsp->xfr.eom - qsp->xfr.cp, + qsp->xfr.ptrs, edp); + if (n > 0 && (qsp->xfr.cp + n + INT16SZ * 2) <= qsp->xfr.eom) { + qsp->xfr.cp += n; + if (qsp->xfr.type == ns_t_zxfr) + type = ns_t_axfr; + else if ((qsp->flags & STREAM_AXFRIXFR) != 0) + type = ns_t_ixfr; + else + type = qsp->xfr.type; + PUTSHORT((u_int16_t) type, qsp->xfr.cp); + PUTSHORT((u_int16_t) qsp->xfr.class, qsp->xfr.cp); + hp->qdcount = htons(ntohs(hp->qdcount) + 1); } } @@ -416,11 +447,9 @@ sx_soarr(struct qstream *qsp) { /* * int * sx_nsrrs(qsp) - * add the NS RR's at the current level's current np, - * to the assembly message - * This function also adds the SIG(NS), KEY, SIG(KEY), NXT, SIG(NXT) - * the reason for this these records are part of the delegation. - * + * add the NS RR's at the current level's current np to the assembly msg. + * This function also adds the SIG(NS), KEY, SIG(KEY), NXT, SIG(NXT), + * since these records are also part of the delegation (see DNSSEC). * return: * >1 = number of NS RRs added, note that there may be more * 0 = success, there are no more NS RRs at this level @@ -438,15 +467,13 @@ sx_nsrrs(struct qstream *qsp) { struct namebuf *gnp, *tnp, *top; struct hashbuf *htp; const char *fname; - int rrcount, class; + int class; class = qsp->xfr.class; top = qsp->xfr.top.axfr; - rrcount = 0; for ((void)NULL; (dp = qsp->xfr.lev->dp) != NULL; qsp->xfr.lev->dp = db_next(dp)) { - /* XYZZY foreach_rr? */ if (dp->d_class != class && class != C_ANY) continue; if (dp->d_rcode) @@ -475,7 +502,9 @@ sx_nsrrs(struct qstream *qsp) { } if (dp->d_type != T_NS) /* no glue processing */ continue; - rrcount++; /* only count NS records */ + /* Remember we have found a zone cut */ + if (qsp->xfr.top.axfr != qsp->xfr.lev->np) + qsp->xfr.lev->flags |= SXL_ZONECUT; } /* @@ -528,9 +557,17 @@ sx_nsrrs(struct qstream *qsp) { */ return (-1); } + foreach_rr(gdp, gnp, ns_t_a6, class, DB_Z_CACHE) + if (sx_addrr(qsp, fname, gdp) < 0) { + /* + * Rats. We already sent the NS RR, too. + * Note that SXL_GLUING is being left on. + */ + return (-1); + } qsp->xfr.lev->flags &= ~SXL_GLUING; } - return (rrcount); + return (0); } /* @@ -565,7 +602,6 @@ sx_allrrs(struct qstream *qsp) { for ((void)NULL; (dp = qsp->xfr.lev->dp) != NULL; qsp->xfr.lev->dp = db_next(dp)) { - /* XYZZY foreach_rr? */ if (dp->d_class != class && class != C_ANY) continue; if (dp->d_rcode) @@ -605,7 +641,6 @@ sx_allrrs(struct qstream *qsp) { void sx_sendlev(struct qstream *qsp) { struct qs_x_lev *lev; - int rrcount; again: lev = qsp->xfr.lev; @@ -618,16 +653,9 @@ sx_sendlev(struct qstream *qsp) { sq_remove(qsp); return; } - rrcount = sx_nsrrs(qsp); /* If we can't pack this one in, come back later. */ - if (rrcount < 0) + if (sx_nsrrs(qsp) < 0) return; - /* - * NS RRs other than those at the - * zone top are zone cuts. - */ - if (rrcount > 0 && qsp->xfr.top.axfr != lev->np) - lev->flags |= SXL_ZONECUT; } /* No more DP's for the NS RR pass on this NP. */ if (lev->flags & SXL_ZONECUT) { diff --git a/contrib/bind/bin/named/pathtemplate.h b/contrib/bind/bin/named/pathtemplate.h index 65056b6..3011713 100644 --- a/contrib/bind/bin/named/pathtemplate.h +++ b/contrib/bind/bin/named/pathtemplate.h @@ -1,9 +1,9 @@ /* - * $Id: pathtemplate.h,v 8.4 1999/01/08 19:28:30 vixie Exp $ + * $Id: pathtemplate.h,v 8.6 2000/04/21 06:54:15 vixie Exp $ */ /* - * Copyright (c) 1996-1999 by Internet Software Consortium. + * Copyright (c) 1996-2000 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any * purpose with or without fee is hereby granted, provided that the above @@ -42,8 +42,12 @@ #endif #ifndef _PATH_NDCSOCK +#ifdef NEED_SECURE_DIRECTORY +#define _PATH_NDCSOCK "%DESTRUN%/ndc.d/ndc" +#else #define _PATH_NDCSOCK "%DESTRUN%/ndc" #endif +#endif #ifndef _PATH_STATS #define _PATH_STATS "named.stats" diff --git a/contrib/bind/bin/ndc/ndc.c b/contrib/bind/bin/ndc/ndc.c index 764d05b..7235586 100644 --- a/contrib/bind/bin/ndc/ndc.c +++ b/contrib/bind/bin/ndc/ndc.c @@ -1,5 +1,5 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ndc.c,v 1.13 1999/10/13 16:39:16 vixie Exp $"; +static const char rcsid[] = "$Id: ndc.c,v 1.14 2000/02/04 08:28:32 vixie Exp $"; #endif /* not lint */ /* @@ -47,7 +47,9 @@ static const char rcsid[] = "$Id: ndc.c,v 1.13 1999/10/13 16:39:16 vixie Exp $"; typedef union { struct sockaddr_in in; +#ifndef NO_SOCKADDR_UN struct sockaddr_un un; +#endif } sockaddr_t; typedef void (*closure)(void *, const char *, int); @@ -603,22 +605,29 @@ static int get_sockaddr(char *name, sockaddr_t *addr) { char *slash; +#ifndef NO_SOCKADDR_UN if (name[0] == '/') { memset(&addr->un, '\0', sizeof addr->un); addr->un.sun_family = AF_UNIX; strncpy(addr->un.sun_path, name, sizeof addr->un.sun_path - 1); addr->un.sun_path[sizeof addr->un.sun_path - 1] = '\0'; - } else if ((slash = strrchr(name, '/')) != NULL) { - *slash = '\0'; + } else +#endif + if ((slash = strrchr(name, '/')) != NULL) { + char *ibuf = malloc(slash - name + 1); + if (!ibuf) + usage("no memory for IP address (%s)", name); + memcpy(ibuf, name, slash - name); + ibuf[slash - name] = '\0'; memset(&addr->in, '\0', sizeof addr->in); - if (!inet_pton(AF_INET, name, &addr->in.sin_addr)) + if (!inet_pton(AF_INET, ibuf, &addr->in.sin_addr)) usage("bad ip address (%s)", name); if ((addr->in.sin_port = htons(atoi(slash+1))) == 0) usage("bad ip port (%s)", slash+1); addr->in.sin_family = AF_INET; - *slash = ':'; - } else { - return (0); + free (ibuf); + } else { + return (0); } return (1); } @@ -630,8 +639,10 @@ impute_addrlen(const struct sockaddr *sa) { switch (sa->sa_family) { case AF_INET: return (sizeof(struct sockaddr_in)); +#ifndef NO_SOCKADDR_UN case AF_UNIX: return (sizeof(struct sockaddr_un)); +#endif default: abort(); } diff --git a/contrib/bind/bin/nslookup/list.c b/contrib/bind/bin/nslookup/list.c index 1b7f452..db46d7f 100644 --- a/contrib/bind/bin/nslookup/list.c +++ b/contrib/bind/bin/nslookup/list.c @@ -53,7 +53,7 @@ #ifndef lint static const char sccsid[] = "@(#)list.c 5.23 (Berkeley) 3/21/91"; -static const char rcsid[] = "$Id: list.c,v 8.21 1999/10/15 19:49:08 vixie Exp $"; +static const char rcsid[] = "$Id: list.c,v 8.23 2000/03/30 23:25:34 vixie Exp $"; #endif /* not lint */ /* @@ -135,7 +135,6 @@ int ListSubr(); * * To see all types of information sorted by name, do the following: * ls -d domain.edu > file - * view file * * Results: * SUCCESS the listing was successful. @@ -422,8 +421,12 @@ ListSubr(int qtype, char *domain, char *cmd) { } name = ns_rr_name(rr); if (origin[0] == '\0' && name[0] != '\0') { - fprintf(filePtr, "$ORIGIN %s.\n", name); - strcpy(origin, name); + if (strcmp(name, ".") != 0) + strcpy(origin, name); + fprintf(filePtr, "$ORIGIN %s.\n", origin); + if (strcmp(name, ".") == 0) + strcpy(origin, name); + strcpy(name_ctx, "@"); } if (qtype == T_ANY || ns_rr_type(rr) == qtype) { if (ns_sprintrr(&handle, &rr, name_ctx, origin, @@ -496,60 +499,6 @@ ListSubr(int qtype, char *domain, char *cmd) { return (ERROR); } } - -/* - ******************************************************************************* - * - * ViewList -- - * - * A hack to view the output of the ls command in sorted - * order using more. - * - ******************************************************************************* - */ - -void -ViewList(char *string) { - char file[PATH_MAX]; - char command[PATH_MAX]; - int i, j; - char soafile[PATH_MAX]; - - /* sscanf(string, " view %s", file); */ - i = matchString(" view ", string); - if (i > 0) { - j = pickString(string + i, file, sizeof file); - if (j == 0) { - fprintf(stderr, "*** invalid file name: %s\n", string + i); - return ; - } - } - - if ( !mktemp(strcpy(soafile,"/var/tmp/nslookup_tmpXXXXXX"))) { - fprintf(stderr, "*** cannot create temp file\n"); - return ; - } - (void)sprintf(command, "sed '\ -/^$/,${\ -/@/,$d\ -}\ -/^[^ ]/{\ -h\ -s/^\\([^ ]* *\\).*/\\1/\ -x\ -}\ -1,/^$/{\ -w %s\ -d\ -}\ -/^ /{\ -G\ -s/^ *//\ -s/^\\(.*\\)\\n\\(.*\\)$/\\2\\1/\ -}' %s | sort | (cat %s -; rm %s) | %s", - soafile, file, soafile, soafile, pager); - system(command); -} /* ******************************************************************************* diff --git a/contrib/bind/bin/nslookup/nslookup.help b/contrib/bind/bin/nslookup/nslookup.help index 015bdc2..31a6634 100644 --- a/contrib/bind/bin/nslookup/nslookup.help +++ b/contrib/bind/bin/nslookup/nslookup.help @@ -1,4 +1,4 @@ -$Id: nslookup.help,v 8.4 1996/10/25 18:09:41 vixie Exp $ +$Id: nslookup.help,v 8.5 2000/03/30 23:25:35 vixie Exp $ Commands: (identifiers are shown in uppercase, [] means optional) NAME - print info about the host/domain NAME using default server @@ -30,5 +30,4 @@ ls [opt] DOMAIN [> FILE] - list addresses in DOMAIN (optional: output to FILE) -s - list well-known services -d - list all records -t TYPE - list records of the given type (e.g., A,CNAME,MX, etc.) -view FILE - sort an 'ls' output file and view it with more exit - exit the program, ^D also exits diff --git a/contrib/bind/bin/nsupdate/nsupdate.c b/contrib/bind/bin/nsupdate/nsupdate.c index a02d0ad..31496b3 100644 --- a/contrib/bind/bin/nsupdate/nsupdate.c +++ b/contrib/bind/bin/nsupdate/nsupdate.c @@ -1,5 +1,5 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: nsupdate.c,v 8.21 1999/10/19 22:22:59 cyarnell Exp $"; +static const char rcsid[] = "$Id: nsupdate.c,v 8.23 2000/02/04 07:51:04 vixie Exp $"; #endif /* not lint */ /* @@ -204,6 +204,8 @@ main(argc, argv) } } + INIT_LIST(listuprec); + if (keyfile) { #ifdef PARSE_KEYFILE if ((fp=fopen(keyfile, "r"))==NULL) { @@ -397,7 +399,7 @@ main(argc, argv) exit (1); } r_dname = dnbuf; - r_ttl = 0; + r_ttl = (r_opcode == ADD) ? -1 : 0; r_type = -1; r_class = C_IN; /* default to IN */ r_size = 0; @@ -500,7 +502,7 @@ main(argc, argv) r_size = endp - cp + 1; break; case ADD: - if (r_ttl == 0) { + if (r_ttl == -1) { fprintf (stderr, "ttl must be specified for record to be added: %s\n", buf); exit (1); diff --git a/contrib/bind/include/arpa/nameser.h b/contrib/bind/include/arpa/nameser.h index c61f8b7..3de42fd 100644 --- a/contrib/bind/include/arpa/nameser.h +++ b/contrib/bind/include/arpa/nameser.h @@ -49,7 +49,7 @@ */ /* - * $Id: nameser.h,v 8.36 1999/10/15 19:49:08 vixie Exp $ + * $Id: nameser.h,v 8.37 2000/03/30 21:16:49 vixie Exp $ */ #ifndef _ARPA_NAMESER_H_ @@ -489,6 +489,7 @@ typedef enum __ns_cert_types { #define ns_name_compress __ns_name_compress #define ns_name_uncompress __ns_name_uncompress #define ns_name_skip __ns_name_skip +#define ns_name_rollback __ns_name_rollback #define ns_sign __ns_sign #define ns_sign_tcp __ns_sign_tcp #define ns_sign_tcp_init __ns_sign_tcp_init @@ -530,6 +531,8 @@ int ns_name_uncompress __P((const u_char *, const u_char *, int ns_name_compress __P((const char *, u_char *, size_t, const u_char **, const u_char **)); int ns_name_skip __P((const u_char **, const u_char *)); +void ns_name_rollback __P((const u_char *, const u_char **, + const u_char **)); int ns_sign __P((u_char *, int *, int, int, void *, const u_char *, int, u_char *, int *, time_t)); int ns_sign_tcp __P((u_char *, int *, int, int, diff --git a/contrib/bind/include/isc/logging.h b/contrib/bind/include/isc/logging.h index 720e2a31..3d3d313 100644 --- a/contrib/bind/include/isc/logging.h +++ b/contrib/bind/include/isc/logging.h @@ -18,8 +18,10 @@ #ifndef LOGGING_H #define LOGGING_H +#include <sys/types.h> #include <stdio.h> #include <stdarg.h> +#include <unistd.h> #define log_critical (-5) #define log_error (-4) @@ -64,6 +66,7 @@ typedef struct log_channel *log_channel; #define log_category_is_active __log_category_is_active #define log_new_syslog_channel __log_new_syslog_channel #define log_new_file_channel __log_new_file_channel +#define log_set_file_owner __log_set_file_owner #define log_new_null_channel __log_new_null_channel #define log_inc_references __log_inc_references #define log_dec_references __log_dec_references @@ -89,6 +92,7 @@ log_channel log_new_syslog_channel(unsigned int, int, int); log_channel log_new_file_channel(unsigned int, int, char *, FILE *, unsigned int, unsigned long); +int log_set_file_owner(log_channel, uid_t, gid_t); log_channel log_new_null_channel(void); int log_inc_references(log_channel); int log_dec_references(log_channel); diff --git a/contrib/bind/include/resolv.h b/contrib/bind/include/resolv.h index 3065313..414fe08 100644 --- a/contrib/bind/include/resolv.h +++ b/contrib/bind/include/resolv.h @@ -50,7 +50,7 @@ /* * @(#)resolv.h 8.1 (Berkeley) 6/2/93 - * $Id: resolv.h,v 8.29 1999/10/07 08:24:14 vixie Exp $ + * $Id: resolv.h,v 8.31 2000/03/30 20:16:50 vixie Exp $ */ #ifndef _RESOLV_H_ @@ -145,6 +145,7 @@ struct res_sym { #define RES_MAXRETRANS 30 /* only for resolv.conf/RES_OPTIONS */ #define RES_MAXRETRY 5 /* only for resolv.conf/RES_OPTIONS */ #define RES_DFLRETRY 2 /* Default #/tries. */ +#define RES_MAXTIME 65535 /* Infinity, in milliseconds. */ struct __res_state { int retrans; /* retransmition time interval */ @@ -168,9 +169,17 @@ struct __res_state { res_send_qhook qhook; /* query hook */ res_send_rhook rhook; /* response hook */ int res_h_errno; /* last one set for this context */ - int _sock; /* PRIVATE: for res_send i/o */ + int _vcsock; /* PRIVATE: for res_send VC i/o */ u_int _flags; /* PRIVATE: see below */ - char pad[52]; /* On an i386 this means 512b total. */ + union { + char pad[52]; /* On an i386 this means 512b total. */ + struct { + u_int16_t nscount; + u_int16_t nstimes[MAXNS]; /* ms. */ + int nssocks[MAXNS]; + struct sockaddr_in nsaddrs[MAXNS]; + } _ext; + } _u; }; typedef struct __res_state *res_state; @@ -204,6 +213,7 @@ typedef struct __res_state *res_state; #define RES_ROTATE 0x00004000 /* rotate ns list after each query */ #define RES_NOCHECKNAME 0x00008000 /* do not check names for sanity. */ #define RES_KEEPTSIG 0x00010000 /* do not strip TSIG records */ +#define RES_BLAST 0x00020000 /* blast all recursive servers */ #define RES_DEFAULT (RES_RECURSE | RES_DEFNAMES | RES_DNSRCH) diff --git a/contrib/bind/lib/Makefile b/contrib/bind/lib/Makefile index 18fa7c8..15aa655 100644 --- a/contrib/bind/lib/Makefile +++ b/contrib/bind/lib/Makefile @@ -15,7 +15,7 @@ # $Id: Makefile,v 8.22 1999/06/08 01:42:57 vixie Exp $ -SUBDIRS = resolv irs isc bsd inet nameser dst +SUBDIRS = resolv irs isc bsd inet nameser dst cylink dnssafe # these are only appropriate for BSD 4.4 or derivatives, and are used in # development. normal builds will be done in the top level directory and diff --git a/contrib/bind/lib/dst/Makefile b/contrib/bind/lib/dst/Makefile index f99813c..28befe8 100644 --- a/contrib/bind/lib/dst/Makefile +++ b/contrib/bind/lib/dst/Makefile @@ -13,7 +13,7 @@ # ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS # SOFTWARE. -# $Id: Makefile,v 1.13 1999/03/07 09:33:47 vixie Exp $ +# $Id: Makefile,v 1.16 2000/02/29 03:38:21 vixie Exp $ # these are only appropriate for BSD 4.4 or derivatives, and are used in # development. normal builds will be done in the top level directory and @@ -50,8 +50,8 @@ OBJS= dst_api.${O} prandom.${O} rsaref_link.${O} support.${O} \ bsafe_link.${O} cylink_link.${O} hmac_link.${O} md5_dgst.${O} \ eay_dss_link.${O} -CRYPTINCL= -CRYPTFLAGS= -DHMAC_MD5 -DUSE_MD5 +CRYPTINCL= -I../cylink -I../dnssafe +CRYPTFLAGS= -DCYLINK_DSS -DHMAC_MD5 -DUSE_MD5 -DDNSSAFE all: ${LIBBIND} @@ -63,13 +63,14 @@ ${LIBBIND}: ${OBJS} ${RANLIB} ${LIBBIND} .c.${O}: - if test ! -d ${THREADED} ; then mkdir ${THREADED} ; fi + if test ! -d ${THREADED} ; then mkdir ${THREADED} ; else true ; fi ${CC} ${CPPFLAGS} ${CFLAGS} ${BOUNDS} ${REENTRANT} ${CRYPTINCL} ${CRYPTFLAGS} -c $*.c -o ${THREADED}/$*.${O} - -${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} -o a.out && \ - ${LDS} mv a.out ${THREADED}/$*.${O} + -${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} \ + -o ${THREADED}/$*.out && \ + ${LDS} mv ${THREADED}/$*.out ${THREADED}/$*.${O} ${CC} ${CPPFLAGS} ${CFLAGS} ${CRYPTINCL} ${CRYPTFLAGS} -c $*.c - -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o a.out && \ - ${LDS} mv a.out $*.${O} + -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o $*.out && \ + ${LDS} mv $*.out $*.${O} $(SRCS):: $(HDRS) @@ -80,7 +81,7 @@ clean: FRC rm -f *.${O} *.BAK *.CKP *~ rm -f prand_conf.h rm -f ${THREADED}/*.${O} - -rmdir ${THREADED} + -if test -d ${THREADED} ; then rmdir ${THREADED}; else true; fi depend: FRC mkdep -I${INCL} -I${PORTINCL} ${CPPFLAGS} ${SRCS} diff --git a/contrib/bind/lib/dst/dst_api.c b/contrib/bind/lib/dst/dst_api.c index 6dde481..f25438e 100644 --- a/contrib/bind/lib/dst/dst_api.c +++ b/contrib/bind/lib/dst/dst_api.c @@ -1,5 +1,5 @@ #ifndef LINT -static const char rcsid[] = "$Header: /proj/cvs/isc/bind/src/lib/dst/dst_api.c,v 1.13 1999/10/13 16:39:22 vixie Exp $"; +static const char rcsid[] = "$Header: /proj/cvs/isc/bind/src/lib/dst/dst_api.c,v 1.14 2000/02/28 07:51:50 vixie Exp $"; #endif /* @@ -334,7 +334,7 @@ dst_read_key(const char *in_keyname, const u_int16_t in_id, in_alg)); return (NULL); } - if ((type && (DST_PUBLIC | DST_PRIVATE)) == 0) + if ((type & (DST_PUBLIC | DST_PRIVATE)) == 0) return (NULL); if (in_keyname == NULL) { EREPORT(("dst_read_private_key(): Null key name passed in\n")); diff --git a/contrib/bind/lib/inet/Makefile b/contrib/bind/lib/inet/Makefile index 04c4c1f..b007412 100644 --- a/contrib/bind/lib/inet/Makefile +++ b/contrib/bind/lib/inet/Makefile @@ -13,7 +13,7 @@ # ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS # SOFTWARE. -# $Id: Makefile,v 8.16 1999/03/03 08:07:16 vixie Exp $ +# $Id: Makefile,v 8.19 2000/02/29 03:38:22 vixie Exp $ # these are only appropriate for BSD 4.4 or derivatives, and are used in # development. normal builds will be done in the top level directory and @@ -61,14 +61,15 @@ ${LIBBIND}: ${OBJS} ${RANLIB} ${LIBBIND} .c.${O}: - if test ! -d ${THREADED} ; then mkdir ${THREADED} ; fi + if test ! -d ${THREADED} ; then mkdir ${THREADED} ; else true ; fi ${CC} ${CPPFLAGS} ${CFLAGS} ${BOUNDS} ${REENTRANT} -c $*.c \ -o ${THREADED}/$*.${O} - -${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} -o a.out && \ - ${LDS} mv a.out ${THREADED}/$*.${O} + -${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} \ + -o ${THREADED}/$*.out && \ + ${LDS} mv ${THREADED}/$*.out ${THREADED}/$*.${O} ${CC} ${CPPFLAGS} ${CFLAGS} ${BOUNDS} -c $*.c - -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o a.out && \ - ${LDS} mv a.out $*.${O} + -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o $*.out && \ + ${LDS} mv $*.out $*.${O} distclean: clean @@ -76,7 +77,7 @@ clean: FRC rm -f .depend a.out core ${LIB} tags rm -f *.${O} *.BAK *.CKP *~ rm -f ${THREADED}/*.${O} - -rmdir ${THREADED} + -if test -d ${THREADED} ; then rmdir ${THREADED}; else true; fi depend: FRC diff --git a/contrib/bind/lib/irs/Makefile b/contrib/bind/lib/irs/Makefile index 3421b8b..2c50e62 100644 --- a/contrib/bind/lib/irs/Makefile +++ b/contrib/bind/lib/irs/Makefile @@ -13,7 +13,7 @@ # ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS # SOFTWARE. -# $Id: Makefile,v 8.16 1999/02/22 02:47:58 vixie Exp $ +# $Id: Makefile,v 8.19 2000/02/29 03:38:22 vixie Exp $ # these are only appropriate for BSD 4.4 or derivatives, and are used in # development. normal builds will be done in the top level directory and @@ -82,14 +82,15 @@ ${LIBBIND}: ${OBJS} ${RANLIB} ${LIBBIND} .c.${O}: - if test ! -d ${THREADED} ; then mkdir ${THREADED} ; fi + if test ! -d ${THREADED} ; then mkdir ${THREADED} ; else true ; fi -(${CC} ${CPPFLAGS} ${CFLAGS} ${BOUNDS} ${REENTRANT} -c $*.c \ -o ${THREADED}/$*.${O} ; \ - ${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} && \ - ${LDS} mv a.out ${THREADED}/$*.${O}) + ${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} \ + -o ${THREADED}/$*.out && \ + ${LDS} mv ${THREADED}/$*.out ${THREADED}/$*.${O}) ${CC} ${CPPFLAGS} ${CFLAGS} ${BOUNDS} -c $*.c - -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o a.out && \ - ${LDS} mv a.out $*.${O} + -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o $*.out && \ + ${LDS} mv $*.out $*.${O} distclean: clean @@ -97,7 +98,7 @@ clean: FRC rm -f .depend a.out core ${LIB} tags rm -f *.${O} *.BAK *.CKP *~ rm -f ${THREADED}/*.${O} - -rmdir ${THREADED} + -if test -d ${THREADED} ; then rmdir ${THREADED}; else true; fi depend: FRC mkdep -I${INCL} -I${PORTINCL} ${CPPFLAGS} ${SRCS} diff --git a/contrib/bind/lib/irs/dns.c b/contrib/bind/lib/irs/dns.c index 7ba7eec..66bdbf5 100644 --- a/contrib/bind/lib/irs/dns.c +++ b/contrib/bind/lib/irs/dns.c @@ -16,7 +16,7 @@ */ #if defined(LIBC_SCCS) && !defined(lint) -static const char rcsid[] = "$Id: dns.c,v 1.14 1999/01/18 07:46:47 vixie Exp $"; +static const char rcsid[] = "$Id: dns.c,v 1.15 2000/02/28 07:52:16 vixie Exp $"; #endif /* @@ -116,7 +116,7 @@ dns_res_get(struct irs_acc *this) { dns_res_set(this, res, free); } - if ((dns->res->options | RES_INIT) == 0 && + if ((dns->res->options & RES_INIT) == 0 && res_ninit(dns->res) < 0) return (NULL); diff --git a/contrib/bind/lib/irs/dns_ho.c b/contrib/bind/lib/irs/dns_ho.c index e319f96..8b2df77 100644 --- a/contrib/bind/lib/irs/dns_ho.c +++ b/contrib/bind/lib/irs/dns_ho.c @@ -52,7 +52,7 @@ /* BIND Id: gethnamaddr.c,v 8.15 1996/05/22 04:56:30 vixie Exp $ */ #if defined(LIBC_SCCS) && !defined(lint) -static const char rcsid[] = "$Id: dns_ho.c,v 1.26 1999/10/15 19:49:09 vixie Exp $"; +static const char rcsid[] = "$Id: dns_ho.c,v 1.28 2000/04/20 07:47:54 vixie Exp $"; #endif /* LIBC_SCCS and not lint */ /* Imports. */ @@ -394,7 +394,7 @@ gethostans(struct irs_ho *this, const HEADER *hp; const u_char *eom; const u_char *cp; - const char *tname; + const char *tname, **tap; char *bp, **ap, **hap; char tbuf[MAXDNAME+1]; @@ -583,9 +583,9 @@ gethostans(struct irs_ho *this, bp += nn; buflen -= nn; } - + /* Ensure alignment. */ bp += sizeof(align) - ((u_long)bp % sizeof(align)); - + /* Avoid overflows. */ if (bp + n >= &pvt->hostbuf[sizeof pvt->hostbuf]) { had_error++; continue; @@ -594,7 +594,19 @@ gethostans(struct irs_ho *this, cp += n; continue; } + /* Suppress duplicates. */ + for (tap = (const char **)pvt->h_addr_ptrs; + *tap != NULL; + tap++) + if (memcmp(*tap, cp, n) == 0) + break; + if (*tap != NULL) { + cp += n; + continue; + } + /* Store address. */ memcpy(*hap++ = bp, cp, n); + *hap = NULL; bp += n; cp += n; break; @@ -606,7 +618,6 @@ gethostans(struct irs_ho *this, } if (haveanswer) { *ap = NULL; - *hap = NULL; if (pvt->res->nsort && haveanswer > 1 && qtype == T_A) addrsort(pvt->res, pvt->h_addr_ptrs, haveanswer); diff --git a/contrib/bind/lib/irs/dns_sv.c b/contrib/bind/lib/irs/dns_sv.c index ea0ba70..e6cb2df 100644 --- a/contrib/bind/lib/irs/dns_sv.c +++ b/contrib/bind/lib/irs/dns_sv.c @@ -16,7 +16,7 @@ */ #if defined(LIBC_SCCS) && !defined(lint) -static const char rcsid[] = "$Id: dns_sv.c,v 1.17 1999/09/04 22:06:14 vixie Exp $"; +static const char rcsid[] = "$Id: dns_sv.c,v 1.19 2000/03/30 22:53:56 vixie Exp $"; #endif /* Imports */ @@ -105,8 +105,8 @@ irs_dns_sv(struct irs_acc *this) { sv->rewind = sv_rewind; sv->close = sv_close; sv->minimize = sv_minimize; - sv->res_get = sv_res_get; - sv->res_set = sv_res_set; + sv->res_get = NULL; /* sv_res_get; */ + sv->res_set = NULL; /* sv_res_set; */ return (sv); } @@ -150,7 +150,7 @@ sv_byport(struct irs_sv *this, int port, const char *proto) { char portstr[16]; char **hes_list; - sprintf(portstr, "%d", port); + sprintf(portstr, "%d", ntohs(port)); if (!(hes_list = hesiod_resolve(dns->hes_ctx, portstr, "port"))) return (NULL); @@ -193,12 +193,13 @@ parse_hes_list(struct irs_sv *this, char **hes_list, const char *proto) { p++; if (!*p) continue; - proto_len = strlen(proto); - if (strncasecmp(++p, proto, proto_len) != 0) - continue; - if (p[proto_len] && !isspace(p[proto_len])) - continue; - + if (proto) { + proto_len = strlen(proto); + if (strncasecmp(++p, proto, proto_len) != 0) + continue; + if (p[proto_len] && !isspace(p[proto_len])) + continue; + } /* OK, we've got a live one. Let's parse it for real. */ if (pvt->svbuf) free(pvt->svbuf); diff --git a/contrib/bind/lib/irs/gethostent.c b/contrib/bind/lib/irs/gethostent.c index ac66520..5d316c8 100644 --- a/contrib/bind/lib/irs/gethostent.c +++ b/contrib/bind/lib/irs/gethostent.c @@ -16,7 +16,7 @@ */ #if !defined(LINT) && !defined(CODECENTER) -static const char rcsid[] = "$Id: gethostent.c,v 1.25 1999/10/19 22:27:20 cyarnell Exp $"; +static const char rcsid[] = "$Id: gethostent.c,v 1.27 2000/04/20 07:10:33 vixie Exp $"; #endif /* Imports */ @@ -461,8 +461,32 @@ freehostent(struct hostent *he) { static int scan_interfaces(int *have_v4, int *have_v6) { - struct ifconf ifc; - struct ifreq ifreq; +#ifndef SIOCGLIFCONF +/* map new to old */ +#define SIOCGLIFCONF SIOCGIFCONF +#define lifc_len ifc_len +#define lifc_buf ifc_buf + struct ifconf lifc; +#else +#define SETFAMILYFLAGS + struct lifconf lifc; +#endif + +#ifndef SIOCGLIFADDR +/* map new to old */ +#define SIOCGLIFADDR SIOCGIFADDR +#endif + +#ifndef SIOCGLIFFLAGS +#define SIOCGLIFFLAGS SIOCGIFFLAGS +#define lifr_addr ifr_addr +#define lifr_name ifr_name +#define lifr_flags ifr_flags +#define ss_family sa_family + struct ifreq lifreq; +#else + struct lifreq lifreq; +#endif struct in_addr in4; struct in6_addr in6; char *buf = NULL, *cp, *cplim; @@ -484,27 +508,31 @@ scan_interfaces(int *have_v4, int *have_v6) { buf = memget(bufsiz); if (buf == NULL) goto err_ret; - ifc.ifc_len = bufsiz; - ifc.ifc_buf = buf; +#ifdef SETFAMILYFLAGS + lifc.lifc_family = AF_UNSPEC; + lifc.lifc_flags = 0; +#endif + lifc.lifc_len = bufsiz; + lifc.lifc_buf = buf; #ifdef IRIX_EMUL_IOCTL_SIOCGIFCONF /* * This is a fix for IRIX OS in which the call to ioctl with * the flag SIOCGIFCONF may not return an entry for all the * interfaces like most flavors of Unix. */ - if (emul_ioctl(&ifc) >= 0) + if (emul_ioctl(&lifc) >= 0) break; #else - if ((n = ioctl(s, SIOCGIFCONF, (char *)&ifc)) != -1) { + if ((n = ioctl(s, SIOCGLIFCONF, (char *)&lifc)) != -1) { /* * Some OS's just return what will fit rather * than set EINVAL if the buffer is too small * to fit all the interfaces in. If - * ifc.ifc_len is too near to the end of the + * lifc.lifc_len is too near to the end of the * buffer we will grow it just in case and * retry. */ - if (ifc.ifc_len + 2 * sizeof(ifreq) < bufsiz) + if (lifc.lifc_len + 2 * sizeof(lifreq) < bufsiz) break; } #endif @@ -519,44 +547,45 @@ scan_interfaces(int *have_v4, int *have_v6) { } /* Parse system's interface list. */ - cplim = buf + ifc.ifc_len; /* skip over if's with big ifr_addr's */ + cplim = buf + lifc.lifc_len; /* skip over if's with big ifr_addr's */ for (cp = buf; (*have_v4 == 0 || *have_v6 == 0) && cp < cplim; cp += cpsize) { - memcpy(&ifreq, cp, sizeof ifreq); + memcpy(&lifreq, cp, sizeof lifreq); #ifdef HAVE_SA_LEN #ifdef FIX_ZERO_SA_LEN - if (ifreq.ifr_addr.sa_len == 0) - ifreq.ifr_addr.sa_len = 16; + if (lifreq.lifr_addr.sa_len == 0) + lifreq.lifr_addr.sa_len = 16; #endif #ifdef HAVE_MINIMUM_IFREQ - cpsize = sizeof ifreq; - if (ifreq.ifr_addr.sa_len > sizeof (struct sockaddr)) - cpsize += (int)ifreq.ifr_addr.sa_len - + cpsize = sizeof lifreq; + if (lifreq.lifr_addr.sa_len > sizeof (struct sockaddr)) + cpsize += (int)lifreq.lifr_addr.sa_len - (int)(sizeof (struct sockaddr)); #else - cpsize = sizeof ifreq.ifr_name + ifreq.ifr_addr.sa_len; + cpsize = sizeof lifreq.lifr_name + lifreq.lifr_addr.sa_len; #endif /* HAVE_MINIMUM_IFREQ */ #elif defined SIOCGIFCONF_ADDR - cpsize = sizeof ifreq; + cpsize = sizeof lifreq; #else - cpsize = sizeof ifreq.ifr_name; + cpsize = sizeof lifreq.lifr_name; /* XXX maybe this should be a hard error? */ - if (ioctl(s, SIOCGIFADDR, (char *)&ifreq) < 0) + if (ioctl(s, SOICGLIFADDR, (char *)&lifreq) < 0) continue; #endif - switch (ifreq.ifr_addr.sa_family) { + switch (lifreq.lifr_addr.ss_family) { case AF_INET: if (*have_v4 == 0) { memcpy(&in4, &((struct sockaddr_in *) - &ifreq.ifr_addr)->sin_addr, sizeof in4); + &lifreq.lifr_addr)->sin_addr, + sizeof in4); if (in4.s_addr == INADDR_ANY) break; - n = ioctl(s, SIOCGIFFLAGS, (char *)&ifreq); + n = ioctl(s, SIOCGLIFFLAGS, (char *)&lifreq); if (n < 0) break; - if ((ifreq.ifr_flags & IFF_UP) == 0) + if ((lifreq.lifr_flags & IFF_UP) == 0) break; *have_v4 = 1; } @@ -565,13 +594,13 @@ scan_interfaces(int *have_v4, int *have_v6) { if (*have_v6 == 0) { memcpy(&in6, &((struct sockaddr_in6 *) - &ifreq.ifr_addr)->sin6_addr, sizeof in6); + &lifreq.lifr_addr)->sin6_addr, sizeof in6); if (memcmp(&in6, &in6addr_any, sizeof in6) == 0) break; - n = ioctl(s, SIOCGIFFLAGS, (char *)&ifreq); + n = ioctl(s, SIOCGLIFFLAGS, (char *)&lifreq); if (n < 0) break; - if ((ifreq.ifr_flags & IFF_UP) == 0) + if ((lifreq.lifr_flags & IFF_UP) == 0) break; *have_v6 = 1; } @@ -581,12 +610,14 @@ scan_interfaces(int *have_v4, int *have_v6) { if (buf != NULL) memput(buf, bufsiz); close(s); + /* printf("scan interface -> 4=%d 6=%d\n", *have_v4, *have_v6); */ return (0); err_ret: if (buf != NULL) memput(buf, bufsiz); if (s != -1) close(s); + /* printf("scan interface -> 4=%d 6=%d\n", *have_v4, *have_v6); */ return (-1); } diff --git a/contrib/bind/lib/irs/getnameinfo.c b/contrib/bind/lib/irs/getnameinfo.c index 3157c66..7bd30ae 100644 --- a/contrib/bind/lib/irs/getnameinfo.c +++ b/contrib/bind/lib/irs/getnameinfo.c @@ -110,7 +110,6 @@ getnameinfo(sa, salen, host, hostlen, serv, servlen, flags) #endif int family, i; char *addr, *p; - u_long v4a; u_char pfx; static int firsttime = 1; static char numserv[512]; @@ -182,15 +181,11 @@ getnameinfo(sa, salen, host, hostlen, serv, servlen, flags) switch (sa->sa_family) { case AF_INET: - v4a = ((struct sockaddr_in *)sa)->sin_addr.s_addr; - if (IN_MULTICAST(v4a) || IN_EXPERIMENTAL(v4a)) - flags |= NI_NUMERICHOST; - v4a >>= IN_CLASSA_NSHIFT; - if (v4a == 0 || v4a == IN_LOOPBACKNET) + if (ntohl(*(u_long *)addr) >> IN_CLASSA_NSHIFT == 0) flags |= NI_NUMERICHOST; break; case AF_INET6: - pfx = ((struct sockaddr_in6 *)sa)->sin6_addr.s6_addr[0]; + pfx = *addr; if (pfx == 0 || pfx == 0xfe || pfx == 0xff) flags |= NI_NUMERICHOST; break; diff --git a/contrib/bind/lib/irs/getpwent.c b/contrib/bind/lib/irs/getpwent.c index 94f2df5..7f536a4 100644 --- a/contrib/bind/lib/irs/getpwent.c +++ b/contrib/bind/lib/irs/getpwent.c @@ -16,7 +16,7 @@ */ #if !defined(LINT) && !defined(CODECENTER) -static const char rcsid[] = "$Id: getpwent.c,v 1.20 1999/10/13 16:39:31 vixie Exp $"; +static const char rcsid[] = "$Id: getpwent.c,v 1.21 2000/02/21 21:40:56 vixie Exp $"; #endif /* Imports */ @@ -97,7 +97,7 @@ void endpwent() { struct net_data *net_data = init(); - return (endpwent_p(net_data)); + endpwent_p(net_data); } /* Shared private. */ diff --git a/contrib/bind/lib/irs/hesiod.c b/contrib/bind/lib/irs/hesiod.c index 54a6657..40826eb 100644 --- a/contrib/bind/lib/irs/hesiod.c +++ b/contrib/bind/lib/irs/hesiod.c @@ -1,5 +1,5 @@ #if defined(LIBC_SCCS) && !defined(lint) -static const char rcsid[] = "$Id: hesiod.c,v 1.20 1999/02/22 04:09:06 vixie Exp $"; +static const char rcsid[] = "$Id: hesiod.c,v 1.21 2000/02/28 14:51:08 vixie Exp $"; #endif /* @@ -85,6 +85,7 @@ hesiod_init(void **context) { ctx->LHS = NULL; ctx->RHS = NULL; + ctx->res = NULL; if (parse_config_file(ctx, _PATH_HESIOD_CONF) < 0) { #ifdef DEF_RHS diff --git a/contrib/bind/lib/irs/irp.c b/contrib/bind/lib/irs/irp.c index c2b64ab..a6c8f4f 100644 --- a/contrib/bind/lib/irs/irp.c +++ b/contrib/bind/lib/irs/irp.c @@ -16,7 +16,7 @@ */ #if !defined(LINT) && !defined(CODECENTER) -static const char rcsid[] = "$Id: irp.c,v 8.5 1999/10/13 17:11:18 vixie Exp $"; +static const char rcsid[] = "$Id: irp.c,v 8.6 2000/02/04 08:28:33 vixie Exp $"; #endif /* Imports */ @@ -151,7 +151,9 @@ irs_irp_connect(struct irp_p *pvt) { int flags; struct sockaddr *addr; struct sockaddr_in iaddr; +#ifndef NO_SOCKADDR_UN struct sockaddr_un uaddr; +#endif long ipaddr; const char *irphost; int code; @@ -163,7 +165,9 @@ irs_irp_connect(struct irp_p *pvt) { return (-1); } +#ifndef NO_SOCKADDR_UN memset(&uaddr, 0, sizeof uaddr); +#endif memset(&iaddr, 0, sizeof iaddr); irphost = getenv(IRPD_HOST_ENV); @@ -171,6 +175,7 @@ irs_irp_connect(struct irp_p *pvt) { irphost = "127.0.0.1"; } +#ifndef NO_SOCKADDR_UN if (irphost[0] == '/') { addr = (struct sockaddr *)&uaddr; strncpy(uaddr.sun_path, irphost, sizeof uaddr.sun_path); @@ -179,7 +184,9 @@ irs_irp_connect(struct irp_p *pvt) { #ifdef HAVE_SA_LEN uaddr.sun_len = socklen; #endif - } else { + } else +#endif + { if (inet_pton(AF_INET, irphost, &ipaddr) != 1) { errno = EADDRNOTAVAIL; perror("inet_pton"); diff --git a/contrib/bind/lib/irs/lcl.c b/contrib/bind/lib/irs/lcl.c index 46c7743..16e167f 100644 --- a/contrib/bind/lib/irs/lcl.c +++ b/contrib/bind/lib/irs/lcl.c @@ -16,7 +16,7 @@ */ #if !defined(LINT) && !defined(CODECENTER) -static const char rcsid[] = "$Id: lcl.c,v 1.15 1999/10/13 16:39:32 vixie Exp $"; +static const char rcsid[] = "$Id: lcl.c,v 1.16 2000/02/28 07:52:16 vixie Exp $"; #endif /* Imports */ @@ -104,7 +104,7 @@ lcl_res_get(struct irs_acc *this) { lcl_res_set(this, res, free); } - if ((lcl->res->options | RES_INIT) == 0 && + if ((lcl->res->options & RES_INIT) == 0 && res_ninit(lcl->res) < 0) return (NULL); diff --git a/contrib/bind/lib/irs/nis.c b/contrib/bind/lib/irs/nis.c index fcd9b79..e19068a 100644 --- a/contrib/bind/lib/irs/nis.c +++ b/contrib/bind/lib/irs/nis.c @@ -16,7 +16,7 @@ */ #if defined(LIBC_SCCS) && !defined(lint) -static const char rcsid[] = "$Id: nis.c,v 1.13 1999/01/18 07:46:58 vixie Exp $"; +static const char rcsid[] = "$Id: nis.c,v 1.14 2000/02/28 07:52:16 vixie Exp $"; #endif /* Imports */ @@ -114,7 +114,7 @@ nis_res_get(struct irs_acc *this) { nis_res_set(this, res, free); } - if ((nis->res->options | RES_INIT) == 0 && + if ((nis->res->options & RES_INIT) == 0 && res_ninit(nis->res) < 0) return (NULL); diff --git a/contrib/bind/lib/irs/util.c b/contrib/bind/lib/irs/util.c index 8965af5..1d097c6 100644 --- a/contrib/bind/lib/irs/util.c +++ b/contrib/bind/lib/irs/util.c @@ -16,7 +16,7 @@ */ #if defined(LIBC_SCCS) && !defined(lint) -static const char rcsid[] = "$Id: util.c,v 1.10 1999/01/08 19:25:11 vixie Exp $"; +static const char rcsid[] = "$Id: util.c,v 1.11 2000/02/04 08:28:33 vixie Exp $"; #endif #include "port_before.h" @@ -48,18 +48,18 @@ static const char rcsid[] = "$Id: util.c,v 1.10 1999/01/08 19:25:11 vixie Exp $" void map_v4v6_address(const char *src, char *dst) { u_char *p = (u_char *)dst; - char tmp[INADDRSZ]; + char tmp[NS_INADDRSZ]; int i; /* Stash a temporary copy so our caller can update in place. */ - memcpy(tmp, src, INADDRSZ); + memcpy(tmp, src, NS_INADDRSZ); /* Mark this ipv6 addr as a mapped ipv4. */ for (i = 0; i < 10; i++) *p++ = 0x00; *p++ = 0xff; *p++ = 0xff; /* Retrieve the saved copy and we're done. */ - memcpy((void*)p, tmp, INADDRSZ); + memcpy((void*)p, tmp, NS_INADDRSZ); } int diff --git a/contrib/bind/lib/isc/Makefile b/contrib/bind/lib/isc/Makefile index 87e20f2..364c442 100644 --- a/contrib/bind/lib/isc/Makefile +++ b/contrib/bind/lib/isc/Makefile @@ -13,7 +13,7 @@ # ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS # SOFTWARE. -# $Id: Makefile,v 8.22 1999/02/22 02:47:58 vixie Exp $ +# $Id: Makefile,v 8.25 2000/02/29 03:38:23 vixie Exp $ # these are only appropriate for BSD 4.4 or derivatives, and are used in # development. normal builds will be done in the top level directory and @@ -64,14 +64,15 @@ ${LIBBIND}: ${OBJS} ${RANLIB} ${LIBBIND} .c.${O}: - if test ! -d ${THREADED} ; then mkdir ${THREADED} ; fi + if test ! -d ${THREADED} ; then mkdir ${THREADED} ; else true ; fi ${CC} ${CPPFLAGS} ${CFLAGS} ${BOUNDS} ${REENTRANT} -c $*.c \ -o ${THREADED}/$*.${O} - -${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} -o a.out && \ - ${LDS} mv a.out ${THREADED}/$*.${O} + -${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} \ + -o ${THREADED}/$*.out && \ + ${LDS} mv ${THREADED}/$*.out ${THREADED}/$*.${O} ${CC} ${CPPFLAGS} ${CFLAGS} ${BOUNDS} -c $*.c - -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o a.out && \ - ${LDS} mv a.out $*.${O} + -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o $*.out && \ + ${LDS} mv $*.out $*.${O} distclean: clean @@ -79,7 +80,7 @@ clean: FRC rm -f .depend a.out core ${LIB} tags rm -f *.${O} *.BAK *.CKP *~ rm -f ${THREADED}/*.${O} - -rmdir ${THREADED} + -if test -d ${THREADED} ; then rmdir ${THREADED}; else true; fi depend: FRC mkdep -I${INCL} -I${PORTINCL} ${CPPFLAGS} ${SRCS} diff --git a/contrib/bind/lib/isc/ctl_p.c b/contrib/bind/lib/isc/ctl_p.c index d70a05f..7d9058c 100644 --- a/contrib/bind/lib/isc/ctl_p.c +++ b/contrib/bind/lib/isc/ctl_p.c @@ -1,5 +1,5 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ctl_p.c,v 8.6 1999/10/13 16:39:34 vixie Exp $"; +static const char rcsid[] = "$Id: ctl_p.c,v 8.7 2000/02/04 08:28:33 vixie Exp $"; #endif /* not lint */ /* @@ -125,6 +125,7 @@ ctl_sa_ntop(const struct sockaddr *sa, (void) sprintf(buf, "[%s].%u", tmp, ntohs(in->sin_port)); return (buf); } +#ifndef NO_SOCKADDR_UN case AF_UNIX: { const struct sockaddr_un *un = (struct sockaddr_un *) sa; int x = sizeof un->sun_path; @@ -135,6 +136,7 @@ ctl_sa_ntop(const struct sockaddr *sa, buf[x - 1] = '\0'; return (buf); } +#endif default: return (punt); } @@ -146,9 +148,11 @@ ctl_sa_copy(const struct sockaddr *src, struct sockaddr *dst) { case AF_INET: *((struct sockaddr_in *)dst) = *((struct sockaddr_in *)src); break; +#ifndef NO_SOCKADDR_UN case AF_UNIX: *((struct sockaddr_un *)dst) = *((struct sockaddr_un *)src); break; +#endif default: *dst = *src; break; diff --git a/contrib/bind/lib/isc/ctl_srvr.c b/contrib/bind/lib/isc/ctl_srvr.c index 0bdc8c8..ff1fc82 100644 --- a/contrib/bind/lib/isc/ctl_srvr.c +++ b/contrib/bind/lib/isc/ctl_srvr.c @@ -1,5 +1,5 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: ctl_srvr.c,v 8.21 1999/10/17 08:41:57 cyarnell Exp $"; +static const char rcsid[] = "$Id: ctl_srvr.c,v 8.23 2000/02/04 08:28:33 vixie Exp $"; #endif /* not lint */ /* @@ -73,7 +73,9 @@ enum state { union sa_un { struct sockaddr_in in; +#ifndef NO_SOCKADDR_UN struct sockaddr_un un; +#endif }; struct ctl_sess { @@ -229,8 +231,12 @@ ctl_server(evContext lev, const struct sockaddr *sap, size_t sap_len, me, strerror(errno)); } if (bind(ctx->sock, sap, sap_len) < 0) { + char tmp[MAX_NTOP]; save_errno = errno; - (*ctx->logger)(ctl_error, "%s: bind: %s", me, strerror(errno)); + (*ctx->logger)(ctl_error, "%s: bind: %s: %s", + me, ctl_sa_ntop((struct sockaddr *)sap, + tmp, sizeof tmp, ctx->logger), + strerror(save_errno)); close(ctx->sock); memput(ctx, sizeof *ctx); errno = save_errno; @@ -561,7 +567,8 @@ ctl_readable(evContext lev, void *uap, int fd, int evmask) { ctl_close(sess); return; } - n = read(sess->sock, sess->inbuf.text, MAX_LINELEN - sess->inbuf.used); + n = read(sess->sock, sess->inbuf.text + sess->inbuf.used, + MAX_LINELEN - sess->inbuf.used); if (n <= 0) { (*ctx->logger)(ctl_debug, "%s: %s: read: %s", me, address_expr, diff --git a/contrib/bind/lib/isc/ev_connects.c b/contrib/bind/lib/isc/ev_connects.c index 237bcb1..1da5c10 100644 --- a/contrib/bind/lib/isc/ev_connects.c +++ b/contrib/bind/lib/isc/ev_connects.c @@ -20,7 +20,7 @@ */ #if !defined(LINT) && !defined(CODECENTER) -static const char rcsid[] = "$Id: ev_connects.c,v 8.25 1999/10/07 20:44:04 vixie Exp $"; +static const char rcsid[] = "$Id: ev_connects.c,v 8.26 2000/02/04 08:28:34 vixie Exp $"; #endif /* Import. */ @@ -235,7 +235,7 @@ evTryAccept(evContext opaqueCtx, evConnID id, int *sys_errno) { OKNEW(new); new->conn = conn; new->ralen = sizeof new->ra; - new->fd = accept(conn->fd, &new->ra, &new->ralen); + new->fd = accept(conn->fd, &new->ra.sa, &new->ralen); if (new->fd > ctx->highestFD) { close(new->fd); new->fd = -1; @@ -243,7 +243,7 @@ evTryAccept(evContext opaqueCtx, evConnID id, int *sys_errno) { } if (new->fd >= 0) { new->lalen = sizeof new->la; - if (GETXXXNAME(getsockname, new->fd, new->la, new->lalen) < 0) { + if (GETXXXNAME(getsockname, new->fd, new->la.sa, new->lalen) < 0) { new->ioErrno = errno; (void) close(new->fd); new->fd = -1; @@ -267,12 +267,18 @@ static void listener(evContext opaqueCtx, void *uap, int fd, int evmask) { evContext_p *ctx = opaqueCtx.opaque; evConn *conn = uap; - struct sockaddr la, ra; - int new, lalen, ralen; + union { + struct sockaddr sa; + struct sockaddr_in in; +#ifndef NO_SOCKADDR_UN + struct sockaddr_un un; +#endif + } la, ra; + int new, lalen = 0, ralen; REQUIRE((evmask & EV_READ) != 0); ralen = sizeof ra; - new = accept(fd, &ra, &ralen); + new = accept(fd, &ra.sa, &ralen); if (new > ctx->highestFD) { close(new); new = -1; @@ -280,7 +286,7 @@ listener(evContext opaqueCtx, void *uap, int fd, int evmask) { } if (new >= 0) { lalen = sizeof la; - if (GETXXXNAME(getsockname, new, la, lalen) < 0) { + if (GETXXXNAME(getsockname, new, la.sa, lalen) < 0) { int save = errno; (void) close(new); @@ -289,13 +295,19 @@ listener(evContext opaqueCtx, void *uap, int fd, int evmask) { } } else if (errno == EAGAIN || errno == EWOULDBLOCK) return; - (*conn->func)(opaqueCtx, conn->uap, new, &la, lalen, &ra, ralen); + (*conn->func)(opaqueCtx, conn->uap, new, &la.sa, lalen, &ra.sa, ralen); } static void connector(evContext opaqueCtx, void *uap, int fd, int evmask) { evConn *conn = uap; - struct sockaddr la, ra; + union { + struct sockaddr sa; + struct sockaddr_in in; +#ifndef NO_SOCKADDR_UN + struct sockaddr_un un; +#endif + } la, ra; int lalen, ralen; char buf[1]; void *conn_uap; @@ -325,13 +337,13 @@ connector(evContext opaqueCtx, void *uap, int fd, int evmask) { #else read(fd, buf, 0) < 0 || #endif - GETXXXNAME(getsockname, fd, la, lalen) < 0 || - GETXXXNAME(getpeername, fd, ra, ralen) < 0) { + GETXXXNAME(getsockname, fd, la.sa, lalen) < 0 || + GETXXXNAME(getpeername, fd, ra.sa, ralen) < 0) { int save = errno; (void) close(fd); /* XXX closing caller's fd */ errno = save; fd = -1; } - (*conn_func)(opaqueCtx, conn_uap, fd, &la, lalen, &ra, ralen); + (*conn_func)(opaqueCtx, conn_uap, fd, &la.sa, lalen, &ra.sa, ralen); } diff --git a/contrib/bind/lib/isc/ev_waits.c b/contrib/bind/lib/isc/ev_waits.c index c336dcb..e7bfbf7 100644 --- a/contrib/bind/lib/isc/ev_waits.c +++ b/contrib/bind/lib/isc/ev_waits.c @@ -20,7 +20,7 @@ */ #if !defined(LINT) && !defined(CODECENTER) -static const char rcsid[] = "$Id: ev_waits.c,v 8.9 1999/10/13 17:11:20 vixie Exp $"; +static const char rcsid[] = "$Id: ev_waits.c,v 8.10 2000/02/04 07:25:50 vixie Exp $"; #endif #include "port_before.h" @@ -212,6 +212,8 @@ evNewWaitList(evContext_p *ctx) { new->first = new->last = NULL; new->prev = NULL; new->next = ctx->waitLists; + if (new->next != NULL) + new->next->prev = new; ctx->waitLists = new; return (new); } diff --git a/contrib/bind/lib/isc/eventlib.c b/contrib/bind/lib/isc/eventlib.c index 6cb227b..cea98ac 100644 --- a/contrib/bind/lib/isc/eventlib.c +++ b/contrib/bind/lib/isc/eventlib.c @@ -20,7 +20,7 @@ */ #if !defined(LINT) && !defined(CODECENTER) -static const char rcsid[] = "$Id: eventlib.c,v 1.44 1999/10/13 17:11:20 vixie Exp $"; +static const char rcsid[] = "$Id: eventlib.c,v 1.45 2000/02/04 07:25:39 vixie Exp $"; #endif #include "port_before.h" @@ -345,7 +345,8 @@ evGetNext(evContext opaqueCtx, evEvent *opaqueEv, int options) { } ERR(pselect_errno); } - if (x == 0 && (nextTimer && !timerPast) && (options & EV_POLL)) + if (x == 0 && (nextTimer == NULL || !timerPast) && + (options & EV_POLL)) ERR(EWOULDBLOCK); ctx->fdCount = x; #ifdef EVENTLIB_TIME_CHECKS diff --git a/contrib/bind/lib/isc/eventlib_p.h b/contrib/bind/lib/isc/eventlib_p.h index 80dc160..b4d7ecc 100644 --- a/contrib/bind/lib/isc/eventlib_p.h +++ b/contrib/bind/lib/isc/eventlib_p.h @@ -18,7 +18,7 @@ /* eventlib_p.h - private interfaces for eventlib * vix 09sep95 [initial] * - * $Id: eventlib_p.h,v 1.27 1999/06/03 20:36:05 vixie Exp $ + * $Id: eventlib_p.h,v 1.28 2000/02/04 08:28:34 vixie Exp $ */ #ifndef _EVENTLIB_P_H @@ -27,6 +27,8 @@ #include <sys/param.h> #include <sys/types.h> #include <sys/socket.h> +#include <netinet/in.h> +#include <sys/un.h> #define EVENTLIB_DEBUG 1 @@ -76,9 +78,21 @@ typedef struct evConn { typedef struct evAccept { int fd; - struct sockaddr la; + union { + struct sockaddr sa; + struct sockaddr_in in; +#ifndef NO_SOCKADDR_UN + struct sockaddr_un un; +#endif + } la; int lalen; - struct sockaddr ra; + union { + struct sockaddr sa; + struct sockaddr_in in; +#ifndef NO_SOCKADDR_UN + struct sockaddr_un un; +#endif + } ra; int ralen; int ioErrno; evConn * conn; diff --git a/contrib/bind/lib/isc/logging.c b/contrib/bind/lib/isc/logging.c index a3988e4..7d6964b 100644 --- a/contrib/bind/lib/isc/logging.c +++ b/contrib/bind/lib/isc/logging.c @@ -16,7 +16,7 @@ */ #if !defined(LINT) && !defined(CODECENTER) -static const char rcsid[] = "$Id: logging.c,v 8.24 1999/10/13 16:39:34 vixie Exp $"; +static const char rcsid[] = "$Id: logging.c,v 8.26 2000/04/23 02:19:02 vixie Exp $"; #endif /* not lint */ #include "port_before.h" @@ -127,7 +127,7 @@ log_open_stream(log_channel chan) { flags = O_WRONLY|O_CREAT|O_APPEND; - if (chan->flags & LOG_TRUNCATE) { + if ((chan->flags & LOG_TRUNCATE) != 0) { if (regular) { (void)unlink(chan->out.file.name); flags |= O_EXCL; @@ -155,6 +155,7 @@ log_open_stream(log_channel chan) { chan->flags |= LOG_CHANNEL_BROKEN; return (NULL); } + (void) fchown(fd, chan->out.file.owner, chan->out.file.group); chan->out.file.stream = stream; return (stream); @@ -617,10 +618,23 @@ log_new_file_channel(unsigned int flags, int level, chan->out.file.stream = stream; chan->out.file.versions = versions; chan->out.file.max_size = max_size; + chan->out.file.owner = getuid(); + chan->out.file.group = getgid(); chan->references = 0; return (chan); } +int +log_set_file_owner(log_channel chan, uid_t owner, gid_t group) { + if (chan->type != log_file) { + errno = EBADF; + return (-1); + } + chan->out.file.owner = owner; + chan->out.file.group = group; + return (0); +} + log_channel log_new_null_channel() { log_channel chan; diff --git a/contrib/bind/lib/isc/logging.mdoc b/contrib/bind/lib/isc/logging.mdoc index 6b48943..47d4312 100644 --- a/contrib/bind/lib/isc/logging.mdoc +++ b/contrib/bind/lib/isc/logging.mdoc @@ -1,4 +1,4 @@ -.\" $Id: logging.mdoc,v 8.3 1999/01/08 19:25:41 vixie Exp $ +.\" $Id: logging.mdoc,v 8.4 2000/04/23 02:19:02 vixie Exp $ .\" .\"Copyright (c) 1995-1999 by Internet Software Consortium .\" @@ -36,6 +36,7 @@ .Nm log_category_is_active , .Nm log_new_syslog_channel , .Nm log_new_file_channel , +.Nm log_set_file_owner , .Nm log_new_null_channel , .Nm log_inc_references , .Nm log_dec_references , @@ -80,6 +81,8 @@ .Fn log_new_file_channel "unsigned int flags" "int level" \ "char *name" "FILE *stream" "unsigned int versions" \ "unsigned long max_size" +.Ft int +.Fn log_set_file_owner "log_channel chan" "uid_t owner" "gid_t group" .Ft log_channel .Fn log_new_null_channel "void" .Ft int @@ -187,7 +190,12 @@ filename. The and .Fn log_get_filename functions return the stream or filename, respectively, of such a logging -channel. +channel. Also unique to logging channels of type +.Dv log_file +is the +.Fn log_set_file_owner +function, which tells the logging system what user and group ought to own +newly created files (which is only effective if the caller is privileged.) .Pp Callers provide .Dq Nm categories , diff --git a/contrib/bind/lib/isc/logging_p.h b/contrib/bind/lib/isc/logging_p.h index e94102e..875da0e 100644 --- a/contrib/bind/lib/isc/logging_p.h +++ b/contrib/bind/lib/isc/logging_p.h @@ -24,6 +24,8 @@ typedef struct log_file_desc { FILE *stream; unsigned int versions; unsigned long max_size; + uid_t owner; + gid_t group; } log_file_desc; typedef union log_output { diff --git a/contrib/bind/lib/nameser/Makefile b/contrib/bind/lib/nameser/Makefile index 52a102f..ed068b1 100644 --- a/contrib/bind/lib/nameser/Makefile +++ b/contrib/bind/lib/nameser/Makefile @@ -15,7 +15,7 @@ # SOFTWARE. # -# $Id: Makefile,v 8.16 1999/09/07 08:47:28 vixie Exp $ +# $Id: Makefile,v 8.19 2000/02/29 03:38:23 vixie Exp $ # these are only appropriate for BSD 4.4 or derivatives, and are used in # development. normal builds will be done in the top level directory and @@ -59,14 +59,15 @@ ${LIBBIND}: ${OBJS} ${RANLIB} ${LIBBIND} .c.${O}: - if test ! -d ${THREADED} ; then mkdir ${THREADED} ; fi + if test ! -d ${THREADED} ; then mkdir ${THREADED} ; else true ; fi ${CC} ${CPPFLAGS} ${CFLAGS} ${BOUNDS} ${REENTRANT} -c $*.c \ -o ${THREADED}/$*.${O} - -${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} -o a.out && \ - ${LDS} mv a.out ${THREADED}/$*.${O} + -${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} \ + -o ${THREADED}/$*.out && \ + ${LDS} mv ${THREADED}/$*.out ${THREADED}/$*.${O} ${CC} ${CPPFLAGS} ${CFLAGS} ${BOUNDS} -c $*.c - -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o a.out && \ - ${LDS} mv a.out $*.${O} + -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o $*.out && \ + ${LDS} mv $*.out $*.${O} distclean: clean @@ -74,7 +75,7 @@ clean: FRC rm -f .depend a.out core ${LIB} tags rm -f *.${O} *.BAK *.CKP *~ rm -f ${THREADED}/*.${O} - -rmdir ${THREADED} + -if test -d ${THREADED} ; then rmdir ${THREADED}; else true; fi depend: FRC mkdep -I${INCL} -I${PORTINCL} ${CPPFLAGS} ${SRCS} diff --git a/contrib/bind/lib/nameser/ns_name.c b/contrib/bind/lib/nameser/ns_name.c index 6bd668d..2424eed 100644 --- a/contrib/bind/lib/nameser/ns_name.c +++ b/contrib/bind/lib/nameser/ns_name.c @@ -16,7 +16,7 @@ */ #ifndef lint -static const char rcsid[] = "$Id: ns_name.c,v 8.12 1999/10/13 17:11:23 vixie Exp $"; +static const char rcsid[] = "$Id: ns_name.c,v 8.15 2000/03/30 22:53:46 vixie Exp $"; #endif #include "port_before.h" @@ -379,7 +379,7 @@ ns_name_pack(const u_char *src, u_char *dst, int dstsiz, u_char *dstp; const u_char **cpp, **lpp, *eob, *msg; const u_char *srcp; - int n, l; + int n, l, first = 1; srcp = src; dstp = dst; @@ -428,9 +428,10 @@ ns_name_pack(const u_char *src, u_char *dst, int dstsiz, } /* Not found, save it. */ if (lastdnptr != NULL && cpp < lastdnptr - 1 && - (dstp - msg) < 0x4000) { + (dstp - msg) < 0x4000 && first) { *cpp++ = dstp; *cpp = NULL; + first = 0; } } /* copy label to buffer */ @@ -503,6 +504,23 @@ ns_name_compress(const char *src, u_char *dst, size_t dstsiz, } /* + * Reset dnptrs so that there are no active references to pointers at or + * after src. + */ +void +ns_name_rollback(const u_char *src, const u_char **dnptrs, + const u_char **lastdnptr) +{ + while (dnptrs < lastdnptr && *dnptrs != NULL) { + if (*dnptrs >= src) { + *dnptrs = NULL; + break; + } + dnptrs++; + } +} + +/* * ns_name_skip(ptrptr, eom) * Advance *ptrptr to skip over the compressed name it points at. * return: @@ -604,36 +622,48 @@ dn_find(const u_char *domain, const u_char *msg, u_int n; for (cpp = dnptrs; cpp < lastdnptr; cpp++) { - dn = domain; - sp = cp = *cpp; - while ((n = *cp++) != 0) { - /* - * check for indirection - */ - switch (n & NS_CMPRSFLGS) { - case 0: /* normal case, n == len */ - if (n != *dn++) - goto next; - for ((void)NULL; n > 0; n--) - if (mklower(*dn++) != mklower(*cp++)) + sp = *cpp; + /* + * terminate search on: + * root label + * compression pointer + * unusable offset + */ + while (*sp != 0 && (*sp & NS_CMPRSFLGS) == 0 && + (sp - msg) < 0x4000) { + dn = domain; + cp = sp; + while ((n = *cp++) != 0) { + /* + * check for indirection + */ + switch (n & NS_CMPRSFLGS) { + case 0: /* normal case, n == len */ + if (n != *dn++) goto next; - /* Is next root for both ? */ - if (*dn == '\0' && *cp == '\0') - return (sp - msg); - if (*dn) - continue; - goto next; - - case NS_CMPRSFLGS: /* indirection */ - cp = msg + (((n & 0x3f) << 8) | *cp); - break; - - default: /* illegal type */ - errno = EMSGSIZE; - return (-1); + for ((void)NULL; n > 0; n--) + if (mklower(*dn++) != + mklower(*cp++)) + goto next; + /* Is next root for both ? */ + if (*dn == '\0' && *cp == '\0') + return (sp - msg); + if (*dn) + continue; + goto next; + + case NS_CMPRSFLGS: /* indirection */ + cp = msg + (((n & 0x3f) << 8) | *cp); + break; + + default: /* illegal type */ + errno = EMSGSIZE; + return (-1); + } } + next: + sp += *sp + 1; } - next: ; } errno = ENOENT; return (-1); diff --git a/contrib/bind/lib/nameser/ns_print.c b/contrib/bind/lib/nameser/ns_print.c index 93f1e91..6c47882 100644 --- a/contrib/bind/lib/nameser/ns_print.c +++ b/contrib/bind/lib/nameser/ns_print.c @@ -16,7 +16,7 @@ */ #ifndef lint -static const char rcsid[] = "$Id: ns_print.c,v 8.17 1999/10/19 02:06:54 gson Exp $"; +static const char rcsid[] = "$Id: ns_print.c,v 8.18 2000/02/29 05:48:12 vixie Exp $"; #endif /* Import. */ @@ -127,9 +127,10 @@ ns_sprintrrf(const u_char *msg, size_t msglen, T(addstr("@\t\t\t", 4, &buf, &buflen)); } else { T(addstr(name, len, &buf, &buflen)); - /* Origin not used and no trailing dot? */ - if ((!origin || !origin[0] || name[len] == '\0') && - name[len - 1] != '.') { + /* Origin not used or not root, and no trailing dot? */ + if (((origin == NULL || origin[0] == '\0') || + (origin[0] != '.' && origin[1] != '\0' && + name[len] == '\0')) && name[len - 1] != '.') { T(addstr(".", 1, &buf, &buflen)); len++; } @@ -751,20 +752,22 @@ addname(const u_char *msg, size_t msglen, if (n < 0) goto enospc; /* Guess. */ newlen = prune_origin(*buf, origin); - if ((origin == NULL || origin[0] == '\0' || (*buf)[newlen] == '\0') && - (newlen == 0 || (*buf)[newlen - 1] != '.')) { - /* No trailing dot. */ - if (newlen + 2 > *buflen) - goto enospc; /* No room for ".\0". */ - (*buf)[newlen++] = '.'; - (*buf)[newlen] = '\0'; - } if (newlen == 0) { /* Use "@" instead of name. */ if (newlen + 2 > *buflen) goto enospc; /* No room for "@\0". */ (*buf)[newlen++] = '@'; (*buf)[newlen] = '\0'; + } else { + if (((origin == NULL || origin[0] == '\0') || + (origin[0] != '.' && origin[1] != '\0' && + (*buf)[newlen] == '\0')) && (*buf)[newlen - 1] != '.') { + /* No trailing dot. */ + if (newlen + 2 > *buflen) + goto enospc; /* No room for ".\0". */ + (*buf)[newlen++] = '.'; + (*buf)[newlen] = '\0'; + } } *pp += n; addlen(newlen, buf, buflen); diff --git a/contrib/bind/lib/nameser/ns_verify.c b/contrib/bind/lib/nameser/ns_verify.c index 316da13..0f19913 100644 --- a/contrib/bind/lib/nameser/ns_verify.c +++ b/contrib/bind/lib/nameser/ns_verify.c @@ -16,7 +16,7 @@ */ #ifndef lint -static const char rcsid[] = "$Id: ns_verify.c,v 8.11 1999/10/15 21:06:51 vixie Exp $"; +static const char rcsid[] = "$Id: ns_verify.c,v 8.13 2000/03/29 15:55:00 bwelling Exp $"; #endif /* Import. */ @@ -231,6 +231,7 @@ ns_verify(u_char *msg, int *msglen, void *k, if (key != NULL && error != ns_r_badsig && error != ns_r_badkey) { void *ctx; u_char buf[MAXDNAME]; + u_char buf2[MAXDNAME]; /* Digest the query signature, if this is a response. */ dst_verify_data(SIG_MODE_INIT, key, &ctx, NULL, 0, NULL, 0); @@ -247,7 +248,12 @@ ns_verify(u_char *msg, int *msglen, void *k, NULL, 0); /* Digest the key name. */ - n = ns_name_ntol(recstart, buf, sizeof(buf)); + n = ns_name_pton(name, buf2, sizeof(buf2)); + if (n < 0) + return (-1); + n = ns_name_ntol(buf2, buf, sizeof(buf)); + if (n < 0) + return (-1); dst_verify_data(SIG_MODE_UPDATE, key, &ctx, buf, n, NULL, 0); /* Digest the class and TTL. */ @@ -256,7 +262,12 @@ ns_verify(u_char *msg, int *msglen, void *k, INT16SZ + INT32SZ, NULL, 0); /* Digest the algorithm. */ - n = ns_name_ntol(rdatastart, buf, sizeof(buf)); + n = ns_name_pton(alg, buf2, sizeof(buf2)); + if (n < 0) + return (-1); + n = ns_name_ntol(buf2, buf, sizeof(buf)); + if (n < 0) + return (-1); dst_verify_data(SIG_MODE_UPDATE, key, &ctx, buf, n, NULL, 0); /* Digest the time signed and fudge. */ @@ -450,9 +461,6 @@ ns_verify_tcp(u_char *msg, int *msglen, ns_tcp_tsig_state *state, return (-ns_r_badsig); if (sigfieldlen > sizeof(state->sig)) - return (ns_r_badsig); - - if (sigfieldlen > sizeof(state->sig)) return (NS_TSIG_ERROR_NO_SPACE); memcpy(state->sig, sigstart, sigfieldlen); diff --git a/contrib/bind/lib/resolv/Makefile b/contrib/bind/lib/resolv/Makefile index 243e69b..78741be 100644 --- a/contrib/bind/lib/resolv/Makefile +++ b/contrib/bind/lib/resolv/Makefile @@ -13,7 +13,7 @@ # ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS # SOFTWARE. -# $Id: Makefile,v 8.30 1999/10/07 08:24:15 vixie Exp $ +# $Id: Makefile,v 8.33 2000/02/29 03:38:24 vixie Exp $ # these are only appropriate for BSD 4.4 or derivatives, and are used in # development. normal builds will be done in the top level directory and @@ -62,14 +62,15 @@ ${LIBBIND}: ${OBJS} ${RANLIB} ${LIBBIND} .c.${O}: - if test ! -d ${THREADED} ; then mkdir ${THREADED} ; fi + if test ! -d ${THREADED} ; then mkdir ${THREADED} ; else true ; fi ${CC} ${CPPFLAGS} ${CFLAGS} ${BOUNDS} ${REENTRANT} -c $*.c \ -o ${THREADED}/$*.${O} - -${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} -o a.out && \ - ${LDS} mv a.out ${THREADED}/$*.${O} + -${LDS} ${LD} ${LD_LIBFLAGS} ${THREADED}/$*.${O} \ + -o ${THREADED}/$*.out && \ + ${LDS} mv ${THREADED}/$*.out ${THREADED}/$*.${O} ${CC} ${CPPFLAGS} ${CFLAGS} ${BOUNDS} -c $*.c - -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o a.out && \ - ${LDS} mv a.out $*.${O} + -${LDS} ${LD} ${LD_LIBFLAGS} $*.${O} -o $*.out && \ + ${LDS} mv $*.out $*.${O} distclean: clean @@ -77,7 +78,7 @@ clean: FRC rm -f .depend a.out core ${LIB} tags rm -f *.${O} *.BAK *.CKP *~ rm -f ${THREADED}/*.${O} - -rmdir ${THREADED} + -if test -d ${THREADED} ; then rmdir ${THREADED}; else true; fi depend: FRC mkdep -I${INCL} -I${PORTINCL} ${CPPFLAGS} ${SRCS} diff --git a/contrib/bind/lib/resolv/res_debug.c b/contrib/bind/lib/resolv/res_debug.c index 39f5e9f..180d67f 100644 --- a/contrib/bind/lib/resolv/res_debug.c +++ b/contrib/bind/lib/resolv/res_debug.c @@ -95,7 +95,7 @@ #if defined(LIBC_SCCS) && !defined(lint) static const char sccsid[] = "@(#)res_debug.c 8.1 (Berkeley) 6/4/93"; -static const char rcsid[] = "$Id: res_debug.c,v 8.32 1999/10/13 16:39:39 vixie Exp $"; +static const char rcsid[] = "$Id: res_debug.c,v 8.34 2000/02/29 05:30:55 vixie Exp $"; #endif /* LIBC_SCCS and not lint */ #include "port_before.h" @@ -149,7 +149,8 @@ do_section(const res_state statp, int pflag, FILE *file) { int n, sflag, rrnum; - char buf[2048]; /* XXX need to malloc */ + static int buflen = 2048; + char *buf; ns_opcode opcode; ns_rr rr; @@ -160,6 +161,12 @@ do_section(const res_state statp, if (statp->pfcode && !sflag) return; + buf = malloc(buflen); + if (buf == NULL) { + fprintf(file, ";; memory allocation failure\n"); + return; + } + opcode = (ns_opcode) ns_msg_getflag(*handle, ns_f_opcode); rrnum = 0; for (;;) { @@ -170,7 +177,7 @@ do_section(const res_state statp, else if (rrnum > 0 && sflag != 0 && (statp->pfcode & RES_PRF_HEAD1)) putc('\n', file); - return; + goto cleanup; } if (rrnum == 0 && sflag != 0 && (statp->pfcode & RES_PRF_HEAD1)) fprintf(file, ";; %s SECTION:\n", @@ -182,17 +189,32 @@ do_section(const res_state statp, p_class(ns_rr_class(rr))); else { n = ns_sprintrr(handle, &rr, NULL, NULL, - buf, sizeof buf); + buf, buflen); if (n < 0) { + if (errno == ENOSPC) { + free(buf); + buf = NULL; + if (buflen < 131072) + buf = malloc(buflen += 1024); + if (buf == NULL) { + fprintf(file, + ";; memory allocation failure\n"); + return; + } + continue; + } fprintf(file, ";; ns_sprintrr: %s\n", strerror(errno)); - return; + goto cleanup; } fputs(buf, file); fputc('\n', file); } rrnum++; } + cleanup: + if (buf != NULL) + free(buf); } /* diff --git a/contrib/bind/lib/resolv/res_debug.h b/contrib/bind/lib/resolv/res_debug.h index 1150551..4a0aa99 100644 --- a/contrib/bind/lib/resolv/res_debug.h +++ b/contrib/bind/lib/resolv/res_debug.h @@ -21,8 +21,8 @@ #ifndef DEBUG # define Dprint(cond, args) /*empty*/ # define DprintQ(cond, args, query, size) /*empty*/ -# define Aerror(file, string, error, address) /*empty*/ -# define Perror(file, string, error) /*empty*/ +# define Aerror(statp, file, string, error, address) /*empty*/ +# define Perror(statp, file, string, error) /*empty*/ #else # define Dprint(cond, args) if (cond) {fprintf args;} else {} # define DprintQ(cond, args, query, size) if (cond) {\ diff --git a/contrib/bind/lib/resolv/res_findzonecut.c b/contrib/bind/lib/resolv/res_findzonecut.c index 73a42a2..e65faa1 100644 --- a/contrib/bind/lib/resolv/res_findzonecut.c +++ b/contrib/bind/lib/resolv/res_findzonecut.c @@ -1,5 +1,5 @@ #if !defined(lint) && !defined(SABER) -static const char rcsid[] = "$Id: res_findzonecut.c,v 8.8 1999/10/15 19:49:11 vixie Exp $"; +static const char rcsid[] = "$Id: res_findzonecut.c,v 8.9 1999/12/21 09:33:34 cyarnell Exp $"; #endif /* not lint */ /* @@ -399,11 +399,16 @@ get_glue(res_state statp, ns_class class, rrset_ns *nsrrsp) { if (EMPTY(nsrr->addrs)) { n = do_query(statp, nsrr->name, class, ns_t_a, resp, &msg); - if (n != 0) { + if (n < 0) { DPRINTF(("get_glue: do_query('%s', %s') failed", - nsrr->name, p_class(class), n)); + nsrr->name, p_class(class))); return (-1); } + if (n > 0) { + DPRINTF(( + "get_glue: do_query('%s', %s') CNAME or DNAME found", + nsrr->name, p_class(class))); + } if (save_a(statp, &msg, ns_s_an, nsrr->name, class, &nsrr->addrs) < 0) { DPRINTF(("get_glue: save_r('%s', %s) failed", diff --git a/contrib/bind/lib/resolv/res_init.c b/contrib/bind/lib/resolv/res_init.c index 85dc7e3..12d9969 100644 --- a/contrib/bind/lib/resolv/res_init.c +++ b/contrib/bind/lib/resolv/res_init.c @@ -70,7 +70,7 @@ #if defined(LIBC_SCCS) && !defined(lint) static const char sccsid[] = "@(#)res_init.c 8.1 (Berkeley) 6/7/93"; -static const char rcsid[] = "$Id: res_init.c,v 8.13 1999/10/13 16:39:40 vixie Exp $"; +static const char rcsid[] = "$Id: res_init.c,v 8.16 2000/05/09 07:10:12 vixie Exp $"; #endif /* LIBC_SCCS and not lint */ #include "port_before.h" @@ -95,7 +95,6 @@ static const char rcsid[] = "$Id: res_init.c,v 8.13 1999/10/13 16:39:40 vixie Ex /* Options. Should all be left alone. */ #define RESOLVSORT -#define RFC1535 #define DEBUG static void res_setoptions __P((res_state, const char *, const char *)); @@ -156,9 +155,7 @@ __res_vinit(res_state statp, int preinit) { int nsort = 0; char *net; #endif -#ifndef RFC1535 int dots; -#endif if (!preinit) { statp->retrans = RES_TIMEOUT; @@ -177,10 +174,11 @@ __res_vinit(res_state statp, int preinit) { statp->nscount = 1; statp->ndots = 1; statp->pfcode = 0; - statp->_sock = -1; + statp->_vcsock = -1; statp->_flags = 0; statp->qhook = NULL; statp->rhook = NULL; + statp->_u._ext.nscount = 0; /* Allow user to override the local domain definition */ if ((cp = getenv("LOCALDOMAIN")) != NULL) { @@ -363,7 +361,6 @@ __res_vinit(res_state statp, int preinit) { *pp++ = statp->defdname; *pp = NULL; -#ifndef RFC1535 dots = 0; for (cp = statp->defdname; *cp; cp++) dots += (*cp == '.'); @@ -385,7 +382,6 @@ __res_vinit(res_state statp, int preinit) { printf(";;\t..END..\n"); } #endif -#endif /* !RFC1535 */ } if ((cp = getenv("RES_OPTIONS")) != NULL) @@ -479,3 +475,28 @@ res_randomid(void) { gettimeofday(&now, NULL); return (0xffff & (now.tv_sec ^ now.tv_usec ^ getpid())); } + +/* + * This routine is for closing the socket if a virtual circuit is used and + * the program wants to close it. This provides support for endhostent() + * which expects to close the socket. + * + * This routine is not expected to be user visible. + */ +void +res_nclose(res_state statp) { + int ns; + + if (statp->_vcsock >= 0) { + (void) close(statp->_vcsock); + statp->_vcsock = -1; + statp->_flags &= ~(RES_F_VC | RES_F_CONN); + } + for (ns = 0; ns < statp->_u._ext.nscount; ns++) { + if (statp->_u._ext.nssocks[ns] != -1) { + (void) close(statp->_u._ext.nssocks[ns]); + statp->_u._ext.nssocks[ns] = -1; + } + } + statp->_u._ext.nscount = 0; +} diff --git a/contrib/bind/lib/resolv/res_query.c b/contrib/bind/lib/resolv/res_query.c index 26c1a60..3147f1e 100644 --- a/contrib/bind/lib/resolv/res_query.c +++ b/contrib/bind/lib/resolv/res_query.c @@ -70,7 +70,7 @@ #if defined(LIBC_SCCS) && !defined(lint) static const char sccsid[] = "@(#)res_query.c 8.1 (Berkeley) 6/4/93"; -static const char rcsid[] = "$Id: res_query.c,v 8.19 1999/10/15 19:49:11 vixie Exp $"; +static const char rcsid[] = "$Id: res_query.c,v 8.20 2000/02/29 05:39:12 vixie Exp $"; #endif /* LIBC_SCCS and not lint */ #include "port_before.h" @@ -190,8 +190,9 @@ res_nsearch(res_state statp, HEADER *hp = (HEADER *) answer; char tmp[NS_MAXDNAME]; u_int dots; - int trailing_dot, ret; + int trailing_dot, ret, saved_herrno; int got_nodata = 0, got_servfail = 0, root_on_list = 0; + int tried_as_is = 0; errno = 0; RES_SET_H_ERRNO(statp, HOST_NOT_FOUND); /* True if we never query. */ @@ -208,12 +209,19 @@ res_nsearch(res_state statp, return (res_nquery(statp, cp, class, type, answer, anslen)); /* - * If there are enough dots in the name, do no searching. - * (The threshold can be set with the "ndots" option.) + * If there are enough dots in the name, let's just give it a + * try 'as is'. The threshold can be set with the "ndots" option. + * Also, query 'as is', if there is a trailing dot in the name. */ - if (dots >= statp->ndots || trailing_dot) - return (res_nquerydomain(statp, name, NULL, class, type, - answer, anslen)); + saved_herrno = -1; + if (dots >= statp->ndots || trailing_dot) { + ret = res_nquerydomain(statp, name, NULL, class, type, + answer, anslen); + if (ret > 0 || trailing_dot) + return (ret); + saved_herrno = h_errno; + tried_as_is++; + } /* * We do at least one level of search if @@ -285,10 +293,11 @@ res_nsearch(res_state statp, } /* - * If the name has any dots at all, and "." is not on the search - * list, then try an as-is query now. + * If the name has any dots at all, and no earlier 'as-is' query + * for the name, and "." is not on the search list, then try an as-is + * query now. */ - if (statp->ndots) { + if (statp->ndots && !(tried_as_is || root_on_list)) { ret = res_nquerydomain(statp, name, NULL, class, type, answer, anslen); if (ret > 0) @@ -302,7 +311,9 @@ res_nsearch(res_state statp, * else send back meaningless H_ERRNO, that being the one from * the last DNSRCH we did. */ - if (got_nodata) + if (saved_herrno != -1) + RES_SET_H_ERRNO(statp, saved_herrno); + else if (got_nodata) RES_SET_H_ERRNO(statp, NO_DATA); else if (got_servfail) RES_SET_H_ERRNO(statp, TRY_AGAIN); diff --git a/contrib/bind/lib/resolv/res_send.c b/contrib/bind/lib/resolv/res_send.c index 80c9e44..af674a1 100644 --- a/contrib/bind/lib/resolv/res_send.c +++ b/contrib/bind/lib/resolv/res_send.c @@ -70,7 +70,7 @@ #if defined(LIBC_SCCS) && !defined(lint) static const char sccsid[] = "@(#)res_send.c 8.1 (Berkeley) 6/4/93"; -static const char rcsid[] = "$Id: res_send.c,v 8.36 1999/10/15 19:49:11 vixie Exp $"; +static const char rcsid[] = "$Id: res_send.c,v 8.38 2000/03/30 20:16:51 vixie Exp $"; #endif /* LIBC_SCCS and not lint */ /* @@ -107,47 +107,33 @@ static const char rcsid[] = "$Id: res_send.c,v 8.36 1999/10/15 19:49:11 vixie Ex #define DEBUG #include "res_debug.h" +#define EXT(res) ((res)->_u._ext) + +static const int highestFD = FD_SETSIZE - 1; + +/* Forward. */ + +static int send_vc(res_state, const u_char *, int, + u_char *, int, int *, int); +static int send_dg(res_state, const u_char *, int, + u_char *, int, int *, int, + int *, int *); +static void Aerror(const res_state, FILE *, const char *, int, + struct sockaddr_in); +static void Perror(const res_state, FILE *, const char *, int); +static int sock_eq(struct sockaddr_in *, struct sockaddr_in *); #ifdef NEED_PSELECT static int pselect(int, void *, void *, void *, struct timespec *, const sigset_t *); #endif -#define CHECK_SRVR_ADDR - -#ifdef DEBUG - static void - Aerror(const res_state statp, FILE *file, const char *string, int error, - struct sockaddr_in address) - { - int save = errno; - - if ((statp->options & RES_DEBUG) != 0) { - char tmp[sizeof "255.255.255.255"]; - - fprintf(file, "res_send: %s ([%s].%u): %s\n", - string, - inet_ntop(address.sin_family, &address.sin_addr, - tmp, sizeof tmp), - ntohs(address.sin_port), - strerror(error)); - } - errno = save; - } - static void - Perror(const res_state statp, FILE *file, const char *string, int error) { - int save = errno; - - if ((statp->options & RES_DEBUG) != 0) - fprintf(file, "res_send: %s: %s\n", - string, strerror(error)); - errno = save; - } -#endif +/* Reachover. */ -static int cmpsock(struct sockaddr_in *a1, struct sockaddr_in *a2); void res_pquery(const res_state, const u_char *, int, FILE *); +/* Public. */ + /* int * res_isourserver(ina) * looks up "ina" in _res.ns_addr_list[] @@ -163,7 +149,7 @@ res_ourserver_p(const res_state statp, const struct sockaddr_in *inp) { int ns; ina = *inp; - for (ns = 0; ns < statp->nscount; ns++) { + for (ns = 0; ns < statp->nscount; ns++) { const struct sockaddr_in *srv = &statp->nsaddr_list[ns]; if (srv->sin_family == ina.sin_family && @@ -238,8 +224,8 @@ res_queriesmatch(const u_char *buf1, const u_char *eom1, * Only header section present in replies to * dynamic update packets. */ - if ( (((HEADER *)buf1)->opcode == ns_o_update) && - (((HEADER *)buf2)->opcode == ns_o_update) ) + if ((((HEADER *)buf1)->opcode == ns_o_update) && + (((HEADER *)buf2)->opcode == ns_o_update)) return (1); if (qdcount != ntohs(((HEADER*)buf2)->qdcount)) @@ -266,12 +252,12 @@ int res_nsend(res_state statp, const u_char *buf, int buflen, u_char *ans, int anssiz) { - HEADER *hp = (HEADER *) buf; - HEADER *anhp = (HEADER *) ans; - int gotsomewhere, connreset, terrno, try, v_circuit, resplen, ns, n; - u_int badns; /* XXX NSMAX can't exceed #/bits in this variable */ - static int highestFD = FD_SETSIZE - 1; + int gotsomewhere, terrno, try, v_circuit, resplen, ns, n; + if (statp->nscount == 0) { + errno = ESRCH; + return (-1); + } if (anssiz < HFIXEDSZ) { errno = EINVAL; return (-1); @@ -280,14 +266,46 @@ res_nsend(res_state statp, (stdout, ";; res_send()\n"), buf, buflen); v_circuit = (statp->options & RES_USEVC) || buflen > PACKETSZ; gotsomewhere = 0; - connreset = 0; terrno = ETIMEDOUT; - badns = 0; /* - * Some callers want to even out the load on their resolver list. + * If the ns_addr_list in the resolver context has changed, then + * invalidate our cached copy and the associated timing data. */ - if (statp->nscount > 0 && (statp->options & RES_ROTATE) != 0) { + if (EXT(statp).nscount != 0) { + int needclose = 0; + + if (EXT(statp).nscount != statp->nscount) + needclose++; + else + for (ns = 0; ns < statp->nscount; ns++) + if (!sock_eq(&statp->nsaddr_list[ns], + &EXT(statp).nsaddrs[ns])) { + needclose++; + break; + } + if (needclose) + res_nclose(statp); + } + + /* + * Maybe initialize our private copy of the ns_addr_list. + */ + if (EXT(statp).nscount == 0) { + for (ns = 0; ns < statp->nscount; ns++) { + EXT(statp).nsaddrs[ns] = statp->nsaddr_list[ns]; + EXT(statp).nstimes[ns] = RES_MAXTIME; + EXT(statp).nssocks[ns] = -1; + } + EXT(statp).nscount = statp->nscount; + } + + /* + * Some resolvers want to even out the load on their nameservers. + * Note that RES_BLAST overrides RES_ROTATE. + */ + if ((statp->options & RES_ROTATE) != 0 && + (statp->options & RES_BLAST) == 0) { struct sockaddr_in ina; int lastns = statp->nscount - 1; @@ -298,17 +316,12 @@ res_nsend(res_state statp, } /* - * Send request, RETRY times, or until successful + * Send request, RETRY times, or until successful. */ for (try = 0; try < statp->retry; try++) { for (ns = 0; ns < statp->nscount; ns++) { struct sockaddr_in *nsap = &statp->nsaddr_list[ns]; same_ns: - if (badns & (1 << ns)) { - res_nclose(statp); - goto next_ns; - } - if (statp->qhook) { int done = 0, loops = 0; @@ -344,454 +357,45 @@ res_nsend(res_state statp, ns + 1, inet_ntoa(nsap->sin_addr))); if (v_circuit) { - int truncated; - struct iovec iov[2]; - u_short len; - u_char *cp; - /* Use VC; at most one attempt per server. */ try = statp->retry; - truncated = 0; - - /* Are we still talking to whom we want to talk to? */ - if (statp->_sock >= 0 && - (statp->_flags & RES_F_VC) != 0) { - struct sockaddr_in peer; - int size = sizeof(peer); - - if (getpeername(statp->_sock, - (struct sockaddr *)&peer, - &size) < 0) { - res_nclose(statp); - statp->_flags &= ~RES_F_VC; - } else if (!cmpsock(&peer, nsap)) { - res_nclose(statp); - statp->_flags &= ~RES_F_VC; - } - } - - if (statp->_sock < 0 || - (statp->_flags & RES_F_VC) == 0) { - if (statp->_sock >= 0) - res_nclose(statp); - - statp->_sock = socket(PF_INET, - SOCK_STREAM, 0); - if (statp->_sock < 0 || - statp->_sock > highestFD) { - terrno = errno; - Perror(statp, stderr, - "socket(vc)", errno); - return (-1); - } - errno = 0; - if (connect(statp->_sock, - (struct sockaddr *)nsap, - sizeof *nsap) < 0) { - terrno = errno; - Aerror(statp, stderr, "connect/vc", - errno, *nsap); - badns |= (1 << ns); - res_nclose(statp); - goto next_ns; - } - statp->_flags |= RES_F_VC; - } - /* - * Send length & message - */ - putshort((u_short)buflen, (u_char*)&len); - iov[0].iov_base = (caddr_t)&len; - iov[0].iov_len = INT16SZ; - iov[1].iov_base = (caddr_t)buf; - iov[1].iov_len = buflen; - if (writev(statp->_sock, iov, 2) != - (INT16SZ + buflen)) { - terrno = errno; - Perror(statp, stderr, "write failed", errno); - badns |= (1 << ns); - res_nclose(statp); + n = send_vc(statp, buf, buflen, ans, anssiz, &terrno, + ns); + if (n < 0) + return (-1); + if (n == 0) goto next_ns; - } - /* - * Receive length & response - */ - read_len: - cp = ans; - len = INT16SZ; - while ((n = read(statp->_sock, - (char *)cp, (int)len)) > 0) { - cp += n; - if ((len -= n) <= 0) - break; - } - if (n <= 0) { - terrno = errno; - Perror(statp, stderr, "read failed", errno); - res_nclose(statp); - /* - * A long running process might get its TCP - * connection reset if the remote server was - * restarted. Requery the server instead of - * trying a new one. When there is only one - * server, this means that a query might work - * instead of failing. We only allow one reset - * per query to prevent looping. - */ - if (terrno == ECONNRESET && !connreset) { - connreset = 1; - res_nclose(statp); - goto same_ns; - } - res_nclose(statp); - goto next_ns; - } - resplen = ns_get16(ans); - if (resplen > anssiz) { - Dprint(statp->options & RES_DEBUG, - (stdout, ";; response truncated\n") - ); - truncated = 1; - len = anssiz; - } else - len = resplen; - if (len < HFIXEDSZ) { - /* - * Undersized message. - */ - Dprint(statp->options & RES_DEBUG, - (stdout, ";; undersized: %d\n", len)); - terrno = EMSGSIZE; - badns |= (1 << ns); - res_nclose(statp); - goto next_ns; - } - cp = ans; - while (len != 0 && - (n = read(statp->_sock, (char *)cp, (int)len)) - > 0) { - cp += n; - len -= n; - } - if (n <= 0) { - terrno = errno; - Perror(statp, stderr, "read(vc)", errno); - res_nclose(statp); - goto next_ns; - } - if (truncated) { - /* - * Flush rest of answer - * so connection stays in synch. - */ - anhp->tc = 1; - len = resplen - anssiz; - while (len != 0) { - char junk[PACKETSZ]; - - n = (len > sizeof(junk) - ? sizeof(junk) - : len); - n = read(statp->_sock, junk, n); - if (n > 0) - len -= n; - else - break; - } - } - /* - * The calling applicating has bailed out of - * a previous call and failed to arrange to have - * the circuit closed or the server has got - * itself confused. Anyway drop the packet and - * wait for the correct one. - */ - if (hp->id != anhp->id) { - DprintQ((statp->options & RES_DEBUG) || - (statp->pfcode & RES_PRF_REPLY), - (stdout, ";; old answer (unexpected):\n"), - ans, (resplen>anssiz)?anssiz:resplen); - goto read_len; - } + resplen = n; } else { - /* - * Use datagrams. - */ - struct timespec start, timeout, finish; - fd_set dsmask; - struct sockaddr_in from; - int fromlen, seconds; - - if (statp->_sock < 0 || - (statp->_flags & RES_F_VC) != 0) { - if ((statp->_flags & RES_F_VC) != 0) - res_nclose(statp); - statp->_sock = socket(PF_INET, SOCK_DGRAM, 0); - if (statp->_sock < 0 || - statp->_sock > highestFD) { -#ifndef CAN_RECONNECT - bad_dg_sock: -#endif - terrno = errno; - Perror(statp, stderr, - "socket(dg)", errno); - return (-1); - } - statp->_flags &= ~RES_F_CONN; - } -#ifndef CANNOT_CONNECT_DGRAM - /* - * On a 4.3BSD+ machine (client and server, - * actually), sending to a nameserver datagram - * port with no nameserver will cause an - * ICMP port unreachable message to be returned. - * If our datagram socket is "connected" to the - * server, we get an ECONNREFUSED error on the next - * socket operation, and select returns if the - * error message is received. We can thus detect - * the absence of a nameserver without timing out. - * If we have sent queries to at least two servers, - * however, we don't want to remain connected, - * as we wish to receive answers from the first - * server to respond. - */ - if (statp->nscount == 1 || (try == 0 && ns == 0)) { - /* - * Connect only if we are sure we won't - * receive a response from another server. - */ - if ((statp->_flags & RES_F_CONN) == 0) { - if (connect(statp->_sock, - (struct sockaddr *)nsap, - sizeof *nsap) < 0) { - Aerror(statp, stderr, - "connect(dg)", - errno, *nsap); - badns |= (1 << ns); - res_nclose(statp); - goto next_ns; - } - statp->_flags |= RES_F_CONN; - } - if (send(statp->_sock, (char*)buf, buflen, 0) - != buflen) { - Perror(statp, stderr, "send", errno); - badns |= (1 << ns); - res_nclose(statp); - goto next_ns; - } - } else { - /* - * Disconnect if we want to listen - * for responses from more than one server. - */ - if ((statp->_flags & RES_F_CONN) != 0) { -#ifdef CAN_RECONNECT - struct sockaddr_in no_addr; - - no_addr.sin_family = AF_INET; - no_addr.sin_addr.s_addr = INADDR_ANY; - no_addr.sin_port = 0; - (void) connect(statp->_sock, - (struct sockaddr *) - &no_addr, - sizeof no_addr); -#else - struct sockaddr_in local_addr; - int len, result, s1; - - len = sizeof(local_addr); - s1 = socket(PF_INET, SOCK_DGRAM, 0); - result = getsockname(statp->_sock, - (struct sockaddr *)&local_addr, - &len); - if (s1 < 0) - goto bad_dg_sock; - (void) dup2(s1, statp->_sock); - (void) close(s1); - if (result == 0) { - /* - * Attempt to rebind to old - * port. Note connected socket - * has an sin_addr set. - */ - local_addr.sin_addr.s_addr = - htonl(0); - (void)bind(statp->_sock, - (struct sockaddr *) - &local_addr, len); - } - Dprint(statp->options & RES_DEBUG, - (stdout, ";; new DG socket\n")) -#endif /* CAN_RECONNECT */ - statp->_flags &= ~RES_F_CONN; - errno = 0; - } -#endif /* !CANNOT_CONNECT_DGRAM */ - if (sendto(statp->_sock, - (char*)buf, buflen, 0, - (struct sockaddr *)nsap, - sizeof *nsap) - != buflen) { - Aerror(statp, stderr, "sendto", errno, *nsap); - badns |= (1 << ns); - res_nclose(statp); - goto next_ns; - } -#ifndef CANNOT_CONNECT_DGRAM - } -#endif /* !CANNOT_CONNECT_DGRAM */ - - if (statp->_sock < 0 || statp->_sock > highestFD) { - Perror(statp, stderr, - "fd out-of-bounds", EMFILE); - res_nclose(statp); - goto next_ns; - } - - /* - * Wait for reply - */ - seconds = (statp->retrans << try); - if (try > 0) - seconds /= statp->nscount; - if (seconds <= 0) - seconds = 1; - start = evNowTime(); - timeout = evConsTime(seconds, 0); - finish = evAddTime(start, timeout); - wait: - FD_ZERO(&dsmask); - FD_SET(statp->_sock, &dsmask); - n = pselect(statp->_sock + 1, - &dsmask, NULL, NULL, - &timeout, NULL); - if (n == 0) { - Dprint(statp->options & RES_DEBUG, - (stdout, ";; timeout\n")); - gotsomewhere = 1; - goto next_ns; - } - if (n < 0) { - if (errno == EINTR) { - struct timespec now; - - now = evNowTime(); - if (evCmpTime(finish, now) >= 0) { - timeout = evSubTime(finish, - now); - goto wait; - } - } - Perror(statp, stderr, "select", errno); - res_nclose(statp); - goto next_ns; - } - errno = 0; - fromlen = sizeof(struct sockaddr_in); - resplen = recvfrom(statp->_sock, (char*)ans, anssiz,0, - (struct sockaddr *)&from, &fromlen); - if (resplen <= 0) { - Perror(statp, stderr, "recvfrom", errno); - res_nclose(statp); - goto next_ns; - } - gotsomewhere = 1; - if (resplen < HFIXEDSZ) { - /* - * Undersized message. - */ - Dprint(statp->options & RES_DEBUG, - (stdout, ";; undersized: %d\n", - resplen)); - terrno = EMSGSIZE; - badns |= (1 << ns); - res_nclose(statp); + /* Use datagrams. */ + n = send_dg(statp, buf, buflen, ans, anssiz, &terrno, + ns, &v_circuit, &gotsomewhere); + if (n < 0) + return (-1); + if (n == 0) goto next_ns; - } - if (hp->id != anhp->id) { - /* - * response from old query, ignore it. - * XXX - potential security hazard could - * be detected here. - */ - DprintQ((statp->options & RES_DEBUG) || - (statp->pfcode & RES_PRF_REPLY), - (stdout, ";; old answer:\n"), - ans, (resplen>anssiz)?anssiz:resplen); - goto wait; - } -#ifdef CHECK_SRVR_ADDR - if (!(statp->options & RES_INSECURE1) && - !res_ourserver_p(statp, &from)) { - /* - * response from wrong server? ignore it. - * XXX - potential security hazard could - * be detected here. - */ - DprintQ((statp->options & RES_DEBUG) || - (statp->pfcode & RES_PRF_REPLY), - (stdout, ";; not our server:\n"), - ans, (resplen>anssiz)?anssiz:resplen); - goto wait; - } -#endif - if (!(statp->options & RES_INSECURE2) && - !res_queriesmatch(buf, buf + buflen, - ans, ans + anssiz)) { - /* - * response contains wrong query? ignore it. - * XXX - potential security hazard could - * be detected here. - */ - DprintQ((statp->options & RES_DEBUG) || - (statp->pfcode & RES_PRF_REPLY), - (stdout, ";; wrong query name:\n"), - ans, (resplen>anssiz)?anssiz:resplen); - goto wait; - } - if (anhp->rcode == SERVFAIL || - anhp->rcode == NOTIMP || - anhp->rcode == REFUSED) { - DprintQ(statp->options & RES_DEBUG, - (stdout, "server rejected query:\n"), - ans, (resplen>anssiz)?anssiz:resplen); - badns |= (1 << ns); - res_nclose(statp); - /* don't retry if called from dig */ - if (!statp->pfcode) - goto next_ns; - } - if (!(statp->options & RES_IGNTC) && anhp->tc) { - /* - * get rest of answer; - * use TCP with same server. - */ - Dprint(statp->options & RES_DEBUG, - (stdout, ";; truncated answer\n")); - v_circuit = 1; - res_nclose(statp); + if (v_circuit) goto same_ns; - } - } /*if vc/dg*/ + resplen = n; + } + Dprint((statp->options & RES_DEBUG) || ((statp->pfcode & RES_PRF_REPLY) && (statp->pfcode & RES_PRF_HEAD1)), (stdout, ";; got answer:\n")); + DprintQ((statp->options & RES_DEBUG) || (statp->pfcode & RES_PRF_REPLY), (stdout, ""), - ans, (resplen>anssiz)?anssiz:resplen); + ans, (resplen > anssiz) ? anssiz : resplen); + /* - * If using virtual circuits, we assume that the first server - * is preferred over the rest (i.e. it is on the local - * machine) and only keep that one open. * If we have temporarily opened a virtual circuit, * or if we haven't been asked to keep a socket open, * close the socket. */ - if ((v_circuit && (!(statp->options & RES_USEVC) || ns != 0)) || - !(statp->options & RES_STAYOPEN)) { + if (v_circuit && (statp->options & RES_USEVC) == 0 || + (statp->options & RES_STAYOPEN) == 0) { res_nclose(statp); } if (statp->rhook) { @@ -838,25 +442,391 @@ res_nsend(res_state statp, return (-1); } -/* - * This routine is for closing the socket if a virtual circuit is used and - * the program wants to close it. This provides support for endhostent() - * which expects to close the socket. - * - * This routine is not expected to be user visible. - */ -void -res_nclose(res_state statp) { - if (statp->_sock >= 0) { - (void) close(statp->_sock); - statp->_sock = -1; - statp->_flags &= ~(RES_F_VC | RES_F_CONN); +/* Private */ + +static int +send_vc(res_state statp, + const u_char *buf, int buflen, u_char *ans, int anssiz, + int *terrno, int ns) +{ + const HEADER *hp = (HEADER *) buf; + HEADER *anhp = (HEADER *) ans; + struct sockaddr_in *nsap = &statp->nsaddr_list[ns]; + int truncating, connreset, resplen, n; + struct iovec iov[2]; + u_short len; + u_char *cp; + + connreset = 0; + same_ns: + truncating = 0; + + /* Are we still talking to whom we want to talk to? */ + if (statp->_vcsock >= 0 && (statp->_flags & RES_F_VC) != 0) { + struct sockaddr_in peer; + int size = sizeof peer; + + if (getpeername(statp->_vcsock, + (struct sockaddr *)&peer, &size) < 0 || + !sock_eq(&peer, nsap)) { + res_nclose(statp); + statp->_flags &= ~RES_F_VC; + } } + + if (statp->_vcsock < 0 || (statp->_flags & RES_F_VC) == 0) { + if (statp->_vcsock >= 0) + res_nclose(statp); + + statp->_vcsock = socket(PF_INET, SOCK_STREAM, 0); + if (statp->_vcsock > highestFD) { + res_nclose(statp); + errno = ENOTSOCK; + } + if (statp->_vcsock < 0) { + *terrno = errno; + Perror(statp, stderr, "socket(vc)", errno); + return (-1); + } + errno = 0; + if (connect(statp->_vcsock, (struct sockaddr *)nsap, + sizeof *nsap) < 0) { + *terrno = errno; + Aerror(statp, stderr, "connect/vc", errno, *nsap); + res_nclose(statp); + return (0); + } + statp->_flags |= RES_F_VC; + } + + /* + * Send length & message + */ + putshort((u_short)buflen, (u_char*)&len); + iov[0] = evConsIovec(&len, INT16SZ); + iov[1] = evConsIovec((void*)buf, buflen); + if (writev(statp->_vcsock, iov, 2) != (INT16SZ + buflen)) { + *terrno = errno; + Perror(statp, stderr, "write failed", errno); + res_nclose(statp); + return (0); + } + /* + * Receive length & response + */ + read_len: + cp = ans; + len = INT16SZ; + while ((n = read(statp->_vcsock, (char *)cp, (int)len)) > 0) { + cp += n; + if ((len -= n) <= 0) + break; + } + if (n <= 0) { + *terrno = errno; + Perror(statp, stderr, "read failed", errno); + res_nclose(statp); + /* + * A long running process might get its TCP + * connection reset if the remote server was + * restarted. Requery the server instead of + * trying a new one. When there is only one + * server, this means that a query might work + * instead of failing. We only allow one reset + * per query to prevent looping. + */ + if (*terrno == ECONNRESET && !connreset) { + connreset = 1; + res_nclose(statp); + goto same_ns; + } + res_nclose(statp); + return (0); + } + resplen = ns_get16(ans); + if (resplen > anssiz) { + Dprint(statp->options & RES_DEBUG, + (stdout, ";; response truncated\n") + ); + truncating = 1; + len = anssiz; + } else + len = resplen; + if (len < HFIXEDSZ) { + /* + * Undersized message. + */ + Dprint(statp->options & RES_DEBUG, + (stdout, ";; undersized: %d\n", len)); + *terrno = EMSGSIZE; + res_nclose(statp); + return (0); + } + cp = ans; + while (len != 0 && (n = read(statp->_vcsock, (char *)cp, (int)len)) > 0){ + cp += n; + len -= n; + } + if (n <= 0) { + *terrno = errno; + Perror(statp, stderr, "read(vc)", errno); + res_nclose(statp); + return (0); + } + if (truncating) { + /* + * Flush rest of answer so connection stays in synch. + */ + anhp->tc = 1; + len = resplen - anssiz; + while (len != 0) { + char junk[PACKETSZ]; + + n = read(statp->_vcsock, junk, + (len > sizeof junk) ? sizeof junk : len); + if (n > 0) + len -= n; + else + break; + } + } + /* + * If the calling applicating has bailed out of + * a previous call and failed to arrange to have + * the circuit closed or the server has got + * itself confused, then drop the packet and + * wait for the correct one. + */ + if (hp->id != anhp->id) { + DprintQ((statp->options & RES_DEBUG) || + (statp->pfcode & RES_PRF_REPLY), + (stdout, ";; old answer (unexpected):\n"), + ans, (resplen > anssiz) ? anssiz: resplen); + goto read_len; + } + + /* + * All is well, or the error is fatal. Signal that the + * next nameserver ought not be tried. + */ + return (resplen); +} + +static int +send_dg(res_state statp, + const u_char *buf, int buflen, u_char *ans, int anssiz, + int *terrno, int ns, int *v_circuit, int *gotsomewhere) +{ + const HEADER *hp = (HEADER *) buf; + HEADER *anhp = (HEADER *) ans; + const struct sockaddr_in *nsap = &statp->nsaddr_list[ns]; + struct timespec now, timeout, finish; + fd_set dsmask; + struct sockaddr_in from; + int fromlen, resplen, seconds, n, s; + + if (EXT(statp).nssocks[ns] == -1) { + EXT(statp).nssocks[ns] = socket(PF_INET, SOCK_DGRAM, 0); + if (EXT(statp).nssocks[ns] > highestFD) { + res_nclose(statp); + errno = ENOTSOCK; + } + if (EXT(statp).nssocks[ns] < 0) { + *terrno = errno; + Perror(statp, stderr, "socket(dg)", errno); + return (-1); + } +#ifndef CANNOT_CONNECT_DGRAM + /* + * On a 4.3BSD+ machine (client and server, + * actually), sending to a nameserver datagram + * port with no nameserver will cause an + * ICMP port unreachable message to be returned. + * If our datagram socket is "connected" to the + * server, we get an ECONNREFUSED error on the next + * socket operation, and select returns if the + * error message is received. We can thus detect + * the absence of a nameserver without timing out. + */ + if (connect(EXT(statp).nssocks[ns], (struct sockaddr *)nsap, + sizeof *nsap) < 0) { + Aerror(statp, stderr, "connect(dg)", errno, *nsap); + res_nclose(statp); + return (0); + } +#endif /* !CANNOT_CONNECT_DGRAM */ + Dprint(statp->options & RES_DEBUG, + (stdout, ";; new DG socket\n")) + } + s = EXT(statp).nssocks[ns]; +#ifndef CANNOT_CONNECT_DGRAM + if (send(s, (char*)buf, buflen, 0) != buflen) { + Perror(statp, stderr, "send", errno); + res_nclose(statp); + return (0); + } +#else /* !CANNOT_CONNECT_DGRAM */ + if (sendto(s, (char*)buf, buflen, 0, + (struct sockaddr *)nsap, sizeof *nsap) != buflen) + { + Aerror(statp, stderr, "sendto", errno, *nsap); + res_nclose(statp); + return (0); + } +#endif /* !CANNOT_CONNECT_DGRAM */ + + /* + * Wait for reply. + */ + seconds = (statp->retrans << ns); + if (ns > 0) + seconds /= statp->nscount; + if (seconds <= 0) + seconds = 1; + now = evNowTime(); + timeout = evConsTime(seconds, 0); + finish = evAddTime(now, timeout); + wait: + FD_ZERO(&dsmask); + FD_SET(s, &dsmask); + n = pselect(s + 1, &dsmask, NULL, NULL, &timeout, NULL); + if (n == 0) { + Dprint(statp->options & RES_DEBUG, (stdout, ";; timeout\n")); + *gotsomewhere = 1; + return (0); + } + if (n < 0) { + if (errno == EINTR) { + now = evNowTime(); + if (evCmpTime(finish, now) > 0) { + timeout = evSubTime(finish, now); + goto wait; + } + } + Perror(statp, stderr, "select", errno); + res_nclose(statp); + return (0); + } + errno = 0; + fromlen = sizeof(struct sockaddr_in); + resplen = recvfrom(s, (char*)ans, anssiz,0, + (struct sockaddr *)&from, &fromlen); + if (resplen <= 0) { + Perror(statp, stderr, "recvfrom", errno); + res_nclose(statp); + return (0); + } + *gotsomewhere = 1; + if (resplen < HFIXEDSZ) { + /* + * Undersized message. + */ + Dprint(statp->options & RES_DEBUG, + (stdout, ";; undersized: %d\n", + resplen)); + *terrno = EMSGSIZE; + res_nclose(statp); + return (0); + } + if (hp->id != anhp->id) { + /* + * response from old query, ignore it. + * XXX - potential security hazard could + * be detected here. + */ + DprintQ((statp->options & RES_DEBUG) || + (statp->pfcode & RES_PRF_REPLY), + (stdout, ";; old answer:\n"), + ans, (resplen > anssiz) ? anssiz : resplen); + goto wait; + } + if (!(statp->options & RES_INSECURE1) && + !res_ourserver_p(statp, &from)) { + /* + * response from wrong server? ignore it. + * XXX - potential security hazard could + * be detected here. + */ + DprintQ((statp->options & RES_DEBUG) || + (statp->pfcode & RES_PRF_REPLY), + (stdout, ";; not our server:\n"), + ans, (resplen > anssiz) ? anssiz : resplen); + goto wait; + } + if (!(statp->options & RES_INSECURE2) && + !res_queriesmatch(buf, buf + buflen, + ans, ans + anssiz)) { + /* + * response contains wrong query? ignore it. + * XXX - potential security hazard could + * be detected here. + */ + DprintQ((statp->options & RES_DEBUG) || + (statp->pfcode & RES_PRF_REPLY), + (stdout, ";; wrong query name:\n"), + ans, (resplen > anssiz) ? anssiz : resplen); + goto wait; + } + if (anhp->rcode == SERVFAIL || + anhp->rcode == NOTIMP || + anhp->rcode == REFUSED) { + DprintQ(statp->options & RES_DEBUG, + (stdout, "server rejected query:\n"), + ans, (resplen > anssiz) ? anssiz : resplen); + res_nclose(statp); + /* don't retry if called from dig */ + if (!statp->pfcode) + return (0); + } + if (!(statp->options & RES_IGNTC) && anhp->tc) { + /* + * To get the rest of answer, + * use TCP with same server. + */ + Dprint(statp->options & RES_DEBUG, + (stdout, ";; truncated answer\n")); + *v_circuit = 1; + res_nclose(statp); + return (1); + } + /* + * All is well, or the error is fatal. Signal that the + * next nameserver ought not be tried. + */ + return (resplen); +} + +static void +Aerror(const res_state statp, FILE *file, const char *string, int error, + struct sockaddr_in address) +{ + int save = errno; + + if ((statp->options & RES_DEBUG) != 0) { + char tmp[sizeof "255.255.255.255"]; + + fprintf(file, "res_send: %s ([%s].%u): %s\n", + string, + inet_ntop(address.sin_family, &address.sin_addr, + tmp, sizeof tmp), + ntohs(address.sin_port), + strerror(error)); + } + errno = save; +} + +static void +Perror(const res_state statp, FILE *file, const char *string, int error) { + int save = errno; + + if ((statp->options & RES_DEBUG) != 0) + fprintf(file, "res_send: %s: %s\n", + string, strerror(error)); + errno = save; } -/* Private */ static int -cmpsock(struct sockaddr_in *a1, struct sockaddr_in *a2) { +sock_eq(struct sockaddr_in *a1, struct sockaddr_in *a2) { return ((a1->sin_family == a2->sin_family) && (a1->sin_port == a2->sin_port) && (a1->sin_addr.s_addr == a2->sin_addr.s_addr)); @@ -866,8 +836,7 @@ cmpsock(struct sockaddr_in *a1, struct sockaddr_in *a2) { /* XXX needs to move to the porting library. */ static int pselect(int nfds, void *rfds, void *wfds, void *efds, - struct timespec *tsp, - const sigset_t *sigmask) + struct timespec *tsp, const sigset_t *sigmask) { struct timeval tv, *tvp; sigset_t sigs; diff --git a/contrib/bind/port/freebsd/include/port_before.h b/contrib/bind/port/freebsd/include/port_before.h index d713050..2791652 100644 --- a/contrib/bind/port/freebsd/include/port_before.h +++ b/contrib/bind/port/freebsd/include/port_before.h @@ -2,6 +2,7 @@ #define WANT_IRS_PW #define WANT_IRS_GR #define SIG_FN void +#define HAS_PTHREADS #define ts_sec tv_sec #define ts_nsec tv_nsec @@ -12,3 +13,91 @@ #if defined (__FreeBSD__) && __FreeBSD__>=3 #define SETPWENT_VOID #endif + +#include <sys/types.h> + +#define GROUP_R_RETURN struct group * +#define GROUP_R_SET_RETURN void +#undef GROUP_R_SET_RESULT /*empty*/ +#define GROUP_R_END_RETURN void +#define GROUP_R_END_RESULT(x) /*empty*/ +#define GROUP_R_ARGS char *buf, int buflen +#undef GROUP_R_ENT_ARGS /*empty*/ +#define GROUP_R_OK gptr +#define GROUP_R_BAD NULL + +#define HOST_R_RETURN struct hostent * +#define HOST_R_SET_RETURN void +#undef HOST_R_SET_RESULT /*empty*/ +#define HOST_R_END_RETURN void +#define HOST_R_END_RESULT(x) /*empty*/ +#define HOST_R_ARGS char *buf, int buflen, int *h_errnop +#undef HOST_R_ENT_ARGS /*empty*/ +#define HOST_R_COPY buf, buflen +#define HOST_R_COPY_ARGS char *buf, int buflen +#define HOST_R_ERRNO *h_errnop = h_errno +#define HOST_R_OK hptr +#define HOST_R_BAD NULL + +#define NET_R_RETURN struct netent * +#define NET_R_SET_RETURN void +#undef NET_R_SET_RESULT /*empty*/ +#define NET_R_END_RETURN void +#define NET_R_END_RESULT(x) /*empty*/ +#define NET_R_ARGS char *buf, int buflen +#undef NET_R_ENT_ARGS /*empty*/ +#define NET_R_COPY buf, buflen +#define NET_R_COPY_ARGS NET_R_ARGS +#define NET_R_OK nptr +#define NET_R_BAD NULL + +#define NGR_R_RETURN int +#define NGR_R_SET_RETURN void +#undef NGR_R_SET_RESULT /*empty*/ +#define NGR_R_END_RETURN void +#undef NGR_R_END_RESULT /*empty*/ +#define NGR_R_ARGS char *buf, int buflen +#undef NGR_R_ENT_ARGS /*empty*/ +#define NGR_R_COPY buf, buflen +#define NGR_R_COPY_ARGS NGR_R_ARGS +#define NGR_R_OK 1 +#define NGR_R_BAD (0) + +#define PROTO_R_RETURN struct protoent * +#define PROTO_R_SET_RETURN void +#undef PROTO_R_SET_RESULT /*empty*/ +#define PROTO_R_END_RETURN void +#define PROTO_R_END_RESULT(x) /*empty*/ +#define PROTO_R_ARGS char *buf, int buflen +#undef PROTO_R_ENT_ARGS /*empty*/ +#define PROTO_R_COPY buf, buflen +#define PROTO_R_COPY_ARGS PROTO_R_ARGS +#define PROTO_R_OK pptr +#define PROTO_R_BAD NULL + +#define PASS_R_RETURN struct passwd * +#define PASS_R_SET_RETURN void +#undef PASS_R_SET_RESULT /*empty*/ +#define PASS_R_END_RETURN void +#define PASS_R_END_RESULT(x) /*empty*/ +#define PASS_R_ARGS char *buf, int buflen +#undef PASS_R_ENT_ARGS /*empty*/ +#define PASS_R_COPY buf, buflen +#define PASS_R_COPY_ARGS PASS_R_ARGS +#define PASS_R_OK pwptr +#define PASS_R_BAD NULL + +#define SERV_R_RETURN struct servent * +#define SERV_R_SET_RETURN void +#undef SERV_R_SET_RESULT /*empty*/ +#define SERV_R_END_RETURN void +#define SERV_R_END_RESULT(x) /*empty*/ +#define SERV_R_ARGS char *buf, int buflen +#undef SERV_R_ENT_ARGS /*empty*/ +#define SERV_R_COPY buf, buflen +#define SERV_R_COPY_ARGS SERV_R_ARGS +#define SERV_R_OK sptr +#define SERV_R_BAD NULL + +#define IRS_LCL_SV_DB + diff --git a/contrib/bind/port/systype b/contrib/bind/port/systype index 56d5e26..b022651 100755 --- a/contrib/bind/port/systype +++ b/contrib/bind/port/systype @@ -12,7 +12,7 @@ case $cachefile in *) cachefile=`pwd`/$cachefile ;; esac -cd `dirname $0` > /dev/null +cd `dirname $0` for systype in [a-z]*; do if [ -f $systype/probe ]; then if sh $systype/probe; then |