summaryrefslogtreecommitdiff
path: root/usr.sbin/bind/bin/dnssec
diff options
context:
space:
mode:
authorJakob Schlyter <jakob@cvs.openbsd.org>2003-01-20 21:07:55 +0000
committerJakob Schlyter <jakob@cvs.openbsd.org>2003-01-20 21:07:55 +0000
commitdcaedb23a762cacc9125d2056adca98bbec67e16 (patch)
tree8b2707b30928ce97b145ca6f3c102c662090d26e /usr.sbin/bind/bin/dnssec
parentcc53f94652b511572cc20f91f0356f1774e7d02c (diff)
ISC BIND version 9.2.2rc1
Diffstat (limited to 'usr.sbin/bind/bin/dnssec')
-rw-r--r--usr.sbin/bind/bin/dnssec/Makefile.in97
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-keygen.8167
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-keygen.c403
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-keygen.docbook327
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-keygen.html572
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-makekeyset.8112
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-makekeyset.c467
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-makekeyset.docbook233
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-makekeyset.html404
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-signkey.8107
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-signkey.c472
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-signkey.docbook237
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-signkey.html404
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-signzone.8154
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-signzone.c1860
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-signzone.docbook325
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssec-signzone.html553
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssectool.c260
-rw-r--r--usr.sbin/bind/bin/dnssec/dnssectool.h73
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/keygen.dsp107
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/keygen.dsw29
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/keygen.mak227
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/makekeyset.dsp107
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/makekeyset.dsw29
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/makekeyset.mak227
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/nsupdate.dsp103
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/nsupdate.dsw29
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/signkey.dsp107
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/signkey.dsw29
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/signkey.mak227
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/signzone.dsp107
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/signzone.dsw29
-rw-r--r--usr.sbin/bind/bin/dnssec/win32/signzone.mak227
33 files changed, 8811 insertions, 0 deletions
diff --git a/usr.sbin/bind/bin/dnssec/Makefile.in b/usr.sbin/bind/bin/dnssec/Makefile.in
new file mode 100644
index 00000000000..8f986102c2a
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/Makefile.in
@@ -0,0 +1,97 @@
+# Copyright (C) 2000, 2001 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
+# copyright notice and this permission notice appear in all copies.
+#
+# THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+# DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+# INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+# INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+# FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+# NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+# WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+
+# $ISC: Makefile.in,v 1.19 2001/06/01 00:44:58 bwelling Exp $
+
+srcdir = @srcdir@
+VPATH = @srcdir@
+top_srcdir = @top_srcdir@
+
+@BIND9_VERSION@
+
+@BIND9_INCLUDES@
+
+CINCLUDES = ${DNS_INCLUDES} ${ISC_INCLUDES}
+
+CDEFINES =
+CWARNINGS =
+
+DNSLIBS = ../../lib/dns/libdns.@A@ @DNS_OPENSSL_LIBS@ @DNS_GSSAPI_LIBS@
+ISCLIBS = ../../lib/isc/libisc.@A@
+
+DNSDEPLIBS = ../../lib/dns/libdns.@A@
+ISCDEPLIBS = ../../lib/isc/libisc.@A@
+
+DEPLIBS = ${DNSDEPLIBS} ${ISCDEPLIBS}
+
+LIBS = ${DNSLIBS} ${ISCLIBS} @LIBS@
+
+# Alphabetically
+TARGETS = dnssec-keygen \
+ dnssec-makekeyset \
+ dnssec-signkey \
+ dnssec-signzone
+
+OBJS = dnssectool.@O@
+
+SRCS = dnssec-keygen.c dnssec-makekeyset.c \
+ dnssec-signkey.c dnssec-signzone.c \
+ dnssectool.c
+
+MANPAGES = dnssec-keygen.8 \
+ dnssec-makekeyset.8 \
+ dnssec-signkey.8 \
+ dnssec-signzone.8
+
+HTMLPAGES = dnssec-keygen.html \
+ dnssec-makekeyset.html \
+ dnssec-signkey.html \
+ dnssec-signzone.html
+
+MANOBJS = ${MANPAGES} ${HTMLPAGES}
+
+@BIND9_MAKE_RULES@
+
+dnssec-keygen: dnssec-keygen.@O@ ${OBJS} ${DEPLIBS}
+ ${LIBTOOL} ${PURIFY} ${CC} ${CFLAGS} -o $@ dnssec-keygen.@O@ ${OBJS} ${LIBS}
+
+dnssec-makekeyset: dnssec-makekeyset.@O@ ${OBJS} ${DEPLIBS}
+ ${LIBTOOL} ${PURIFY} ${CC} ${CFLAGS} -o $@ dnssec-makekeyset.@O@ ${OBJS} ${LIBS}
+
+dnssec-signkey: dnssec-signkey.@O@ ${OBJS} ${DEPLIBS}
+ ${LIBTOOL} ${PURIFY} ${CC} ${CFLAGS} -o $@ dnssec-signkey.@O@ ${OBJS} ${LIBS}
+
+dnssec-signzone.@O@: dnssec-signzone.c
+ ${LIBTOOL} ${PURIFY} ${CC} ${ALL_CFLAGS} -DVERSION=\"${VERSION}\" -c $<
+
+dnssec-signzone: dnssec-signzone.@O@ ${OBJS} ${DEPLIBS}
+ ${LIBTOOL} ${PURIFY} ${CC} ${CFLAGS} -o $@ dnssec-signzone.@O@ ${OBJS} ${LIBS}
+
+doc man:: ${MANOBJS}
+
+docclean manclean maintainer-clean::
+ rm -f ${MANOBJS}
+
+installdirs:
+ $(SHELL) ${top_srcdir}/mkinstalldirs ${DESTDIR}${sbindir}
+ $(SHELL) ${top_srcdir}/mkinstalldirs ${DESTDIR}${mandir}/man8
+
+install:: ${TARGETS} installdirs
+ for t in ${TARGETS}; do ${LIBTOOL} ${INSTALL_PROGRAM} $$t ${DESTDIR}${sbindir}; done
+ for m in ${MANPAGES}; do ${INSTALL_DATA} ${srcdir}/$$m ${DESTDIR}${mandir}/man8; done
+
+clean distclean::
+ rm -f ${TARGETS}
+
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-keygen.8 b/usr.sbin/bind/bin/dnssec/dnssec-keygen.8
new file mode 100644
index 00000000000..ae16469db40
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-keygen.8
@@ -0,0 +1,167 @@
+.\"
+.\" Copyright (C) 2000, 2001 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
+.\" copyright notice and this permission notice appear in all copies.
+.\"
+.\" THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+.\" DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+.\" INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+.\" INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+.\" FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+.\" NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+.\" WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+.\"
+.TH "DNSSEC-KEYGEN" "8" "June 30, 2000" "BIND9" ""
+.SH NAME
+dnssec-keygen \- DNSSEC key generation tool
+.SH SYNOPSIS
+.sp
+\fBdnssec-keygen\fR \fB-a \fIalgorithm\fB\fR \fB-b \fIkeysize\fB\fR \fB-n \fInametype\fB\fR [ \fB-c \fIclass\fB\fR ] [ \fB-e\fR ] [ \fB-g \fIgenerator\fB\fR ] [ \fB-h\fR ] [ \fB-p \fIprotocol\fB\fR ] [ \fB-r \fIrandomdev\fB\fR ] [ \fB-s \fIstrength\fB\fR ] [ \fB-t \fItype\fB\fR ] [ \fB-v \fIlevel\fB\fR ] \fBname\fR
+.SH "DESCRIPTION"
+.PP
+\fBdnssec-keygen\fR generates keys for DNSSEC
+(Secure DNS), as defined in RFC 2535. It can also generate
+keys for use with TSIG (Transaction Signatures), as
+defined in RFC 2845.
+.SH "OPTIONS"
+.TP
+\fB-a \fIalgorithm\fB\fR
+Selects the cryptographic algorithm. The value of
+\fBalgorithm\fR must be one of RSAMD5 or RSA,
+DSA, DH (Diffie Hellman), or HMAC-MD5. These values
+are case insensitive.
+
+Note that for DNSSEC, DSA is a mandatory to implement algorithm,
+and RSA is recommended. For TSIG, HMAC-MD5 is mandatory.
+.TP
+\fB-b \fIkeysize\fB\fR
+Specifies the number of bits in the key. The choice of key
+size depends on the algorithm used. RSA keys must be between
+512 and 2048 bits. Diffie Hellman keys must be between
+128 and 4096 bits. DSA keys must be between 512 and 1024
+bits and an exact multiple of 64. HMAC-MD5 keys must be
+between 1 and 512 bits.
+.TP
+\fB-n \fInametype\fB\fR
+Specifies the owner type of the key. The value of
+\fBnametype\fR must either be ZONE (for a DNSSEC
+zone key), HOST or ENTITY (for a key associated with a host),
+or USER (for a key associated with a user). These values are
+case insensitive.
+.TP
+\fB-c \fIclass\fB\fR
+Indicates that the DNS record containing the key should have
+the specified class. If not specified, class IN is used.
+.TP
+\fB-e\fR
+If generating an RSA key, use a large exponent.
+.TP
+\fB-g \fIgenerator\fB\fR
+If generating a Diffie Hellman key, use this generator.
+Allowed values are 2 and 5. If no generator
+is specified, a known prime from RFC 2539 will be used
+if possible; otherwise the default is 2.
+.TP
+\fB-h\fR
+Prints a short summary of the options and arguments to
+\fBdnssec-keygen\fR.
+.TP
+\fB-p \fIprotocol\fB\fR
+Sets the protocol value for the generated key. The protocol
+is a number between 0 and 255. The default is 2 (email) for
+keys of type USER and 3 (DNSSEC) for all other key types.
+Other possible values for this argument are listed in
+RFC 2535 and its successors.
+.TP
+\fB-r \fIrandomdev\fB\fR
+Specifies the source of randomness. If the operating
+system does not provide a \fI/dev/random\fR
+or equivalent device, the default source of randomness
+is keyboard input. \fIrandomdev\fR specifies
+the name of a character device or file containing random
+data to be used instead of the default. The special value
+\fIkeyboard\fR indicates that keyboard
+input should be used.
+.TP
+\fB-s \fIstrength\fB\fR
+Specifies the strength value of the key. The strength is
+a number between 0 and 15, and currently has no defined
+purpose in DNSSEC.
+.TP
+\fB-t \fItype\fB\fR
+Indicates the use of the key. \fBtype\fR must be
+one of AUTHCONF, NOAUTHCONF, NOAUTH, or NOCONF. The default
+is AUTHCONF. AUTH refers to the ability to authenticate
+data, and CONF the ability to encrypt data.
+.TP
+\fB-v \fIlevel\fB\fR
+Sets the debugging level.
+.SH "GENERATED KEYS"
+.PP
+When \fBdnssec-keygen\fR completes successfully,
+it prints a string of the form \fIKnnnn.+aaa+iiiii\fR
+to the standard output. This is an identification string for
+the key it has generated. These strings can be used as arguments
+to \fBdnssec-makekeyset\fR.
+.TP 0.2i
+\(bu
+\fInnnn\fR is the key name.
+.TP 0.2i
+\(bu
+\fIaaa\fR is the numeric representation of the
+algorithm.
+.TP 0.2i
+\(bu
+\fIiiiii\fR is the key identifier (or footprint).
+.PP
+\fBdnssec-keygen\fR creates two file, with names based
+on the printed string. \fIKnnnn.+aaa+iiiii.key\fR
+contains the public key, and
+\fIKnnnn.+aaa+iiiii.private\fR contains the private
+key.
+.PP
+.PP
+The \fI.key\fR file contains a DNS KEY record that
+can be inserted into a zone file (directly or with a $INCLUDE
+statement).
+.PP
+.PP
+The \fI.private\fR file contains algorithm specific
+fields. For obvious security reasons, this file does not have
+general read permission.
+.PP
+.PP
+Both \fI.key\fR and \fI.private\fR
+files are generated for symmetric encryption algorithm such as
+HMAC-MD5, even though the public and private key are equivalent.
+.PP
+.SH "EXAMPLE"
+.PP
+To generate a 768-bit DSA key for the domain
+\fBexample.com\fR, the following command would be
+issued:
+.PP
+\fBdnssec-keygen -a DSA -b 768 -n ZONE example.com\fR
+.PP
+The command would print a string of the form:
+.PP
+\fBKexample.com.+003+26160\fR
+.PP
+In this example, \fBdnssec-keygen\fR creates
+the files \fIKexample.com.+003+26160.key\fR and
+\fIKexample.com.+003+26160.private\fR
+.SH "SEE ALSO"
+.PP
+\fBdnssec-makekeyset\fR(8),
+\fBdnssec-signkey\fR(8),
+\fBdnssec-signzone\fR(8),
+\fIBIND 9 Administrator Reference Manual\fR,
+\fIRFC 2535\fR,
+\fIRFC 2845\fR,
+\fIRFC 2539\fR.
+.SH "AUTHOR"
+.PP
+Internet Software Consortium
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-keygen.c b/usr.sbin/bind/bin/dnssec/dnssec-keygen.c
new file mode 100644
index 00000000000..b4101bf87fb
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-keygen.c
@@ -0,0 +1,403 @@
+/*
+ * Portions Copyright (C) 2000, 2001 Internet Software Consortium.
+ * Portions Copyright (C) 1995-2000 by Network Associates, Inc.
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM AND
+ * NETWORK ASSOCIATES DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS. IN NO EVENT SHALL INTERNET SOFTWARE CONSORTIUM OR NETWORK
+ * ASSOCIATES BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF
+ * USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
+ * OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/* $ISC: dnssec-keygen.c,v 1.48.2.1 2001/10/05 00:21:44 bwelling Exp $ */
+
+#include <config.h>
+
+#include <stdlib.h>
+
+#include <isc/buffer.h>
+#include <isc/commandline.h>
+#include <isc/entropy.h>
+#include <isc/mem.h>
+#include <isc/region.h>
+#include <isc/string.h>
+#include <isc/util.h>
+
+#include <dns/fixedname.h>
+#include <dns/keyvalues.h>
+#include <dns/log.h>
+#include <dns/name.h>
+#include <dns/rdataclass.h>
+#include <dns/result.h>
+#include <dns/secalg.h>
+
+#include <dst/dst.h>
+
+#include "dnssectool.h"
+
+#define MAX_RSA 4096 /* should be long enough... */
+
+const char *program = "dnssec-keygen";
+int verbose;
+
+static isc_boolean_t
+dsa_size_ok(int size) {
+ return (ISC_TF(size >= 512 && size <= 1024 && size % 64 == 0));
+}
+
+static void
+usage(void) {
+ fprintf(stderr, "Usage:\n");
+ fprintf(stderr, " %s -a alg -b bits -n type [options] name\n\n",
+ program);
+ fprintf(stderr, "Required options:\n");
+ fprintf(stderr, " -a algorithm: RSA | RSAMD5 | DH | DSA | HMAC-MD5"
+ "\n");
+ fprintf(stderr, " -b key size, in bits:\n");
+ fprintf(stderr, " RSA:\t\t[512..%d]\n", MAX_RSA);
+ fprintf(stderr, " DH:\t\t[128..4096]\n");
+ fprintf(stderr, " DSA:\t\t[512..1024] and divisible by 64\n");
+ fprintf(stderr, " HMAC-MD5:\t[1..512]\n");
+ fprintf(stderr, " -n nametype: ZONE | HOST | ENTITY | USER\n");
+ fprintf(stderr, " name: owner of the key\n");
+ fprintf(stderr, "Other options:\n");
+ fprintf(stderr, " -c class (default: IN)\n");
+ fprintf(stderr, " -e use large exponent (RSA only)\n");
+ fprintf(stderr, " -g use specified generator (DH only)\n");
+ fprintf(stderr, " -t type: AUTHCONF | NOAUTHCONF | NOAUTH | NOCONF "
+ "(default: AUTHCONF)\n");
+ fprintf(stderr, " -p protocol value "
+ "(default: 2 [email] for USER, 3 [dnssec] otherwise)\n");
+ fprintf(stderr, " -s strength value this key signs DNS records "
+ "with (default: 0)\n");
+ fprintf(stderr, " -r randomdev (a file containing random data)\n");
+ fprintf(stderr, " -v verbose level\n");
+ fprintf(stderr, "Output:\n");
+ fprintf(stderr, " K<name>+<alg>+<id>.key, "
+ "K<name>+<alg>+<id>.private\n");
+
+ exit (-1);
+}
+
+int
+main(int argc, char **argv) {
+ char *algname = NULL, *nametype = NULL, *type = NULL;
+ char *classname = NULL;
+ char *randomfile = NULL;
+ char *prog, *endp;
+ dst_key_t *key = NULL, *oldkey;
+ dns_fixedname_t fname;
+ dns_name_t *name;
+ isc_uint16_t flags = 0;
+ dns_secalg_t alg;
+ isc_boolean_t conflict = ISC_FALSE, null_key = ISC_FALSE;
+ isc_mem_t *mctx = NULL;
+ int ch, rsa_exp = 0, generator = 0, param = 0;
+ int protocol = -1, size = -1, signatory = 0;
+ isc_result_t ret;
+ isc_textregion_t r;
+ char filename[255];
+ isc_buffer_t buf;
+ isc_log_t *log = NULL;
+ isc_entropy_t *ectx = NULL;
+ dns_rdataclass_t rdclass;
+
+ RUNTIME_CHECK(isc_mem_create(0, 0, &mctx) == ISC_R_SUCCESS);
+
+ if ((prog = strrchr(argv[0],'/')) == NULL)
+ prog = isc_mem_strdup(mctx, argv[0]);
+ else
+ prog = isc_mem_strdup(mctx, ++prog);
+ if (prog == NULL)
+ fatal("out of memory");
+
+ if (argc == 1)
+ usage();
+
+ dns_result_register();
+
+ while ((ch = isc_commandline_parse(argc, argv,
+ "a:b:c:eg:n:t:p:s:hr:v:")) != -1)
+ {
+ switch (ch) {
+ case 'a':
+ algname = isc_commandline_argument;
+ break;
+ case 'b':
+ size = strtol(isc_commandline_argument, &endp, 10);
+ if (*endp != '\0' || size < 0)
+ fatal("-b requires a non-negative number");
+ break;
+ case 'c':
+ classname = isc_commandline_argument;
+ break;
+ case 'e':
+ rsa_exp = 1;
+ break;
+ case 'g':
+ generator = strtol(isc_commandline_argument,
+ &endp, 10);
+ if (*endp != '\0' || generator <= 0)
+ fatal("-g requires a positive number");
+ break;
+ case 'n':
+ nametype = isc_commandline_argument;
+ if (nametype == NULL)
+ fatal("out of memory");
+ break;
+ case 't':
+ type = isc_commandline_argument;
+ if (type == NULL)
+ fatal("out of memory");
+ break;
+ case 'p':
+ protocol = strtol(isc_commandline_argument, &endp, 10);
+ if (*endp != '\0' || protocol < 0 || protocol > 255)
+ fatal("-p must be followed by a number "
+ "[0..255]");
+ break;
+ case 's':
+ signatory = strtol(isc_commandline_argument,
+ &endp, 10);
+ if (*endp != '\0' || signatory < 0 || signatory > 15)
+ fatal("-s must be followed by a number "
+ "[0..15]");
+ break;
+ case 'r':
+ randomfile = isc_commandline_argument;
+ break;
+ case 'v':
+ endp = NULL;
+ verbose = strtol(isc_commandline_argument, &endp, 0);
+ if (*endp != '\0')
+ fatal("-v must be followed by a number");
+ break;
+
+ case 'h':
+ usage();
+ default:
+ fprintf(stderr, "%s: invalid argument -%c\n",
+ program, ch);
+ usage();
+ }
+ }
+
+ setup_entropy(mctx, randomfile, &ectx);
+ ret = dst_lib_init(mctx, ectx,
+ ISC_ENTROPY_BLOCKING | ISC_ENTROPY_GOODONLY);
+ if (ret != ISC_R_SUCCESS)
+ fatal("could not initialize dst");
+
+ setup_logging(verbose, mctx, &log);
+
+ if (argc < isc_commandline_index + 1)
+ fatal("the key name was not specified");
+ if (argc > isc_commandline_index + 1)
+ fatal("extraneous arguments");
+
+ if (algname == NULL)
+ fatal("no algorithm was specified");
+ if (strcasecmp(algname, "RSA") == 0)
+ alg = DNS_KEYALG_RSA;
+ else if (strcasecmp(algname, "HMAC-MD5") == 0)
+ alg = DST_ALG_HMACMD5;
+ else {
+ r.base = algname;
+ r.length = strlen(algname);
+ ret = dns_secalg_fromtext(&alg, &r);
+ if (ret != ISC_R_SUCCESS)
+ fatal("unknown algorithm %s", algname);
+ }
+
+ if (type != NULL) {
+ if (strcasecmp(type, "NOAUTH") == 0)
+ flags |= DNS_KEYTYPE_NOAUTH;
+ else if (strcasecmp(type, "NOCONF") == 0)
+ flags |= DNS_KEYTYPE_NOCONF;
+ else if (strcasecmp(type, "NOAUTHCONF") == 0) {
+ flags |= (DNS_KEYTYPE_NOAUTH | DNS_KEYTYPE_NOCONF);
+ if (size < 0)
+ size = 0;
+ }
+ else if (strcasecmp(type, "AUTHCONF") == 0)
+ /* nothing */;
+ else
+ fatal("invalid type %s", type);
+ }
+
+ if (size < 0)
+ fatal("key size not specified (-b option)");
+
+ switch (alg) {
+ case DNS_KEYALG_RSA:
+ if (size != 0 && (size < 512 || size > MAX_RSA))
+ fatal("RSA key size %d out of range", size);
+ break;
+ case DNS_KEYALG_DH:
+ if (size != 0 && (size < 128 || size > 4096))
+ fatal("DH key size %d out of range", size);
+ break;
+ case DNS_KEYALG_DSA:
+ if (size != 0 && !dsa_size_ok(size))
+ fatal("Invalid DSS key size: %d", size);
+ break;
+ case DST_ALG_HMACMD5:
+ if (size < 1 || size > 512)
+ fatal("HMAC-MD5 key size %d out of range", size);
+ break;
+ }
+
+ if (alg != DNS_KEYALG_RSA && rsa_exp != 0)
+ fatal("specified RSA exponent without RSA");
+
+ if (alg != DNS_KEYALG_DH && generator != 0)
+ fatal("specified DH generator without DH");
+
+ if (nametype == NULL)
+ fatal("no nametype specified");
+ if (strcasecmp(nametype, "zone") == 0)
+ flags |= DNS_KEYOWNER_ZONE;
+ else if (strcasecmp(nametype, "host") == 0 ||
+ strcasecmp(nametype, "entity") == 0)
+ flags |= DNS_KEYOWNER_ENTITY;
+ else if (strcasecmp(nametype, "user") == 0)
+ flags |= DNS_KEYOWNER_USER;
+ else
+ fatal("invalid nametype %s", nametype);
+
+ if (classname != NULL) {
+ r.base = classname;
+ r.length = strlen(classname);
+ ret = dns_rdataclass_fromtext(&rdclass, &r);
+ if (ret != ISC_R_SUCCESS)
+ fatal("unknown class %s",classname);
+ } else
+ rdclass = dns_rdataclass_in;
+
+ flags |= signatory;
+
+ if (protocol == -1) {
+ if ((flags & DNS_KEYFLAG_OWNERMASK) == DNS_KEYOWNER_USER)
+ protocol = DNS_KEYPROTO_EMAIL;
+ else
+ protocol = DNS_KEYPROTO_DNSSEC;
+ }
+
+ if ((flags & DNS_KEYFLAG_TYPEMASK) == DNS_KEYTYPE_NOKEY) {
+ if (size > 0)
+ fatal("Specified null key with non-zero size");
+ if ((flags & DNS_KEYFLAG_SIGNATORYMASK) != 0)
+ fatal("Specified null key with signing authority");
+ }
+
+ dns_fixedname_init(&fname);
+ name = dns_fixedname_name(&fname);
+ isc_buffer_init(&buf, argv[isc_commandline_index],
+ strlen(argv[isc_commandline_index]));
+ isc_buffer_add(&buf, strlen(argv[isc_commandline_index]));
+ ret = dns_name_fromtext(name, &buf, dns_rootname, ISC_FALSE, NULL);
+ if (ret != ISC_R_SUCCESS)
+ fatal("Invalid key name %s: %s", argv[isc_commandline_index],
+ isc_result_totext(ret));
+
+ switch(alg) {
+ case DNS_KEYALG_RSA:
+ param = rsa_exp;
+ break;
+ case DNS_KEYALG_DH:
+ param = generator;
+ break;
+ case DNS_KEYALG_DSA:
+ case DST_ALG_HMACMD5:
+ param = 0;
+ break;
+ }
+
+ if ((flags & DNS_KEYFLAG_TYPEMASK) == DNS_KEYTYPE_NOKEY)
+ null_key = ISC_TRUE;
+
+ isc_buffer_init(&buf, filename, sizeof(filename) - 1);
+
+ do {
+ conflict = ISC_FALSE;
+ oldkey = NULL;
+
+ /* generate the key */
+ ret = dst_key_generate(name, alg, size, param, flags, protocol,
+ rdclass, mctx, &key);
+ isc_entropy_stopcallbacksources(ectx);
+
+ if (ret != ISC_R_SUCCESS) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ char algstr[ALG_FORMATSIZE];
+ dns_name_format(name, namestr, sizeof namestr);
+ alg_format(alg, algstr, sizeof algstr);
+ fatal("failed to generate key %s/%s: %s\n",
+ namestr, algstr, isc_result_totext(ret));
+ exit(-1);
+ }
+
+ /*
+ * Try to read a key with the same name, alg and id from disk.
+ * If there is one we must continue generating a new one
+ * unless we were asked to generate a null key, in which
+ * case we return failure.
+ */
+ ret = dst_key_fromfile(name, dst_key_id(key), alg,
+ DST_TYPE_PRIVATE, NULL, mctx, &oldkey);
+ /* do not overwrite an existing key */
+ if (ret == ISC_R_SUCCESS) {
+ dst_key_free(&oldkey);
+ conflict = ISC_TRUE;
+ if (null_key)
+ break;
+ }
+ if (conflict == ISC_TRUE) {
+ if (verbose > 0) {
+ isc_buffer_clear(&buf);
+ ret = dst_key_buildfilename(key, 0, NULL, &buf);
+ fprintf(stderr,
+ "%s: %s already exists, "
+ "generating a new key\n",
+ program, filename);
+ }
+ dst_key_free(&key);
+ }
+
+ } while (conflict == ISC_TRUE);
+
+ if (conflict)
+ fatal("cannot generate a null key when a key with id 0 "
+ "already exists");
+
+ ret = dst_key_tofile(key, DST_TYPE_PUBLIC | DST_TYPE_PRIVATE, NULL);
+ if (ret != ISC_R_SUCCESS) {
+ char keystr[KEY_FORMATSIZE];
+ key_format(key, keystr, sizeof keystr);
+ fatal("failed to write key %s: %s\n", keystr,
+ isc_result_totext(ret));
+ }
+
+ isc_buffer_clear(&buf);
+ ret = dst_key_buildfilename(key, 0, NULL, &buf);
+ printf("%s\n", filename);
+ isc_mem_free(mctx, prog);
+ dst_key_free(&key);
+
+ cleanup_logging(&log);
+ cleanup_entropy(&ectx);
+ dst_lib_destroy();
+ if (verbose > 10)
+ isc_mem_stats(mctx, stdout);
+ isc_mem_destroy(&mctx);
+
+ return (0);
+}
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-keygen.docbook b/usr.sbin/bind/bin/dnssec/dnssec-keygen.docbook
new file mode 100644
index 00000000000..8ee3ddad29d
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-keygen.docbook
@@ -0,0 +1,327 @@
+<!DOCTYPE refentry PUBLIC "-//OASIS//DTD DocBook V4.1//EN">
+<!--
+ - Copyright (C) 2001 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
+ - copyright notice and this permission notice appear in all copies.
+ -
+ - THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+ - DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+ - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+ - INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+ - INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+ - FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ - NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ - WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+-->
+
+<!-- $ISC: dnssec-keygen.docbook,v 1.3 2001/04/10 21:50:26 bwelling Exp $ -->
+
+<refentry>
+ <refentryinfo>
+ <date>June 30, 2000</date>
+ </refentryinfo>
+
+ <refmeta>
+ <refentrytitle><application>dnssec-keygen</application></refentrytitle>
+ <manvolnum>8</manvolnum>
+ <refmiscinfo>BIND9</refmiscinfo>
+ </refmeta>
+
+ <refnamediv>
+ <refname><application>dnssec-keygen</application></refname>
+ <refpurpose>DNSSEC key generation tool</refpurpose>
+ </refnamediv>
+
+ <refsynopsisdiv>
+ <cmdsynopsis>
+ <command>dnssec-keygen</command>
+ <arg choice="req">-a <replaceable class="parameter">algorithm</replaceable></arg>
+ <arg choice="req">-b <replaceable class="parameter">keysize</replaceable></arg>
+ <arg choice="req">-n <replaceable class="parameter">nametype</replaceable></arg>
+ <arg><option>-c <replaceable class="parameter">class</replaceable></option></arg>
+ <arg><option>-e</option></arg>
+ <arg><option>-g <replaceable class="parameter">generator</replaceable></option></arg>
+ <arg><option>-h</option></arg>
+ <arg><option>-p <replaceable class="parameter">protocol</replaceable></option></arg>
+ <arg><option>-r <replaceable class="parameter">randomdev</replaceable></option></arg>
+ <arg><option>-s <replaceable class="parameter">strength</replaceable></option></arg>
+ <arg><option>-t <replaceable class="parameter">type</replaceable></option></arg>
+ <arg><option>-v <replaceable class="parameter">level</replaceable></option></arg>
+ <arg choice="req">name</arg>
+ </cmdsynopsis>
+ </refsynopsisdiv>
+
+ <refsect1>
+ <title>DESCRIPTION</title>
+ <para>
+ <command>dnssec-keygen</command> generates keys for DNSSEC
+ (Secure DNS), as defined in RFC 2535. It can also generate
+ keys for use with TSIG (Transaction Signatures), as
+ defined in RFC 2845.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>OPTIONS</title>
+
+ <variablelist>
+ <varlistentry>
+ <term>-a <replaceable class="parameter">algorithm</replaceable></term>
+ <listitem>
+ <para>
+ Selects the cryptographic algorithm. The value of
+ <option>algorithm</option> must be one of RSAMD5 or RSA,
+ DSA, DH (Diffie Hellman), or HMAC-MD5. These values
+ are case insensitive.
+ </para>
+ <para>
+ Note that for DNSSEC, DSA is a mandatory to implement algorithm,
+ and RSA is recommended. For TSIG, HMAC-MD5 is mandatory.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-b <replaceable class="parameter">keysize</replaceable></term>
+ <listitem>
+ <para>
+ Specifies the number of bits in the key. The choice of key
+ size depends on the algorithm used. RSA keys must be between
+ 512 and 2048 bits. Diffie Hellman keys must be between
+ 128 and 4096 bits. DSA keys must be between 512 and 1024
+ bits and an exact multiple of 64. HMAC-MD5 keys must be
+ between 1 and 512 bits.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-n <replaceable class="parameter">nametype</replaceable></term>
+ <listitem>
+ <para>
+ Specifies the owner type of the key. The value of
+ <option>nametype</option> must either be ZONE (for a DNSSEC
+ zone key), HOST or ENTITY (for a key associated with a host),
+ or USER (for a key associated with a user). These values are
+ case insensitive.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-c <replaceable class="parameter">class</replaceable></term>
+ <listitem>
+ <para>
+ Indicates that the DNS record containing the key should have
+ the specified class. If not specified, class IN is used.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-e</term>
+ <listitem>
+ <para>
+ If generating an RSA key, use a large exponent.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-g <replaceable class="parameter">generator</replaceable></term>
+ <listitem>
+ <para>
+ If generating a Diffie Hellman key, use this generator.
+ Allowed values are 2 and 5. If no generator
+ is specified, a known prime from RFC 2539 will be used
+ if possible; otherwise the default is 2.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-h</term>
+ <listitem>
+ <para>
+ Prints a short summary of the options and arguments to
+ <command>dnssec-keygen</command>.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-p <replaceable class="parameter">protocol</replaceable></term>
+ <listitem>
+ <para>
+ Sets the protocol value for the generated key. The protocol
+ is a number between 0 and 255. The default is 2 (email) for
+ keys of type USER and 3 (DNSSEC) for all other key types.
+ Other possible values for this argument are listed in
+ RFC 2535 and its successors.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-r <replaceable class="parameter">randomdev</replaceable></term>
+ <listitem>
+ <para>
+ Specifies the source of randomness. If the operating
+ system does not provide a <filename>/dev/random</filename>
+ or equivalent device, the default source of randomness
+ is keyboard input. <filename>randomdev</filename> specifies
+ the name of a character device or file containing random
+ data to be used instead of the default. The special value
+ <filename>keyboard</filename> indicates that keyboard
+ input should be used.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-s <replaceable class="parameter">strength</replaceable></term>
+ <listitem>
+ <para>
+ Specifies the strength value of the key. The strength is
+ a number between 0 and 15, and currently has no defined
+ purpose in DNSSEC.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-t <replaceable class="parameter">type</replaceable></term>
+ <listitem>
+ <para>
+ Indicates the use of the key. <option>type</option> must be
+ one of AUTHCONF, NOAUTHCONF, NOAUTH, or NOCONF. The default
+ is AUTHCONF. AUTH refers to the ability to authenticate
+ data, and CONF the ability to encrypt data.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-v <replaceable class="parameter">level</replaceable></term>
+ <listitem>
+ <para>
+ Sets the debugging level.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ </variablelist>
+ </refsect1>
+
+ <refsect1>
+ <title>GENERATED KEYS</title>
+ <para>
+ When <command>dnssec-keygen</command> completes successfully,
+ it prints a string of the form <filename>Knnnn.+aaa+iiiii</filename>
+ to the standard output. This is an identification string for
+ the key it has generated. These strings can be used as arguments
+ to <command>dnssec-makekeyset</command>.
+ </para>
+ <itemizedlist>
+ <listitem>
+ <para>
+ <filename>nnnn</filename> is the key name.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ <filename>aaa</filename> is the numeric representation of the
+ algorithm.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+ <filename>iiiii</filename> is the key identifier (or footprint).
+ </para>
+ </listitem>
+ </itemizedlist>
+ <para>
+ <command>dnssec-keygen</command> creates two file, with names based
+ on the printed string. <filename>Knnnn.+aaa+iiiii.key</filename>
+ contains the public key, and
+ <filename>Knnnn.+aaa+iiiii.private</filename> contains the private
+ key.
+ </para>
+ <para>
+ The <filename>.key</filename> file contains a DNS KEY record that
+ can be inserted into a zone file (directly or with a $INCLUDE
+ statement).
+ </para>
+ <para>
+ The <filename>.private</filename> file contains algorithm specific
+ fields. For obvious security reasons, this file does not have
+ general read permission.
+ </para>
+ <para>
+ Both <filename>.key</filename> and <filename>.private</filename>
+ files are generated for symmetric encryption algorithm such as
+ HMAC-MD5, even though the public and private key are equivalent.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>EXAMPLE</title>
+ <para>
+ To generate a 768-bit DSA key for the domain
+ <userinput>example.com</userinput>, the following command would be
+ issued:
+ </para>
+ <para>
+ <userinput>dnssec-keygen -a DSA -b 768 -n ZONE example.com</userinput>
+ </para>
+ <para>
+ The command would print a string of the form:
+ </para>
+ <para>
+ <userinput>Kexample.com.+003+26160</userinput>
+ </para>
+ <para>
+ In this example, <command>dnssec-keygen</command> creates
+ the files <filename>Kexample.com.+003+26160.key</filename> and
+ <filename>Kexample.com.+003+26160.private</filename>
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>SEE ALSO</title>
+ <para>
+ <citerefentry>
+ <refentrytitle>dnssec-makekeyset</refentrytitle>
+ <manvolnum>8</manvolnum>
+ </citerefentry>,
+ <citerefentry>
+ <refentrytitle>dnssec-signkey</refentrytitle>
+ <manvolnum>8</manvolnum>
+ </citerefentry>,
+ <citerefentry>
+ <refentrytitle>dnssec-signzone</refentrytitle>
+ <manvolnum>8</manvolnum>
+ </citerefentry>,
+ <citetitle>BIND 9 Administrator Reference Manual</citetitle>,
+ <citetitle>RFC 2535</citetitle>,
+ <citetitle>RFC 2845</citetitle>,
+ <citetitle>RFC 2539</citetitle>.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>AUTHOR</title>
+ <para>
+ <corpauthor>Internet Software Consortium</corpauthor>
+ </para>
+ </refsect1>
+
+</refentry>
+
+<!--
+ - Local variables:
+ - mode: sgml
+ - End:
+-->
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-keygen.html b/usr.sbin/bind/bin/dnssec/dnssec-keygen.html
new file mode 100644
index 00000000000..d7ba6e412e7
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-keygen.html
@@ -0,0 +1,572 @@
+<!--
+ - Copyright (C) 2000, 2001 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
+ - copyright notice and this permission notice appear in all copies.
+ -
+ - THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+ - DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+ - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+ - INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+ - INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+ - FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ - NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ - WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+-->
+<HTML
+><HEAD
+><TITLE
+>dnssec-keygen</TITLE
+><META
+NAME="GENERATOR"
+CONTENT="Modular DocBook HTML Stylesheet Version 1.61
+"></HEAD
+><BODY
+CLASS="REFENTRY"
+BGCOLOR="#FFFFFF"
+TEXT="#000000"
+LINK="#0000FF"
+VLINK="#840084"
+ALINK="#0000FF"
+><H1
+><A
+NAME="AEN1"
+><SPAN
+CLASS="APPLICATION"
+>dnssec-keygen</SPAN
+></A
+></H1
+><DIV
+CLASS="REFNAMEDIV"
+><A
+NAME="AEN9"
+></A
+><H2
+>Name</H2
+><SPAN
+CLASS="APPLICATION"
+>dnssec-keygen</SPAN
+>&nbsp;--&nbsp;DNSSEC key generation tool</DIV
+><DIV
+CLASS="REFSYNOPSISDIV"
+><A
+NAME="AEN13"
+></A
+><H2
+>Synopsis</H2
+><P
+><B
+CLASS="COMMAND"
+>dnssec-keygen</B
+> {-a <TT
+CLASS="REPLACEABLE"
+><I
+>algorithm</I
+></TT
+>} {-b <TT
+CLASS="REPLACEABLE"
+><I
+>keysize</I
+></TT
+>} {-n <TT
+CLASS="REPLACEABLE"
+><I
+>nametype</I
+></TT
+>} [<TT
+CLASS="OPTION"
+>-c <TT
+CLASS="REPLACEABLE"
+><I
+>class</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-e</TT
+>] [<TT
+CLASS="OPTION"
+>-g <TT
+CLASS="REPLACEABLE"
+><I
+>generator</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-h</TT
+>] [<TT
+CLASS="OPTION"
+>-p <TT
+CLASS="REPLACEABLE"
+><I
+>protocol</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-r <TT
+CLASS="REPLACEABLE"
+><I
+>randomdev</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-s <TT
+CLASS="REPLACEABLE"
+><I
+>strength</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-t <TT
+CLASS="REPLACEABLE"
+><I
+>type</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-v <TT
+CLASS="REPLACEABLE"
+><I
+>level</I
+></TT
+></TT
+>] {name}</P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN48"
+></A
+><H2
+>DESCRIPTION</H2
+><P
+> <B
+CLASS="COMMAND"
+>dnssec-keygen</B
+> generates keys for DNSSEC
+ (Secure DNS), as defined in RFC 2535. It can also generate
+ keys for use with TSIG (Transaction Signatures), as
+ defined in RFC 2845.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN52"
+></A
+><H2
+>OPTIONS</H2
+><P
+></P
+><DIV
+CLASS="VARIABLELIST"
+><DL
+><DT
+>-a <TT
+CLASS="REPLACEABLE"
+><I
+>algorithm</I
+></TT
+></DT
+><DD
+><P
+> Selects the cryptographic algorithm. The value of
+ <TT
+CLASS="OPTION"
+>algorithm</TT
+> must be one of RSAMD5 or RSA,
+ DSA, DH (Diffie Hellman), or HMAC-MD5. These values
+ are case insensitive.
+ </P
+><P
+> Note that for DNSSEC, DSA is a mandatory to implement algorithm,
+ and RSA is recommended. For TSIG, HMAC-MD5 is mandatory.
+ </P
+></DD
+><DT
+>-b <TT
+CLASS="REPLACEABLE"
+><I
+>keysize</I
+></TT
+></DT
+><DD
+><P
+> Specifies the number of bits in the key. The choice of key
+ size depends on the algorithm used. RSA keys must be between
+ 512 and 2048 bits. Diffie Hellman keys must be between
+ 128 and 4096 bits. DSA keys must be between 512 and 1024
+ bits and an exact multiple of 64. HMAC-MD5 keys must be
+ between 1 and 512 bits.
+ </P
+></DD
+><DT
+>-n <TT
+CLASS="REPLACEABLE"
+><I
+>nametype</I
+></TT
+></DT
+><DD
+><P
+> Specifies the owner type of the key. The value of
+ <TT
+CLASS="OPTION"
+>nametype</TT
+> must either be ZONE (for a DNSSEC
+ zone key), HOST or ENTITY (for a key associated with a host),
+ or USER (for a key associated with a user). These values are
+ case insensitive.
+ </P
+></DD
+><DT
+>-c <TT
+CLASS="REPLACEABLE"
+><I
+>class</I
+></TT
+></DT
+><DD
+><P
+> Indicates that the DNS record containing the key should have
+ the specified class. If not specified, class IN is used.
+ </P
+></DD
+><DT
+>-e</DT
+><DD
+><P
+> If generating an RSA key, use a large exponent.
+ </P
+></DD
+><DT
+>-g <TT
+CLASS="REPLACEABLE"
+><I
+>generator</I
+></TT
+></DT
+><DD
+><P
+> If generating a Diffie Hellman key, use this generator.
+ Allowed values are 2 and 5. If no generator
+ is specified, a known prime from RFC 2539 will be used
+ if possible; otherwise the default is 2.
+ </P
+></DD
+><DT
+>-h</DT
+><DD
+><P
+> Prints a short summary of the options and arguments to
+ <B
+CLASS="COMMAND"
+>dnssec-keygen</B
+>.
+ </P
+></DD
+><DT
+>-p <TT
+CLASS="REPLACEABLE"
+><I
+>protocol</I
+></TT
+></DT
+><DD
+><P
+> Sets the protocol value for the generated key. The protocol
+ is a number between 0 and 255. The default is 2 (email) for
+ keys of type USER and 3 (DNSSEC) for all other key types.
+ Other possible values for this argument are listed in
+ RFC 2535 and its successors.
+ </P
+></DD
+><DT
+>-r <TT
+CLASS="REPLACEABLE"
+><I
+>randomdev</I
+></TT
+></DT
+><DD
+><P
+> Specifies the source of randomness. If the operating
+ system does not provide a <TT
+CLASS="FILENAME"
+>/dev/random</TT
+>
+ or equivalent device, the default source of randomness
+ is keyboard input. <TT
+CLASS="FILENAME"
+>randomdev</TT
+> specifies
+ the name of a character device or file containing random
+ data to be used instead of the default. The special value
+ <TT
+CLASS="FILENAME"
+>keyboard</TT
+> indicates that keyboard
+ input should be used.
+ </P
+></DD
+><DT
+>-s <TT
+CLASS="REPLACEABLE"
+><I
+>strength</I
+></TT
+></DT
+><DD
+><P
+> Specifies the strength value of the key. The strength is
+ a number between 0 and 15, and currently has no defined
+ purpose in DNSSEC.
+ </P
+></DD
+><DT
+>-t <TT
+CLASS="REPLACEABLE"
+><I
+>type</I
+></TT
+></DT
+><DD
+><P
+> Indicates the use of the key. <TT
+CLASS="OPTION"
+>type</TT
+> must be
+ one of AUTHCONF, NOAUTHCONF, NOAUTH, or NOCONF. The default
+ is AUTHCONF. AUTH refers to the ability to authenticate
+ data, and CONF the ability to encrypt data.
+ </P
+></DD
+><DT
+>-v <TT
+CLASS="REPLACEABLE"
+><I
+>level</I
+></TT
+></DT
+><DD
+><P
+> Sets the debugging level.
+ </P
+></DD
+></DL
+></DIV
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN121"
+></A
+><H2
+>GENERATED KEYS</H2
+><P
+> When <B
+CLASS="COMMAND"
+>dnssec-keygen</B
+> completes successfully,
+ it prints a string of the form <TT
+CLASS="FILENAME"
+>Knnnn.+aaa+iiiii</TT
+>
+ to the standard output. This is an identification string for
+ the key it has generated. These strings can be used as arguments
+ to <B
+CLASS="COMMAND"
+>dnssec-makekeyset</B
+>.
+ </P
+><P
+></P
+><UL
+><LI
+><P
+> <TT
+CLASS="FILENAME"
+>nnnn</TT
+> is the key name.
+ </P
+></LI
+><LI
+><P
+> <TT
+CLASS="FILENAME"
+>aaa</TT
+> is the numeric representation of the
+ algorithm.
+ </P
+></LI
+><LI
+><P
+> <TT
+CLASS="FILENAME"
+>iiiii</TT
+> is the key identifier (or footprint).
+ </P
+></LI
+></UL
+><P
+> <B
+CLASS="COMMAND"
+>dnssec-keygen</B
+> creates two file, with names based
+ on the printed string. <TT
+CLASS="FILENAME"
+>Knnnn.+aaa+iiiii.key</TT
+>
+ contains the public key, and
+ <TT
+CLASS="FILENAME"
+>Knnnn.+aaa+iiiii.private</TT
+> contains the private
+ key.
+ </P
+><P
+> The <TT
+CLASS="FILENAME"
+>.key</TT
+> file contains a DNS KEY record that
+ can be inserted into a zone file (directly or with a $INCLUDE
+ statement).
+ </P
+><P
+> The <TT
+CLASS="FILENAME"
+>.private</TT
+> file contains algorithm specific
+ fields. For obvious security reasons, this file does not have
+ general read permission.
+ </P
+><P
+> Both <TT
+CLASS="FILENAME"
+>.key</TT
+> and <TT
+CLASS="FILENAME"
+>.private</TT
+>
+ files are generated for symmetric encryption algorithm such as
+ HMAC-MD5, even though the public and private key are equivalent.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN148"
+></A
+><H2
+>EXAMPLE</H2
+><P
+> To generate a 768-bit DSA key for the domain
+ <TT
+CLASS="USERINPUT"
+><B
+>example.com</B
+></TT
+>, the following command would be
+ issued:
+ </P
+><P
+> <TT
+CLASS="USERINPUT"
+><B
+>dnssec-keygen -a DSA -b 768 -n ZONE example.com</B
+></TT
+>
+ </P
+><P
+> The command would print a string of the form:
+ </P
+><P
+> <TT
+CLASS="USERINPUT"
+><B
+>Kexample.com.+003+26160</B
+></TT
+>
+ </P
+><P
+> In this example, <B
+CLASS="COMMAND"
+>dnssec-keygen</B
+> creates
+ the files <TT
+CLASS="FILENAME"
+>Kexample.com.+003+26160.key</TT
+> and
+ <TT
+CLASS="FILENAME"
+>Kexample.com.+003+26160.private</TT
+>
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN161"
+></A
+><H2
+>SEE ALSO</H2
+><P
+> <SPAN
+CLASS="CITEREFENTRY"
+><SPAN
+CLASS="REFENTRYTITLE"
+>dnssec-makekeyset</SPAN
+>(8)</SPAN
+>,
+ <SPAN
+CLASS="CITEREFENTRY"
+><SPAN
+CLASS="REFENTRYTITLE"
+>dnssec-signkey</SPAN
+>(8)</SPAN
+>,
+ <SPAN
+CLASS="CITEREFENTRY"
+><SPAN
+CLASS="REFENTRYTITLE"
+>dnssec-signzone</SPAN
+>(8)</SPAN
+>,
+ <I
+CLASS="CITETITLE"
+>BIND 9 Administrator Reference Manual</I
+>,
+ <I
+CLASS="CITETITLE"
+>RFC 2535</I
+>,
+ <I
+CLASS="CITETITLE"
+>RFC 2845</I
+>,
+ <I
+CLASS="CITETITLE"
+>RFC 2539</I
+>.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN177"
+></A
+><H2
+>AUTHOR</H2
+><P
+> Internet Software Consortium
+ </P
+></DIV
+></BODY
+></HTML
+> \ No newline at end of file
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.8 b/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.8
new file mode 100644
index 00000000000..85639c10da5
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.8
@@ -0,0 +1,112 @@
+.\"
+.\" Copyright (C) 2000, 2001 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
+.\" copyright notice and this permission notice appear in all copies.
+.\"
+.\" THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+.\" DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+.\" INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+.\" INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+.\" FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+.\" NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+.\" WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+.\"
+.TH "DNSSEC-MAKEKEYSET" "8" "June 30, 2000" "BIND9" ""
+.SH NAME
+dnssec-makekeyset \- DNSSEC zone signing tool
+.SH SYNOPSIS
+.sp
+\fBdnssec-makekeyset\fR [ \fB-a\fR ] [ \fB-s \fIstart-time\fB\fR ] [ \fB-e \fIend-time\fB\fR ] [ \fB-h\fR ] [ \fB-p\fR ] [ \fB-r \fIrandomdev\fB\fR ] [ \fB-t\fIttl\fB\fR ] [ \fB-v \fIlevel\fB\fR ] \fBkey\fR\fI...\fR
+.SH "DESCRIPTION"
+.PP
+\fBdnssec-makekeyset\fR generates a key set from one
+or more keys created by \fBdnssec-keygen\fR. It creates
+a file containing a KEY record for each key, and self-signs the key
+set with each zone key. The output file is of the form
+\fIkeyset-nnnn.\fR, where \fInnnn\fR
+is the zone name.
+.SH "OPTIONS"
+.TP
+\fB-a\fR
+Verify all generated signatures.
+.TP
+\fB-s \fIstart-time\fB\fR
+Specify the date and time when the generated SIG records
+become valid. This can be either an absolute or relative
+time. An absolute start time is indicated by a number
+in YYYYMMDDHHMMSS notation; 20000530144500 denotes
+14:45:00 UTC on May 30th, 2000. A relative start time is
+indicated by +N, which is N seconds from the current time.
+If no \fBstart-time\fR is specified, the current
+time is used.
+.TP
+\fB-e \fIend-time\fB\fR
+Specify the date and time when the generated SIG records
+expire. As with \fBstart-time\fR, an absolute
+time is indicated in YYYYMMDDHHMMSS notation. A time relative
+to the start time is indicated with +N, which is N seconds from
+the start time. A time realtive to the current time is
+indicated with now+N. If no \fBend-time\fR is
+specified, 30 days from the start time is used as a default.
+.TP
+\fB-h\fR
+Prints a short summary of the options and arguments to
+\fBdnssec-makekeyset\fR.
+.TP
+\fB-p\fR
+Use pseudo-random data when signing the zone. This is faster,
+but less secure, than using real random data. This option
+may be useful when signing large zones or when the entropy
+source is limited.
+.TP
+\fB-r \fIrandomdev\fB\fR
+Specifies the source of randomness. If the operating
+system does not provide a \fI/dev/random\fR
+or equivalent device, the default source of randomness
+is keyboard input. \fIrandomdev\fR specifies
+the name of a character device or file containing random
+data to be used instead of the default. The special value
+\fIkeyboard\fR indicates that keyboard
+input should be used.
+.TP
+\fB-t \fIttl\fB\fR
+Specify the TTL (time to live) of the KEY and SIG records.
+The default is 3600 seconds.
+.TP
+\fB-v \fIlevel\fB\fR
+Sets the debugging level.
+.TP
+\fBkey\fR
+The list of keys to be included in the keyset file. These keys
+are expressed in the form \fIKnnnn.+aaa+iiiii\fR
+as generated by \fBdnssec-keygen\fR.
+.SH "EXAMPLE"
+.PP
+The following command generates a keyset containing the DSA key for
+\fBexample.com\fR generated in the
+\fBdnssec-keygen\fR man page.
+.PP
+\fBdnssec-makekeyset -t 86400 -s 20000701120000 -e +2592000 Kexample.com.+003+26160\fR
+.PP
+In this example, \fBdnssec-makekeyset\fR creates
+the file \fIkeyset-example.com.\fR. This file
+contains the specified key and a self-generated signature.
+.PP
+The DNS administrator for \fBexample.com\fR could
+send \fIkeyset-example.com.\fR to the DNS
+administrator for \fB.com\fR for signing, if the
+\&.com zone is DNSSEC-aware and the administrators of the two zones
+have some mechanism for authenticating each other and exchanging
+the keys and signatures securely.
+.SH "SEE ALSO"
+.PP
+\fBdnssec-keygen\fR(8),
+\fBdnssec-signkey\fR(8),
+\fIBIND 9 Administrator Reference Manual\fR,
+\fIRFC 2535\fR.
+.SH "AUTHOR"
+.PP
+Internet Software Consortium
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.c b/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.c
new file mode 100644
index 00000000000..669db9ec070
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.c
@@ -0,0 +1,467 @@
+/*
+ * Portions Copyright (C) 2000, 2001 Internet Software Consortium.
+ * Portions Copyright (C) 1995-2000 by Network Associates, Inc.
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM AND
+ * NETWORK ASSOCIATES DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS. IN NO EVENT SHALL INTERNET SOFTWARE CONSORTIUM OR NETWORK
+ * ASSOCIATES BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF
+ * USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
+ * OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/* $ISC: dnssec-makekeyset.c,v 1.52.2.1 2001/10/05 00:21:45 bwelling Exp $ */
+
+#include <config.h>
+
+#include <stdlib.h>
+
+#include <isc/commandline.h>
+#include <isc/entropy.h>
+#include <isc/mem.h>
+#include <isc/string.h>
+#include <isc/util.h>
+
+#include <dns/db.h>
+#include <dns/dnssec.h>
+#include <dns/fixedname.h>
+#include <dns/log.h>
+#include <dns/rdata.h>
+#include <dns/rdatalist.h>
+#include <dns/rdataset.h>
+#include <dns/result.h>
+#include <dns/secalg.h>
+#include <dns/time.h>
+
+#include <dst/dst.h>
+
+#include "dnssectool.h"
+
+#define BUFSIZE 2048
+
+const char *program = "dnssec-makekeyset";
+int verbose;
+
+typedef struct keynode keynode_t;
+struct keynode {
+ dst_key_t *key;
+ ISC_LINK(keynode_t) link;
+};
+typedef ISC_LIST(keynode_t) keylist_t;
+
+static isc_stdtime_t starttime = 0, endtime = 0, now;
+static int ttl = -1;
+
+static isc_mem_t *mctx = NULL;
+static isc_entropy_t *ectx = NULL;
+
+static keylist_t keylist;
+
+static void
+usage(void) {
+ fprintf(stderr, "Usage:\n");
+ fprintf(stderr, "\t%s [options] keys\n", program);
+
+ fprintf(stderr, "\n");
+
+ fprintf(stderr, "Options: (default value in parenthesis) \n");
+ fprintf(stderr, "\t-a\n");
+ fprintf(stderr, "\t\tverify generated signatures\n");
+ fprintf(stderr, "\t-s YYYYMMDDHHMMSS|+offset:\n");
+ fprintf(stderr, "\t\tSIG start time - absolute|offset (now)\n");
+ fprintf(stderr, "\t-e YYYYMMDDHHMMSS|+offset|\"now\"+offset]:\n");
+ fprintf(stderr, "\t\tSIG end time - "
+ "absolute|from start|from now (now + 30 days)\n");
+ fprintf(stderr, "\t-t ttl\n");
+ fprintf(stderr, "\t-p\n");
+ fprintf(stderr, "\t\tuse pseudorandom data (faster but less secure)\n");
+ fprintf(stderr, "\t-r randomdev:\n");
+ fprintf(stderr, "\t\ta file containing random data\n");
+ fprintf(stderr, "\t-v level:\n");
+ fprintf(stderr, "\t\tverbose level (0)\n");
+
+ fprintf(stderr, "\n");
+
+ fprintf(stderr, "keys:\n");
+ fprintf(stderr, "\tkeyfile (Kname+alg+tag)\n");
+
+ fprintf(stderr, "\n");
+
+ fprintf(stderr, "Output:\n");
+ fprintf(stderr, "\tkeyset (keyset-<name>)\n");
+ exit(0);
+}
+
+static isc_boolean_t
+zonekey_on_list(dst_key_t *key) {
+ keynode_t *keynode;
+ for (keynode = ISC_LIST_HEAD(keylist);
+ keynode != NULL;
+ keynode = ISC_LIST_NEXT(keynode, link))
+ {
+ if (dst_key_compare(keynode->key, key))
+ return (ISC_TRUE);
+ }
+ return (ISC_FALSE);
+}
+
+static isc_boolean_t
+rdata_on_list(dns_rdata_t *rdata, dns_rdatalist_t *list) {
+ dns_rdata_t *trdata;
+ for (trdata = ISC_LIST_HEAD(list->rdata);
+ trdata != NULL;
+ trdata = ISC_LIST_NEXT(trdata, link))
+ {
+ if (dns_rdata_compare(trdata, rdata) == 0)
+ return (ISC_TRUE);
+ }
+ return (ISC_FALSE);
+}
+
+int
+main(int argc, char *argv[]) {
+ int i, ch;
+ char *startstr = NULL, *endstr = NULL;
+ char *randomfile = NULL;
+ dns_fixedname_t fdomain;
+ dns_name_t *domain = NULL;
+ char *output = NULL;
+ char *endp;
+ unsigned char *data;
+ dns_db_t *db;
+ dns_dbnode_t *node;
+ dns_dbversion_t *version;
+ dst_key_t *key = NULL;
+ dns_rdata_t *rdata;
+ dns_rdatalist_t rdatalist, sigrdatalist;
+ dns_rdataset_t rdataset, sigrdataset;
+ isc_result_t result;
+ isc_buffer_t b;
+ isc_region_t r;
+ isc_log_t *log = NULL;
+ keynode_t *keynode;
+ dns_name_t *savedname = NULL;
+ unsigned int eflags;
+ isc_boolean_t pseudorandom = ISC_FALSE;
+ isc_boolean_t tryverify = ISC_FALSE;
+
+ result = isc_mem_create(0, 0, &mctx);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to create memory context: %s",
+ isc_result_totext(result));
+
+ dns_result_register();
+
+ while ((ch = isc_commandline_parse(argc, argv, "as:e:t:r:v:ph")) != -1)
+ {
+ switch (ch) {
+ case 'a':
+ tryverify = ISC_TRUE;
+ break;
+ case 's':
+ startstr = isc_commandline_argument;
+ break;
+
+ case 'e':
+ endstr = isc_commandline_argument;
+ break;
+
+ case 't':
+ endp = NULL;
+ ttl = strtol(isc_commandline_argument, &endp, 0);
+ if (*endp != '\0')
+ fatal("TTL must be numeric");
+ break;
+
+ case 'r':
+ randomfile = isc_commandline_argument;
+ break;
+
+ case 'v':
+ endp = NULL;
+ verbose = strtol(isc_commandline_argument, &endp, 0);
+ if (*endp != '\0')
+ fatal("verbose level must be numeric");
+ break;
+
+ case 'p':
+ pseudorandom = ISC_TRUE;
+ break;
+
+ case 'h':
+ default:
+ usage();
+
+ }
+ }
+
+ argc -= isc_commandline_index;
+ argv += isc_commandline_index;
+
+ if (argc < 1)
+ usage();
+
+ setup_entropy(mctx, randomfile, &ectx);
+ eflags = ISC_ENTROPY_BLOCKING;
+ if (!pseudorandom)
+ eflags |= ISC_ENTROPY_GOODONLY;
+ result = dst_lib_init(mctx, ectx, eflags);
+ if (result != ISC_R_SUCCESS)
+ fatal("could not initialize dst: %s",
+ isc_result_totext(result));
+
+ isc_stdtime_get(&now);
+
+ if (startstr != NULL)
+ starttime = strtotime(startstr, now, now);
+ else
+ starttime = now;
+
+ if (endstr != NULL)
+ endtime = strtotime(endstr, now, starttime);
+ else
+ endtime = starttime + (30 * 24 * 60 * 60);
+
+ if (ttl == -1) {
+ ttl = 3600;
+ fprintf(stderr, "%s: TTL not specified, assuming 3600\n",
+ program);
+ }
+
+ setup_logging(verbose, mctx, &log);
+
+ dns_rdatalist_init(&rdatalist);
+ rdatalist.rdclass = 0;
+ rdatalist.type = dns_rdatatype_key;
+ rdatalist.covers = 0;
+ rdatalist.ttl = ttl;
+
+ ISC_LIST_INIT(keylist);
+
+ for (i = 0; i < argc; i++) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ isc_buffer_t namebuf;
+
+ key = NULL;
+ result = dst_key_fromnamedfile(argv[i], DST_TYPE_PUBLIC,
+ mctx, &key);
+ if (result != ISC_R_SUCCESS)
+ fatal("error loading key from %s: %s", argv[i],
+ isc_result_totext(result));
+ if (rdatalist.rdclass == 0)
+ rdatalist.rdclass = dst_key_class(key);
+
+ isc_buffer_init(&namebuf, namestr, sizeof namestr);
+ result = dns_name_tofilenametext(dst_key_name(key),
+ ISC_FALSE,
+ &namebuf);
+ check_result(result, "dns_name_tofilenametext");
+ isc_buffer_putuint8(&namebuf, 0);
+
+ if (savedname == NULL) {
+ savedname = isc_mem_get(mctx, sizeof(dns_name_t));
+ if (savedname == NULL)
+ fatal("out of memory");
+ dns_name_init(savedname, NULL);
+ result = dns_name_dup(dst_key_name(key), mctx,
+ savedname);
+ if (result != ISC_R_SUCCESS)
+ fatal("out of memory");
+ } else {
+ char savednamestr[DNS_NAME_FORMATSIZE];
+ dns_name_format(savedname, savednamestr,
+ sizeof savednamestr);
+ if (!dns_name_equal(savedname, dst_key_name(key)) != 0)
+ fatal("all keys must have the same owner - %s "
+ "and %s do not match",
+ savednamestr, namestr);
+ }
+ if (output == NULL) {
+ output = isc_mem_allocate(mctx,
+ strlen("keyset-") +
+ strlen(namestr) + 1);
+ if (output == NULL)
+ fatal("out of memory");
+ strcpy(output, "keyset-");
+ strcat(output, namestr);
+ }
+ if (domain == NULL) {
+ dns_fixedname_init(&fdomain);
+ domain = dns_fixedname_name(&fdomain);
+ dns_name_copy(dst_key_name(key), domain, NULL);
+ }
+ if (dst_key_iszonekey(key)) {
+ dst_key_t *zonekey = NULL;
+ result = dst_key_fromnamedfile(argv[i],
+ DST_TYPE_PUBLIC |
+ DST_TYPE_PRIVATE,
+ mctx, &zonekey);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to read private key %s: %s",
+ argv[i], isc_result_totext(result));
+ if (!zonekey_on_list(zonekey)) {
+ keynode = isc_mem_get(mctx,
+ sizeof (keynode_t));
+ if (keynode == NULL)
+ fatal("out of memory");
+ keynode->key = zonekey;
+ ISC_LIST_INITANDAPPEND(keylist, keynode, link);
+ } else
+ dst_key_free(&zonekey);
+ }
+ rdata = isc_mem_get(mctx, sizeof(dns_rdata_t));
+ if (rdata == NULL)
+ fatal("out of memory");
+ dns_rdata_init(rdata);
+ data = isc_mem_get(mctx, BUFSIZE);
+ if (data == NULL)
+ fatal("out of memory");
+ isc_buffer_init(&b, data, BUFSIZE);
+ result = dst_key_todns(key, &b);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to convert key %s to a DNS KEY: %s",
+ argv[i], isc_result_totext(result));
+ isc_buffer_usedregion(&b, &r);
+ dns_rdata_fromregion(rdata, rdatalist.rdclass,
+ dns_rdatatype_key, &r);
+ if (!rdata_on_list(rdata, &rdatalist))
+ ISC_LIST_APPEND(rdatalist.rdata, rdata, link);
+ else {
+ isc_mem_put(mctx, data, BUFSIZE);
+ isc_mem_put(mctx, rdata, sizeof *rdata);
+ }
+ dst_key_free(&key);
+ }
+
+ dns_rdataset_init(&rdataset);
+ result = dns_rdatalist_tordataset(&rdatalist, &rdataset);
+ check_result(result, "dns_rdatalist_tordataset()");
+
+ dns_rdatalist_init(&sigrdatalist);
+ sigrdatalist.rdclass = rdatalist.rdclass;
+ sigrdatalist.type = dns_rdatatype_sig;
+ sigrdatalist.covers = dns_rdatatype_key;
+ sigrdatalist.ttl = ttl;
+
+ if (ISC_LIST_EMPTY(keylist))
+ fprintf(stderr,
+ "%s: no private zone key found; not self-signing\n",
+ program);
+ for (keynode = ISC_LIST_HEAD(keylist);
+ keynode != NULL;
+ keynode = ISC_LIST_NEXT(keynode, link))
+ {
+ rdata = isc_mem_get(mctx, sizeof(dns_rdata_t));
+ if (rdata == NULL)
+ fatal("out of memory");
+ dns_rdata_init(rdata);
+ data = isc_mem_get(mctx, BUFSIZE);
+ if (data == NULL)
+ fatal("out of memory");
+ isc_buffer_init(&b, data, BUFSIZE);
+ result = dns_dnssec_sign(domain, &rdataset, keynode->key,
+ &starttime, &endtime, mctx, &b,
+ rdata);
+ isc_entropy_stopcallbacksources(ectx);
+ if (result != ISC_R_SUCCESS) {
+ char keystr[KEY_FORMATSIZE];
+ key_format(keynode->key, keystr, sizeof keystr);
+ fatal("failed to sign keyset with key %s: %s",
+ keystr, isc_result_totext(result));
+ }
+ if (tryverify) {
+ result = dns_dnssec_verify(domain, &rdataset,
+ keynode->key, ISC_TRUE,
+ mctx, rdata);
+ if (result != ISC_R_SUCCESS) {
+ char keystr[KEY_FORMATSIZE];
+ key_format(keynode->key, keystr, sizeof keystr);
+ fatal("signature from key '%s' failed to "
+ "verify: %s",
+ keystr, isc_result_totext(result));
+ }
+ }
+ ISC_LIST_APPEND(sigrdatalist.rdata, rdata, link);
+ dns_rdataset_init(&sigrdataset);
+ result = dns_rdatalist_tordataset(&sigrdatalist, &sigrdataset);
+ check_result(result, "dns_rdatalist_tordataset()");
+ }
+
+ db = NULL;
+ result = dns_db_create(mctx, "rbt", dns_rootname, dns_dbtype_zone,
+ rdataset.rdclass, 0, NULL, &db);
+ if (result != ISC_R_SUCCESS) {
+ char domainstr[DNS_NAME_FORMATSIZE];
+ dns_name_format(domain, domainstr, sizeof domainstr);
+ fatal("failed to create a database for %s", domainstr);
+ }
+
+ version = NULL;
+ dns_db_newversion(db, &version);
+
+ node = NULL;
+ result = dns_db_findnode(db, domain, ISC_TRUE, &node);
+ check_result(result, "dns_db_findnode()");
+
+ dns_db_addrdataset(db, node, version, 0, &rdataset, 0, NULL);
+ if (!ISC_LIST_EMPTY(keylist))
+ dns_db_addrdataset(db, node, version, 0, &sigrdataset, 0,
+ NULL);
+
+ dns_db_detachnode(db, &node);
+ dns_db_closeversion(db, &version, ISC_TRUE);
+ result = dns_db_dump(db, version, output);
+ if (result != ISC_R_SUCCESS) {
+ char domainstr[DNS_NAME_FORMATSIZE];
+ dns_name_format(domain, domainstr, sizeof domainstr);
+ fatal("failed to write database for %s to %s",
+ domainstr, output);
+ }
+
+ printf("%s\n", output);
+
+ dns_db_detach(&db);
+
+ dns_rdataset_disassociate(&rdataset);
+ while (!ISC_LIST_EMPTY(rdatalist.rdata)) {
+ rdata = ISC_LIST_HEAD(rdatalist.rdata);
+ ISC_LIST_UNLINK(rdatalist.rdata, rdata, link);
+ isc_mem_put(mctx, rdata->data, BUFSIZE);
+ isc_mem_put(mctx, rdata, sizeof *rdata);
+ }
+ while (!ISC_LIST_EMPTY(sigrdatalist.rdata)) {
+ rdata = ISC_LIST_HEAD(sigrdatalist.rdata);
+ ISC_LIST_UNLINK(sigrdatalist.rdata, rdata, link);
+ isc_mem_put(mctx, rdata->data, BUFSIZE);
+ isc_mem_put(mctx, rdata, sizeof *rdata);
+ }
+
+ while (!ISC_LIST_EMPTY(keylist)) {
+ keynode = ISC_LIST_HEAD(keylist);
+ ISC_LIST_UNLINK(keylist, keynode, link);
+ dst_key_free(&keynode->key);
+ isc_mem_put(mctx, keynode, sizeof(keynode_t));
+ }
+
+ if (savedname != NULL) {
+ dns_name_free(savedname, mctx);
+ isc_mem_put(mctx, savedname, sizeof(dns_name_t));
+ }
+
+ cleanup_logging(&log);
+ cleanup_entropy(&ectx);
+
+ isc_mem_free(mctx, output);
+ dst_lib_destroy();
+ if (verbose > 10)
+ isc_mem_stats(mctx, stdout);
+ isc_mem_destroy(&mctx);
+ return (0);
+}
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.docbook b/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.docbook
new file mode 100644
index 00000000000..d2d087af92d
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.docbook
@@ -0,0 +1,233 @@
+<!DOCTYPE refentry PUBLIC "-//OASIS//DTD DocBook V4.1//EN">
+<!--
+ - Copyright (C) 2001 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
+ - copyright notice and this permission notice appear in all copies.
+ -
+ - THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+ - DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+ - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+ - INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+ - INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+ - FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ - NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ - WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+-->
+
+<!-- $ISC: dnssec-makekeyset.docbook,v 1.2.2.1 2001/09/14 20:29:32 gson Exp $ -->
+
+<refentry>
+ <refentryinfo>
+ <date>June 30, 2000</date>
+ </refentryinfo>
+
+ <refmeta>
+ <refentrytitle><application>dnssec-makekeyset</application></refentrytitle>
+ <manvolnum>8</manvolnum>
+ <refmiscinfo>BIND9</refmiscinfo>
+ </refmeta>
+
+ <refnamediv>
+ <refname><application>dnssec-makekeyset</application></refname>
+ <refpurpose>DNSSEC zone signing tool</refpurpose>
+ </refnamediv>
+
+ <refsynopsisdiv>
+ <cmdsynopsis>
+ <command>dnssec-makekeyset</command>
+ <arg><option>-a</option></arg>
+ <arg><option>-s <replaceable class="parameter">start-time</replaceable></option></arg>
+ <arg><option>-e <replaceable class="parameter">end-time</replaceable></option></arg>
+ <arg><option>-h</option></arg>
+ <arg><option>-p</option></arg>
+ <arg><option>-r <replaceable class="parameter">randomdev</replaceable></option></arg>
+ <arg><option>-t</option><replaceable class="parameter">ttl</replaceable></arg>
+ <arg><option>-v <replaceable class="parameter">level</replaceable></option></arg>
+ <arg choice="req" rep="repeat">key</arg>
+ </cmdsynopsis>
+ </refsynopsisdiv>
+
+ <refsect1>
+ <title>DESCRIPTION</title>
+ <para>
+ <command>dnssec-makekeyset</command> generates a key set from one
+ or more keys created by <command>dnssec-keygen</command>. It creates
+ a file containing a KEY record for each key, and self-signs the key
+ set with each zone key. The output file is of the form
+ <filename>keyset-nnnn.</filename>, where <filename>nnnn</filename>
+ is the zone name.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>OPTIONS</title>
+
+ <variablelist>
+ <varlistentry>
+ <term>-a</term>
+ <listitem>
+ <para>
+ Verify all generated signatures.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-s <replaceable class="parameter">start-time</replaceable></term>
+ <listitem>
+ <para>
+ Specify the date and time when the generated SIG records
+ become valid. This can be either an absolute or relative
+ time. An absolute start time is indicated by a number
+ in YYYYMMDDHHMMSS notation; 20000530144500 denotes
+ 14:45:00 UTC on May 30th, 2000. A relative start time is
+ indicated by +N, which is N seconds from the current time.
+ If no <option>start-time</option> is specified, the current
+ time is used.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-e <replaceable class="parameter">end-time</replaceable></term>
+ <listitem>
+ <para>
+ Specify the date and time when the generated SIG records
+ expire. As with <option>start-time</option>, an absolute
+ time is indicated in YYYYMMDDHHMMSS notation. A time relative
+ to the start time is indicated with +N, which is N seconds from
+ the start time. A time realtive to the current time is
+ indicated with now+N. If no <option>end-time</option> is
+ specified, 30 days from the start time is used as a default.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-h</term>
+ <listitem>
+ <para>
+ Prints a short summary of the options and arguments to
+ <command>dnssec-makekeyset</command>.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-p</term>
+ <listitem>
+ <para>
+ Use pseudo-random data when signing the zone. This is faster,
+ but less secure, than using real random data. This option
+ may be useful when signing large zones or when the entropy
+ source is limited.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-r <replaceable class="parameter">randomdev</replaceable></term>
+ <listitem>
+ <para>
+ Specifies the source of randomness. If the operating
+ system does not provide a <filename>/dev/random</filename>
+ or equivalent device, the default source of randomness
+ is keyboard input. <filename>randomdev</filename> specifies
+ the name of a character device or file containing random
+ data to be used instead of the default. The special value
+ <filename>keyboard</filename> indicates that keyboard
+ input should be used.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-t <replaceable class="parameter">ttl</replaceable></term>
+ <listitem>
+ <para>
+ Specify the TTL (time to live) of the KEY and SIG records.
+ The default is 3600 seconds.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-v <replaceable class="parameter">level</replaceable></term>
+ <listitem>
+ <para>
+ Sets the debugging level.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>key</term>
+ <listitem>
+ <para>
+ The list of keys to be included in the keyset file. These keys
+ are expressed in the form <filename>Knnnn.+aaa+iiiii</filename>
+ as generated by <command>dnssec-keygen</command>.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ </variablelist>
+ </refsect1>
+
+ <refsect1>
+ <title>EXAMPLE</title>
+ <para>
+ The following command generates a keyset containing the DSA key for
+ <userinput>example.com</userinput> generated in the
+ <command>dnssec-keygen</command> man page.
+ </para>
+ <para>
+ <userinput>dnssec-makekeyset -t 86400 -s 20000701120000 -e +2592000 Kexample.com.+003+26160</userinput>
+ </para>
+ <para>
+ In this example, <command>dnssec-makekeyset</command> creates
+ the file <filename>keyset-example.com.</filename>. This file
+ contains the specified key and a self-generated signature.
+ </para>
+ <para>
+ The DNS administrator for <userinput>example.com</userinput> could
+ send <filename>keyset-example.com.</filename> to the DNS
+ administrator for <userinput>.com</userinput> for signing, if the
+ .com zone is DNSSEC-aware and the administrators of the two zones
+ have some mechanism for authenticating each other and exchanging
+ the keys and signatures securely.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>SEE ALSO</title>
+ <para>
+ <citerefentry>
+ <refentrytitle>dnssec-keygen</refentrytitle>
+ <manvolnum>8</manvolnum>
+ </citerefentry>,
+ <citerefentry>
+ <refentrytitle>dnssec-signkey</refentrytitle>
+ <manvolnum>8</manvolnum>
+ </citerefentry>,
+ <citetitle>BIND 9 Administrator Reference Manual</citetitle>,
+ <citetitle>RFC 2535</citetitle>.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>AUTHOR</title>
+ <para>
+ <corpauthor>Internet Software Consortium</corpauthor>
+ </para>
+ </refsect1>
+
+</refentry>
+
+<!--
+ - Local variables:
+ - mode: sgml
+ - End:
+-->
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.html b/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.html
new file mode 100644
index 00000000000..aa7566da273
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-makekeyset.html
@@ -0,0 +1,404 @@
+<!--
+ - Copyright (C) 2000, 2001 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
+ - copyright notice and this permission notice appear in all copies.
+ -
+ - THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+ - DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+ - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+ - INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+ - INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+ - FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ - NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ - WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+-->
+<HTML
+><HEAD
+><TITLE
+>dnssec-makekeyset</TITLE
+><META
+NAME="GENERATOR"
+CONTENT="Modular DocBook HTML Stylesheet Version 1.61
+"></HEAD
+><BODY
+CLASS="REFENTRY"
+BGCOLOR="#FFFFFF"
+TEXT="#000000"
+LINK="#0000FF"
+VLINK="#840084"
+ALINK="#0000FF"
+><H1
+><A
+NAME="AEN1"
+><SPAN
+CLASS="APPLICATION"
+>dnssec-makekeyset</SPAN
+></A
+></H1
+><DIV
+CLASS="REFNAMEDIV"
+><A
+NAME="AEN9"
+></A
+><H2
+>Name</H2
+><SPAN
+CLASS="APPLICATION"
+>dnssec-makekeyset</SPAN
+>&nbsp;--&nbsp;DNSSEC zone signing tool</DIV
+><DIV
+CLASS="REFSYNOPSISDIV"
+><A
+NAME="AEN13"
+></A
+><H2
+>Synopsis</H2
+><P
+><B
+CLASS="COMMAND"
+>dnssec-makekeyset</B
+> [<TT
+CLASS="OPTION"
+>-a</TT
+>] [<TT
+CLASS="OPTION"
+>-s <TT
+CLASS="REPLACEABLE"
+><I
+>start-time</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-e <TT
+CLASS="REPLACEABLE"
+><I
+>end-time</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-h</TT
+>] [<TT
+CLASS="OPTION"
+>-p</TT
+>] [<TT
+CLASS="OPTION"
+>-r <TT
+CLASS="REPLACEABLE"
+><I
+>randomdev</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-t</TT
+><TT
+CLASS="REPLACEABLE"
+><I
+>ttl</I
+></TT
+>] [<TT
+CLASS="OPTION"
+>-v <TT
+CLASS="REPLACEABLE"
+><I
+>level</I
+></TT
+></TT
+>] {key...}</P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN38"
+></A
+><H2
+>DESCRIPTION</H2
+><P
+> <B
+CLASS="COMMAND"
+>dnssec-makekeyset</B
+> generates a key set from one
+ or more keys created by <B
+CLASS="COMMAND"
+>dnssec-keygen</B
+>. It creates
+ a file containing a KEY record for each key, and self-signs the key
+ set with each zone key. The output file is of the form
+ <TT
+CLASS="FILENAME"
+>keyset-nnnn.</TT
+>, where <TT
+CLASS="FILENAME"
+>nnnn</TT
+>
+ is the zone name.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN45"
+></A
+><H2
+>OPTIONS</H2
+><P
+></P
+><DIV
+CLASS="VARIABLELIST"
+><DL
+><DT
+>-a</DT
+><DD
+><P
+> Verify all generated signatures.
+ </P
+></DD
+><DT
+>-s <TT
+CLASS="REPLACEABLE"
+><I
+>start-time</I
+></TT
+></DT
+><DD
+><P
+> Specify the date and time when the generated SIG records
+ become valid. This can be either an absolute or relative
+ time. An absolute start time is indicated by a number
+ in YYYYMMDDHHMMSS notation; 20000530144500 denotes
+ 14:45:00 UTC on May 30th, 2000. A relative start time is
+ indicated by +N, which is N seconds from the current time.
+ If no <TT
+CLASS="OPTION"
+>start-time</TT
+> is specified, the current
+ time is used.
+ </P
+></DD
+><DT
+>-e <TT
+CLASS="REPLACEABLE"
+><I
+>end-time</I
+></TT
+></DT
+><DD
+><P
+> Specify the date and time when the generated SIG records
+ expire. As with <TT
+CLASS="OPTION"
+>start-time</TT
+>, an absolute
+ time is indicated in YYYYMMDDHHMMSS notation. A time relative
+ to the start time is indicated with +N, which is N seconds from
+ the start time. A time realtive to the current time is
+ indicated with now+N. If no <TT
+CLASS="OPTION"
+>end-time</TT
+> is
+ specified, 30 days from the start time is used as a default.
+ </P
+></DD
+><DT
+>-h</DT
+><DD
+><P
+> Prints a short summary of the options and arguments to
+ <B
+CLASS="COMMAND"
+>dnssec-makekeyset</B
+>.
+ </P
+></DD
+><DT
+>-p</DT
+><DD
+><P
+> Use pseudo-random data when signing the zone. This is faster,
+ but less secure, than using real random data. This option
+ may be useful when signing large zones or when the entropy
+ source is limited.
+ </P
+></DD
+><DT
+>-r <TT
+CLASS="REPLACEABLE"
+><I
+>randomdev</I
+></TT
+></DT
+><DD
+><P
+> Specifies the source of randomness. If the operating
+ system does not provide a <TT
+CLASS="FILENAME"
+>/dev/random</TT
+>
+ or equivalent device, the default source of randomness
+ is keyboard input. <TT
+CLASS="FILENAME"
+>randomdev</TT
+> specifies
+ the name of a character device or file containing random
+ data to be used instead of the default. The special value
+ <TT
+CLASS="FILENAME"
+>keyboard</TT
+> indicates that keyboard
+ input should be used.
+ </P
+></DD
+><DT
+>-t <TT
+CLASS="REPLACEABLE"
+><I
+>ttl</I
+></TT
+></DT
+><DD
+><P
+> Specify the TTL (time to live) of the KEY and SIG records.
+ The default is 3600 seconds.
+ </P
+></DD
+><DT
+>-v <TT
+CLASS="REPLACEABLE"
+><I
+>level</I
+></TT
+></DT
+><DD
+><P
+> Sets the debugging level.
+ </P
+></DD
+><DT
+>key</DT
+><DD
+><P
+> The list of keys to be included in the keyset file. These keys
+ are expressed in the form <TT
+CLASS="FILENAME"
+>Knnnn.+aaa+iiiii</TT
+>
+ as generated by <B
+CLASS="COMMAND"
+>dnssec-keygen</B
+>.
+ </P
+></DD
+></DL
+></DIV
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN98"
+></A
+><H2
+>EXAMPLE</H2
+><P
+> The following command generates a keyset containing the DSA key for
+ <TT
+CLASS="USERINPUT"
+><B
+>example.com</B
+></TT
+> generated in the
+ <B
+CLASS="COMMAND"
+>dnssec-keygen</B
+> man page.
+ </P
+><P
+> <TT
+CLASS="USERINPUT"
+><B
+>dnssec-makekeyset -t 86400 -s 20000701120000 -e +2592000 Kexample.com.+003+26160</B
+></TT
+>
+ </P
+><P
+> In this example, <B
+CLASS="COMMAND"
+>dnssec-makekeyset</B
+> creates
+ the file <TT
+CLASS="FILENAME"
+>keyset-example.com.</TT
+>. This file
+ contains the specified key and a self-generated signature.
+ </P
+><P
+> The DNS administrator for <TT
+CLASS="USERINPUT"
+><B
+>example.com</B
+></TT
+> could
+ send <TT
+CLASS="FILENAME"
+>keyset-example.com.</TT
+> to the DNS
+ administrator for <TT
+CLASS="USERINPUT"
+><B
+>.com</B
+></TT
+> for signing, if the
+ .com zone is DNSSEC-aware and the administrators of the two zones
+ have some mechanism for authenticating each other and exchanging
+ the keys and signatures securely.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN112"
+></A
+><H2
+>SEE ALSO</H2
+><P
+> <SPAN
+CLASS="CITEREFENTRY"
+><SPAN
+CLASS="REFENTRYTITLE"
+>dnssec-keygen</SPAN
+>(8)</SPAN
+>,
+ <SPAN
+CLASS="CITEREFENTRY"
+><SPAN
+CLASS="REFENTRYTITLE"
+>dnssec-signkey</SPAN
+>(8)</SPAN
+>,
+ <I
+CLASS="CITETITLE"
+>BIND 9 Administrator Reference Manual</I
+>,
+ <I
+CLASS="CITETITLE"
+>RFC 2535</I
+>.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN123"
+></A
+><H2
+>AUTHOR</H2
+><P
+> Internet Software Consortium
+ </P
+></DIV
+></BODY
+></HTML
+> \ No newline at end of file
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-signkey.8 b/usr.sbin/bind/bin/dnssec/dnssec-signkey.8
new file mode 100644
index 00000000000..80051aff262
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-signkey.8
@@ -0,0 +1,107 @@
+.\"
+.\" Copyright (C) 2000, 2001 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
+.\" copyright notice and this permission notice appear in all copies.
+.\"
+.\" THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+.\" DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+.\" INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+.\" INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+.\" FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+.\" NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+.\" WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+.\"
+.TH "DNSSEC-SIGNKEY" "8" "June 30, 2000" "BIND9" ""
+.SH NAME
+dnssec-signkey \- DNSSEC key set signing tool
+.SH SYNOPSIS
+.sp
+\fBdnssec-signkey\fR [ \fB-a\fR ] [ \fB-c \fIclass\fB\fR ] [ \fB-s \fIstart-time\fB\fR ] [ \fB-e \fIend-time\fB\fR ] [ \fB-h\fR ] [ \fB-p\fR ] [ \fB-r \fIrandomdev\fB\fR ] [ \fB-v \fIlevel\fB\fR ] \fBkeyset\fR \fBkey\fR\fI...\fR
+.SH "DESCRIPTION"
+.PP
+\fBdnssec-signkey\fR signs a keyset. Typically
+the keyset will be for a child zone, and will have been generated
+by \fBdnssec-makekeyset\fR. The child zone's keyset
+is signed with the zone keys for its parent zone. The output file
+is of the form \fIsignedkey-nnnn.\fR, where
+\fInnnn\fR is the zone name.
+.SH "OPTIONS"
+.TP
+\fB-a\fR
+Verify all generated signatures.
+.TP
+\fB-c \fIclass\fB\fR
+Specifies the DNS class of the key sets.
+.TP
+\fB-s \fIstart-time\fB\fR
+Specify the date and time when the generated SIG records
+become valid. This can be either an absolute or relative
+time. An absolute start time is indicated by a number
+in YYYYMMDDHHMMSS notation; 20000530144500 denotes
+14:45:00 UTC on May 30th, 2000. A relative start time is
+indicated by +N, which is N seconds from the current time.
+If no \fBstart-time\fR is specified, the current
+time is used.
+.TP
+\fB-e \fIend-time\fB\fR
+Specify the date and time when the generated SIG records
+expire. As with \fBstart-time\fR, an absolute
+time is indicated in YYYYMMDDHHMMSS notation. A time relative
+to the start time is indicated with +N, which is N seconds from
+the start time. A time realtive to the current time is
+indicated with now+N. If no \fBend-time\fR is
+specified, 30 days from the start time is used as a default.
+.TP
+\fB-h\fR
+Prints a short summary of the options and arguments to
+\fBdnssec-signkey\fR.
+.TP
+\fB-p\fR
+Use pseudo-random data when signing the zone. This is faster,
+but less secure, than using real random data. This option
+may be useful when signing large zones or when the entropy
+source is limited.
+.TP
+\fB-r \fIrandomdev\fB\fR
+Specifies the source of randomness. If the operating
+system does not provide a \fI/dev/random\fR
+or equivalent device, the default source of randomness
+is keyboard input. \fIrandomdev\fR specifies
+the name of a character device or file containing random
+data to be used instead of the default. The special value
+\fIkeyboard\fR indicates that keyboard
+input should be used.
+.TP
+\fB-v \fIlevel\fB\fR
+Sets the debugging level.
+.TP
+\fBkeyset\fR
+The file containing the child's keyset.
+.TP
+\fBkey\fR
+The keys used to sign the child's keyset.
+.SH "EXAMPLE"
+.PP
+The DNS administrator for a DNSSEC-aware \fB.com\fR
+zone would use the following command to sign the
+\fIkeyset\fR file for \fBexample.com\fR
+created by \fBdnssec-makekeyset\fR with a key generated
+by \fBdnssec-keygen\fR:
+.PP
+\fBdnssec-signkey keyset-example.com. Kcom.+003+51944\fR
+.PP
+In this example, \fBdnssec-signkey\fR creates
+the file \fIsignedkey-example.com.\fR, which
+contains the \fBexample.com\fR keys and the
+signatures by the \fB.com\fR keys.
+.SH "SEE ALSO"
+.PP
+\fBdnssec-keygen\fR(8),
+\fBdnssec-makekeyset\fR(8),
+\fBdnssec-signzone\fR(8).
+.SH "AUTHOR"
+.PP
+Internet Software Consortium
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-signkey.c b/usr.sbin/bind/bin/dnssec/dnssec-signkey.c
new file mode 100644
index 00000000000..69f587fd03e
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-signkey.c
@@ -0,0 +1,472 @@
+/*
+ * Portions Copyright (C) 2000, 2001 Internet Software Consortium.
+ * Portions Copyright (C) 1995-2000 by Network Associates, Inc.
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM AND
+ * NETWORK ASSOCIATES DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS. IN NO EVENT SHALL INTERNET SOFTWARE CONSORTIUM OR NETWORK
+ * ASSOCIATES BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF
+ * USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
+ * OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/* $ISC: dnssec-signkey.c,v 1.50.2.1 2001/10/05 00:21:46 bwelling Exp $ */
+
+#include <config.h>
+
+#include <stdlib.h>
+
+#include <isc/string.h>
+#include <isc/commandline.h>
+#include <isc/entropy.h>
+#include <isc/mem.h>
+#include <isc/util.h>
+
+#include <dns/db.h>
+#include <dns/dbiterator.h>
+#include <dns/dnssec.h>
+#include <dns/fixedname.h>
+#include <dns/log.h>
+#include <dns/rdata.h>
+#include <dns/rdataclass.h>
+#include <dns/rdatalist.h>
+#include <dns/rdataset.h>
+#include <dns/rdatasetiter.h>
+#include <dns/rdatastruct.h>
+#include <dns/result.h>
+#include <dns/secalg.h>
+
+#include <dst/dst.h>
+
+#include "dnssectool.h"
+
+const char *program = "dnssec-signkey";
+int verbose;
+
+#define BUFSIZE 2048
+
+typedef struct keynode keynode_t;
+struct keynode {
+ dst_key_t *key;
+ isc_boolean_t verified;
+ ISC_LINK(keynode_t) link;
+};
+typedef ISC_LIST(keynode_t) keylist_t;
+
+static isc_stdtime_t starttime = 0, endtime = 0, now;
+
+static isc_mem_t *mctx = NULL;
+static isc_entropy_t *ectx = NULL;
+static keylist_t keylist;
+
+static void
+usage(void) {
+ fprintf(stderr, "Usage:\n");
+ fprintf(stderr, "\t%s [options] keyset keys\n", program);
+
+ fprintf(stderr, "\n");
+
+ fprintf(stderr, "Options: (default value in parenthesis) \n");
+ fprintf(stderr, "\t-a\n");
+ fprintf(stderr, "\t\tverify generated signatures\n");
+ fprintf(stderr, "\t-c class (IN)\n");
+ fprintf(stderr, "\t-s YYYYMMDDHHMMSS|+offset:\n");
+ fprintf(stderr, "\t\tSIG start time - absolute|offset (from keyset)\n");
+ fprintf(stderr, "\t-e YYYYMMDDHHMMSS|+offset|\"now\"+offset]:\n");
+ fprintf(stderr, "\t\tSIG end time - absolute|from start|from now "
+ "(from keyset)\n");
+ fprintf(stderr, "\t-v level:\n");
+ fprintf(stderr, "\t\tverbose level (0)\n");
+ fprintf(stderr, "\t-p\n");
+ fprintf(stderr, "\t\tuse pseudorandom data (faster but less secure)\n");
+ fprintf(stderr, "\t-r randomdev:\n");
+ fprintf(stderr, "\t\ta file containing random data\n");
+
+ fprintf(stderr, "\n");
+
+ fprintf(stderr, "keyset:\n");
+ fprintf(stderr, "\tfile with keyset to be signed (keyset-<name>)\n");
+ fprintf(stderr, "keys:\n");
+ fprintf(stderr, "\tkeyfile (Kname+alg+tag)\n");
+
+ fprintf(stderr, "\n");
+ fprintf(stderr, "Output:\n");
+ fprintf(stderr, "\tsigned keyset (signedkey-<name>)\n");
+ exit(0);
+}
+
+static void
+loadkeys(dns_name_t *name, dns_rdataset_t *rdataset) {
+ dst_key_t *key;
+ dns_rdata_t rdata = DNS_RDATA_INIT;
+ keynode_t *keynode;
+ isc_result_t result;
+
+ ISC_LIST_INIT(keylist);
+ result = dns_rdataset_first(rdataset);
+ check_result(result, "dns_rdataset_first");
+ for (; result == ISC_R_SUCCESS; result = dns_rdataset_next(rdataset)) {
+ dns_rdata_reset(&rdata);
+ dns_rdataset_current(rdataset, &rdata);
+ key = NULL;
+ result = dns_dnssec_keyfromrdata(name, &rdata, mctx, &key);
+ if (result != ISC_R_SUCCESS)
+ continue;
+ if (!dst_key_iszonekey(key))
+ continue;
+ keynode = isc_mem_get(mctx, sizeof (keynode_t));
+ if (keynode == NULL)
+ fatal("out of memory");
+ keynode->key = key;
+ keynode->verified = ISC_FALSE;
+ ISC_LIST_INITANDAPPEND(keylist, keynode, link);
+ }
+ if (result != ISC_R_NOMORE)
+ fatal("failure traversing key list");
+}
+
+static dst_key_t *
+findkey(dns_rdata_sig_t *sig) {
+ keynode_t *keynode;
+ for (keynode = ISC_LIST_HEAD(keylist);
+ keynode != NULL;
+ keynode = ISC_LIST_NEXT(keynode, link))
+ {
+ if (dst_key_id(keynode->key) == sig->keyid &&
+ dst_key_alg(keynode->key) == sig->algorithm) {
+ keynode->verified = ISC_TRUE;
+ return (keynode->key);
+ }
+ }
+ fatal("signature generated by non-zone or missing key");
+ return (NULL);
+}
+
+int
+main(int argc, char *argv[]) {
+ int i, ch;
+ char *startstr = NULL, *endstr = NULL, *classname = NULL;
+ char tdomain[1025];
+ dns_fixedname_t fdomain;
+ dns_name_t *domain;
+ char *output = NULL;
+ char *endp;
+ unsigned char *data;
+ char *randomfile = NULL;
+ dns_db_t *db;
+ dns_dbnode_t *node;
+ dns_dbversion_t *version;
+ dns_dbiterator_t *dbiter;
+ dns_rdatasetiter_t *rdsiter;
+ dst_key_t *key = NULL;
+ dns_rdata_t *rdata;
+ dns_rdata_t sigrdata = DNS_RDATA_INIT;
+ dns_rdatalist_t sigrdatalist;
+ dns_rdataset_t rdataset, sigrdataset, newsigrdataset;
+ dns_rdata_sig_t sig;
+ isc_result_t result;
+ isc_buffer_t b;
+ isc_textregion_t tr;
+ isc_log_t *log = NULL;
+ keynode_t *keynode;
+ isc_boolean_t pseudorandom = ISC_FALSE;
+ unsigned int eflags;
+ dns_rdataclass_t rdclass;
+ static isc_boolean_t tryverify = ISC_FALSE;
+
+ result = isc_mem_create(0, 0, &mctx);
+ check_result(result, "isc_mem_create()");
+
+ dns_result_register();
+
+ while ((ch = isc_commandline_parse(argc, argv, "ac:s:e:pr:v:h")) != -1)
+ {
+ switch (ch) {
+ case 'a':
+ tryverify = ISC_TRUE;
+ break;
+ case 'c':
+ classname = isc_commandline_argument;
+ break;
+
+ case 's':
+ startstr = isc_commandline_argument;
+ break;
+
+ case 'e':
+ endstr = isc_commandline_argument;
+ break;
+
+ case 'p':
+ pseudorandom = ISC_TRUE;
+ break;
+
+ case 'r':
+ randomfile = isc_commandline_argument;
+ break;
+
+ case 'v':
+ endp = NULL;
+ verbose = strtol(isc_commandline_argument, &endp, 0);
+ if (*endp != '\0')
+ fatal("verbose level must be numeric");
+ break;
+
+ case 'h':
+ default:
+ usage();
+
+ }
+ }
+
+ argc -= isc_commandline_index;
+ argv += isc_commandline_index;
+
+ if (argc < 2)
+ usage();
+
+ if (classname != NULL) {
+ tr.base = classname;
+ tr.length = strlen(classname);
+ result = dns_rdataclass_fromtext(&rdclass, &tr);
+ if (result != ISC_R_SUCCESS)
+ fatal("unknown class %s",classname);
+ } else
+ rdclass = dns_rdataclass_in;
+
+ setup_entropy(mctx, randomfile, &ectx);
+ eflags = ISC_ENTROPY_BLOCKING;
+ if (!pseudorandom)
+ eflags |= ISC_ENTROPY_GOODONLY;
+ result = dst_lib_init(mctx, ectx, eflags);
+ if (result != ISC_R_SUCCESS)
+ fatal("could not initialize dst: %s",
+ isc_result_totext(result));
+
+ isc_stdtime_get(&now);
+
+ if ((startstr == NULL || endstr == NULL) &&
+ !(startstr == NULL && endstr == NULL))
+ fatal("if -s or -e is specified, both must be");
+
+ setup_logging(verbose, mctx, &log);
+
+ if (strlen(argv[0]) < 8 || strncmp(argv[0], "keyset-", 7) != 0)
+ fatal("keyset file '%s' must start with keyset-", argv[0]);
+
+ db = NULL;
+ result = dns_db_create(mctx, "rbt", dns_rootname, dns_dbtype_zone,
+ rdclass, 0, NULL, &db);
+ check_result(result, "dns_db_create()");
+
+ result = dns_db_load(db, argv[0]);
+ if (result != ISC_R_SUCCESS && result != DNS_R_SEENINCLUDE)
+ fatal("failed to load database from '%s': %s", argv[0],
+ isc_result_totext(result));
+
+ dns_fixedname_init(&fdomain);
+ domain = dns_fixedname_name(&fdomain);
+
+ dbiter = NULL;
+ result = dns_db_createiterator(db, ISC_FALSE, &dbiter);
+ check_result(result, "dns_db_createiterator()");
+
+ result = dns_dbiterator_first(dbiter);
+ check_result(result, "dns_dbiterator_first()");
+ while (result == ISC_R_SUCCESS) {
+ node = NULL;
+ dns_dbiterator_current(dbiter, &node, domain);
+ rdsiter = NULL;
+ result = dns_db_allrdatasets(db, node, NULL, 0, &rdsiter);
+ check_result(result, "dns_db_allrdatasets()");
+ result = dns_rdatasetiter_first(rdsiter);
+ dns_rdatasetiter_destroy(&rdsiter);
+ if (result == ISC_R_SUCCESS)
+ break;
+ dns_db_detachnode(db, &node);
+ result = dns_dbiterator_next(dbiter);
+ }
+ dns_dbiterator_destroy(&dbiter);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to find data in keyset file");
+
+ isc_buffer_init(&b, tdomain, sizeof(tdomain) - 1);
+ result = dns_name_tofilenametext(domain, ISC_FALSE, &b);
+ check_result(result, "dns_name_tofilenametext()");
+ isc_buffer_putuint8(&b, 0);
+
+ output = isc_mem_allocate(mctx,
+ strlen("signedkey-") + strlen(tdomain) + 1);
+ if (output == NULL)
+ fatal("out of memory");
+ strcpy(output, "signedkey-");
+ strcat(output, tdomain);
+
+ version = NULL;
+ dns_db_newversion(db, &version);
+
+ dns_rdataset_init(&rdataset);
+ dns_rdataset_init(&sigrdataset);
+ result = dns_db_findrdataset(db, node, version, dns_rdatatype_key, 0,
+ 0, &rdataset, &sigrdataset);
+ if (result != ISC_R_SUCCESS) {
+ char domainstr[DNS_NAME_FORMATSIZE];
+ dns_name_format(domain, domainstr, sizeof domainstr);
+ fatal("failed to find rdataset '%s KEY': %s",
+ domainstr, isc_result_totext(result));
+ }
+
+ loadkeys(domain, &rdataset);
+
+ if (!dns_rdataset_isassociated(&sigrdataset))
+ fatal("no SIG KEY set present");
+
+ result = dns_rdataset_first(&sigrdataset);
+ check_result(result, "dns_rdataset_first()");
+ do {
+ dns_rdataset_current(&sigrdataset, &sigrdata);
+ result = dns_rdata_tostruct(&sigrdata, &sig, mctx);
+ check_result(result, "dns_rdata_tostruct()");
+ key = findkey(&sig);
+ result = dns_dnssec_verify(domain, &rdataset, key,
+ ISC_TRUE, mctx, &sigrdata);
+ if (result != ISC_R_SUCCESS) {
+ char keystr[KEY_FORMATSIZE];
+ key_format(key, keystr, sizeof keystr);
+ fatal("signature by key '%s' did not verify: %s",
+ keystr, isc_result_totext(result));
+ }
+ dns_rdata_reset(&sigrdata);
+ dns_rdata_freestruct(&sig);
+ result = dns_rdataset_next(&sigrdataset);
+ } while (result == ISC_R_SUCCESS);
+
+ if (startstr != NULL) {
+ starttime = strtotime(startstr, now, now);
+ endtime = strtotime(endstr, now, starttime);
+ } else {
+ starttime = sig.timesigned;
+ endtime = sig.timeexpire;
+ }
+
+
+ for (keynode = ISC_LIST_HEAD(keylist);
+ keynode != NULL;
+ keynode = ISC_LIST_NEXT(keynode, link))
+ if (!keynode->verified)
+ fatal("Not all zone keys self signed the key set");
+
+ result = dns_rdataset_first(&sigrdataset);
+ check_result(result, "dns_rdataset_first()");
+ dns_rdataset_current(&sigrdataset, &sigrdata);
+ result = dns_rdata_tostruct(&sigrdata, &sig, mctx);
+ check_result(result, "dns_rdata_tostruct()");
+
+ dns_rdataset_disassociate(&sigrdataset);
+
+ argc -= 1;
+ argv += 1;
+
+ dns_rdatalist_init(&sigrdatalist);
+ sigrdatalist.rdclass = rdataset.rdclass;
+ sigrdatalist.type = dns_rdatatype_sig;
+ sigrdatalist.covers = dns_rdatatype_key;
+ sigrdatalist.ttl = rdataset.ttl;
+
+ for (i = 0; i < argc; i++) {
+ key = NULL;
+ result = dst_key_fromnamedfile(argv[i],
+ DST_TYPE_PUBLIC |
+ DST_TYPE_PRIVATE,
+ mctx, &key);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to read key %s from disk: %s",
+ argv[i], isc_result_totext(result));
+
+ rdata = isc_mem_get(mctx, sizeof(dns_rdata_t));
+ if (rdata == NULL)
+ fatal("out of memory");
+ dns_rdata_init(rdata);
+ data = isc_mem_get(mctx, BUFSIZE);
+ if (data == NULL)
+ fatal("out of memory");
+ isc_buffer_init(&b, data, BUFSIZE);
+ result = dns_dnssec_sign(domain, &rdataset, key,
+ &starttime, &endtime,
+ mctx, &b, rdata);
+ isc_entropy_stopcallbacksources(ectx);
+ if (result != ISC_R_SUCCESS) {
+ char keystr[KEY_FORMATSIZE];
+ key_format(key, keystr, sizeof keystr);
+ fatal("key '%s' failed to sign data: %s",
+ keystr, isc_result_totext(result));
+ }
+ if (tryverify) {
+ result = dns_dnssec_verify(domain, &rdataset, key,
+ ISC_TRUE, mctx, rdata);
+ if (result != ISC_R_SUCCESS) {
+ char keystr[KEY_FORMATSIZE];
+ key_format(key, keystr, sizeof keystr);
+ fatal("signature from key '%s' failed to "
+ "verify: %s",
+ keystr, isc_result_totext(result));
+ }
+ }
+ ISC_LIST_APPEND(sigrdatalist.rdata, rdata, link);
+ dst_key_free(&key);
+ }
+
+ dns_rdataset_init(&newsigrdataset);
+ result = dns_rdatalist_tordataset(&sigrdatalist, &newsigrdataset);
+ check_result (result, "dns_rdatalist_tordataset()");
+
+ dns_db_addrdataset(db, node, version, 0, &newsigrdataset, 0, NULL);
+ check_result (result, "dns_db_addrdataset()");
+
+ dns_db_detachnode(db, &node);
+ dns_db_closeversion(db, &version, ISC_TRUE);
+ result = dns_db_dump(db, version, output);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to write database to '%s': %s",
+ output, isc_result_totext(result));
+
+ printf("%s\n", output);
+
+ dns_rdataset_disassociate(&rdataset);
+ dns_rdataset_disassociate(&newsigrdataset);
+
+ dns_rdata_freestruct(&sig);
+
+ while (!ISC_LIST_EMPTY(sigrdatalist.rdata)) {
+ rdata = ISC_LIST_HEAD(sigrdatalist.rdata);
+ ISC_LIST_UNLINK(sigrdatalist.rdata, rdata, link);
+ isc_mem_put(mctx, rdata->data, BUFSIZE);
+ isc_mem_put(mctx, rdata, sizeof *rdata);
+ }
+
+ dns_db_detach(&db);
+
+ while (!ISC_LIST_EMPTY(keylist)) {
+ keynode = ISC_LIST_HEAD(keylist);
+ ISC_LIST_UNLINK(keylist, keynode, link);
+ dst_key_free(&keynode->key);
+ isc_mem_put(mctx, keynode, sizeof(keynode_t));
+ }
+
+ cleanup_logging(&log);
+
+ isc_mem_free(mctx, output);
+ cleanup_entropy(&ectx);
+ dst_lib_destroy();
+ if (verbose > 10)
+ isc_mem_stats(mctx, stdout);
+ isc_mem_destroy(&mctx);
+ return (0);
+}
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-signkey.docbook b/usr.sbin/bind/bin/dnssec/dnssec-signkey.docbook
new file mode 100644
index 00000000000..00c6a4c24b3
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-signkey.docbook
@@ -0,0 +1,237 @@
+<!DOCTYPE refentry PUBLIC "-//OASIS//DTD DocBook V4.1//EN">
+<!--
+ - Copyright (C) 2001 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
+ - copyright notice and this permission notice appear in all copies.
+ -
+ - THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+ - DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+ - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+ - INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+ - INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+ - FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ - NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ - WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+-->
+
+<!-- $ISC: dnssec-signkey.docbook,v 1.2 2001/04/10 21:50:34 bwelling Exp $ -->
+
+<refentry>
+ <refentryinfo>
+ <date>June 30, 2000</date>
+ </refentryinfo>
+
+ <refmeta>
+ <refentrytitle><application>dnssec-signkey</application></refentrytitle>
+ <manvolnum>8</manvolnum>
+ <refmiscinfo>BIND9</refmiscinfo>
+ </refmeta>
+
+ <refnamediv>
+ <refname><application>dnssec-signkey</application></refname>
+ <refpurpose>DNSSEC key set signing tool</refpurpose>
+ </refnamediv>
+
+ <refsynopsisdiv>
+ <cmdsynopsis>
+ <command>dnssec-signkey</command>
+ <arg><option>-a</option></arg>
+ <arg><option>-c <replaceable class="parameter">class</replaceable></option></arg>
+ <arg><option>-s <replaceable class="parameter">start-time</replaceable></option></arg>
+ <arg><option>-e <replaceable class="parameter">end-time</replaceable></option></arg>
+ <arg><option>-h</option></arg>
+ <arg><option>-p</option></arg>
+ <arg><option>-r <replaceable class="parameter">randomdev</replaceable></option></arg>
+ <arg><option>-v <replaceable class="parameter">level</replaceable></option></arg>
+ <arg choice="req">keyset</arg>
+ <arg choice="req" rep="repeat">key</arg>
+ </cmdsynopsis>
+ </refsynopsisdiv>
+
+ <refsect1>
+ <title>DESCRIPTION</title>
+ <para>
+ <command>dnssec-signkey</command> signs a keyset. Typically
+ the keyset will be for a child zone, and will have been generated
+ by <command>dnssec-makekeyset</command>. The child zone's keyset
+ is signed with the zone keys for its parent zone. The output file
+ is of the form <filename>signedkey-nnnn.</filename>, where
+ <filename>nnnn</filename> is the zone name.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>OPTIONS</title>
+
+ <variablelist>
+ <varlistentry>
+ <term>-a</term>
+ <listitem>
+ <para>
+ Verify all generated signatures.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-c <replaceable class="parameter">class</replaceable></term>
+ <listitem>
+ <para>
+ Specifies the DNS class of the key sets.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-s <replaceable class="parameter">start-time</replaceable></term>
+ <listitem>
+ <para>
+ Specify the date and time when the generated SIG records
+ become valid. This can be either an absolute or relative
+ time. An absolute start time is indicated by a number
+ in YYYYMMDDHHMMSS notation; 20000530144500 denotes
+ 14:45:00 UTC on May 30th, 2000. A relative start time is
+ indicated by +N, which is N seconds from the current time.
+ If no <option>start-time</option> is specified, the current
+ time is used.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-e <replaceable class="parameter">end-time</replaceable></term>
+ <listitem>
+ <para>
+ Specify the date and time when the generated SIG records
+ expire. As with <option>start-time</option>, an absolute
+ time is indicated in YYYYMMDDHHMMSS notation. A time relative
+ to the start time is indicated with +N, which is N seconds from
+ the start time. A time realtive to the current time is
+ indicated with now+N. If no <option>end-time</option> is
+ specified, 30 days from the start time is used as a default.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-h</term>
+ <listitem>
+ <para>
+ Prints a short summary of the options and arguments to
+ <command>dnssec-signkey</command>.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-p</term>
+ <listitem>
+ <para>
+ Use pseudo-random data when signing the zone. This is faster,
+ but less secure, than using real random data. This option
+ may be useful when signing large zones or when the entropy
+ source is limited.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-r <replaceable class="parameter">randomdev</replaceable></term>
+ <listitem>
+ <para>
+ Specifies the source of randomness. If the operating
+ system does not provide a <filename>/dev/random</filename>
+ or equivalent device, the default source of randomness
+ is keyboard input. <filename>randomdev</filename> specifies
+ the name of a character device or file containing random
+ data to be used instead of the default. The special value
+ <filename>keyboard</filename> indicates that keyboard
+ input should be used.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-v <replaceable class="parameter">level</replaceable></term>
+ <listitem>
+ <para>
+ Sets the debugging level.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>keyset</term>
+ <listitem>
+ <para>
+ The file containing the child's keyset.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>key</term>
+ <listitem>
+ <para>
+ The keys used to sign the child's keyset.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ </variablelist>
+ </refsect1>
+
+ <refsect1>
+ <title>EXAMPLE</title>
+ <para>
+ The DNS administrator for a DNSSEC-aware <userinput>.com</userinput>
+ zone would use the following command to sign the
+ <filename>keyset</filename> file for <userinput>example.com</userinput>
+ created by <command>dnssec-makekeyset</command> with a key generated
+ by <command>dnssec-keygen</command>:
+ </para>
+ <para>
+ <userinput>dnssec-signkey keyset-example.com. Kcom.+003+51944</userinput>
+ </para>
+ <para>
+ In this example, <command>dnssec-signkey</command> creates
+ the file <filename>signedkey-example.com.</filename>, which
+ contains the <userinput>example.com</userinput> keys and the
+ signatures by the <userinput>.com</userinput> keys.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>SEE ALSO</title>
+ <para>
+ <citerefentry>
+ <refentrytitle>dnssec-keygen</refentrytitle>
+ <manvolnum>8</manvolnum>
+ </citerefentry>,
+ <citerefentry>
+ <refentrytitle>dnssec-makekeyset</refentrytitle>
+ <manvolnum>8</manvolnum>
+ </citerefentry>,
+ <citerefentry>
+ <refentrytitle>dnssec-signzone</refentrytitle>
+ <manvolnum>8</manvolnum>
+ </citerefentry>.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>AUTHOR</title>
+ <para>
+ <corpauthor>Internet Software Consortium</corpauthor>
+ </para>
+ </refsect1>
+
+</refentry>
+
+<!--
+ - Local variables:
+ - mode: sgml
+ - End:
+-->
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-signkey.html b/usr.sbin/bind/bin/dnssec/dnssec-signkey.html
new file mode 100644
index 00000000000..d98fd225c22
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-signkey.html
@@ -0,0 +1,404 @@
+<!--
+ - Copyright (C) 2000, 2001 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
+ - copyright notice and this permission notice appear in all copies.
+ -
+ - THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+ - DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+ - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+ - INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+ - INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+ - FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ - NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ - WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+-->
+<HTML
+><HEAD
+><TITLE
+>dnssec-signkey</TITLE
+><META
+NAME="GENERATOR"
+CONTENT="Modular DocBook HTML Stylesheet Version 1.61
+"></HEAD
+><BODY
+CLASS="REFENTRY"
+BGCOLOR="#FFFFFF"
+TEXT="#000000"
+LINK="#0000FF"
+VLINK="#840084"
+ALINK="#0000FF"
+><H1
+><A
+NAME="AEN1"
+><SPAN
+CLASS="APPLICATION"
+>dnssec-signkey</SPAN
+></A
+></H1
+><DIV
+CLASS="REFNAMEDIV"
+><A
+NAME="AEN9"
+></A
+><H2
+>Name</H2
+><SPAN
+CLASS="APPLICATION"
+>dnssec-signkey</SPAN
+>&nbsp;--&nbsp;DNSSEC key set signing tool</DIV
+><DIV
+CLASS="REFSYNOPSISDIV"
+><A
+NAME="AEN13"
+></A
+><H2
+>Synopsis</H2
+><P
+><B
+CLASS="COMMAND"
+>dnssec-signkey</B
+> [<TT
+CLASS="OPTION"
+>-a</TT
+>] [<TT
+CLASS="OPTION"
+>-c <TT
+CLASS="REPLACEABLE"
+><I
+>class</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-s <TT
+CLASS="REPLACEABLE"
+><I
+>start-time</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-e <TT
+CLASS="REPLACEABLE"
+><I
+>end-time</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-h</TT
+>] [<TT
+CLASS="OPTION"
+>-p</TT
+>] [<TT
+CLASS="OPTION"
+>-r <TT
+CLASS="REPLACEABLE"
+><I
+>randomdev</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-v <TT
+CLASS="REPLACEABLE"
+><I
+>level</I
+></TT
+></TT
+>] {keyset} {key...}</P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN39"
+></A
+><H2
+>DESCRIPTION</H2
+><P
+> <B
+CLASS="COMMAND"
+>dnssec-signkey</B
+> signs a keyset. Typically
+ the keyset will be for a child zone, and will have been generated
+ by <B
+CLASS="COMMAND"
+>dnssec-makekeyset</B
+>. The child zone's keyset
+ is signed with the zone keys for its parent zone. The output file
+ is of the form <TT
+CLASS="FILENAME"
+>signedkey-nnnn.</TT
+>, where
+ <TT
+CLASS="FILENAME"
+>nnnn</TT
+> is the zone name.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN46"
+></A
+><H2
+>OPTIONS</H2
+><P
+></P
+><DIV
+CLASS="VARIABLELIST"
+><DL
+><DT
+>-a</DT
+><DD
+><P
+> Verify all generated signatures.
+ </P
+></DD
+><DT
+>-c <TT
+CLASS="REPLACEABLE"
+><I
+>class</I
+></TT
+></DT
+><DD
+><P
+> Specifies the DNS class of the key sets.
+ </P
+></DD
+><DT
+>-s <TT
+CLASS="REPLACEABLE"
+><I
+>start-time</I
+></TT
+></DT
+><DD
+><P
+> Specify the date and time when the generated SIG records
+ become valid. This can be either an absolute or relative
+ time. An absolute start time is indicated by a number
+ in YYYYMMDDHHMMSS notation; 20000530144500 denotes
+ 14:45:00 UTC on May 30th, 2000. A relative start time is
+ indicated by +N, which is N seconds from the current time.
+ If no <TT
+CLASS="OPTION"
+>start-time</TT
+> is specified, the current
+ time is used.
+ </P
+></DD
+><DT
+>-e <TT
+CLASS="REPLACEABLE"
+><I
+>end-time</I
+></TT
+></DT
+><DD
+><P
+> Specify the date and time when the generated SIG records
+ expire. As with <TT
+CLASS="OPTION"
+>start-time</TT
+>, an absolute
+ time is indicated in YYYYMMDDHHMMSS notation. A time relative
+ to the start time is indicated with +N, which is N seconds from
+ the start time. A time realtive to the current time is
+ indicated with now+N. If no <TT
+CLASS="OPTION"
+>end-time</TT
+> is
+ specified, 30 days from the start time is used as a default.
+ </P
+></DD
+><DT
+>-h</DT
+><DD
+><P
+> Prints a short summary of the options and arguments to
+ <B
+CLASS="COMMAND"
+>dnssec-signkey</B
+>.
+ </P
+></DD
+><DT
+>-p</DT
+><DD
+><P
+> Use pseudo-random data when signing the zone. This is faster,
+ but less secure, than using real random data. This option
+ may be useful when signing large zones or when the entropy
+ source is limited.
+ </P
+></DD
+><DT
+>-r <TT
+CLASS="REPLACEABLE"
+><I
+>randomdev</I
+></TT
+></DT
+><DD
+><P
+> Specifies the source of randomness. If the operating
+ system does not provide a <TT
+CLASS="FILENAME"
+>/dev/random</TT
+>
+ or equivalent device, the default source of randomness
+ is keyboard input. <TT
+CLASS="FILENAME"
+>randomdev</TT
+> specifies
+ the name of a character device or file containing random
+ data to be used instead of the default. The special value
+ <TT
+CLASS="FILENAME"
+>keyboard</TT
+> indicates that keyboard
+ input should be used.
+ </P
+></DD
+><DT
+>-v <TT
+CLASS="REPLACEABLE"
+><I
+>level</I
+></TT
+></DT
+><DD
+><P
+> Sets the debugging level.
+ </P
+></DD
+><DT
+>keyset</DT
+><DD
+><P
+> The file containing the child's keyset.
+ </P
+></DD
+><DT
+>key</DT
+><DD
+><P
+> The keys used to sign the child's keyset.
+ </P
+></DD
+></DL
+></DIV
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN101"
+></A
+><H2
+>EXAMPLE</H2
+><P
+> The DNS administrator for a DNSSEC-aware <TT
+CLASS="USERINPUT"
+><B
+>.com</B
+></TT
+>
+ zone would use the following command to sign the
+ <TT
+CLASS="FILENAME"
+>keyset</TT
+> file for <TT
+CLASS="USERINPUT"
+><B
+>example.com</B
+></TT
+>
+ created by <B
+CLASS="COMMAND"
+>dnssec-makekeyset</B
+> with a key generated
+ by <B
+CLASS="COMMAND"
+>dnssec-keygen</B
+>:
+ </P
+><P
+> <TT
+CLASS="USERINPUT"
+><B
+>dnssec-signkey keyset-example.com. Kcom.+003+51944</B
+></TT
+>
+ </P
+><P
+> In this example, <B
+CLASS="COMMAND"
+>dnssec-signkey</B
+> creates
+ the file <TT
+CLASS="FILENAME"
+>signedkey-example.com.</TT
+>, which
+ contains the <TT
+CLASS="USERINPUT"
+><B
+>example.com</B
+></TT
+> keys and the
+ signatures by the <TT
+CLASS="USERINPUT"
+><B
+>.com</B
+></TT
+> keys.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN116"
+></A
+><H2
+>SEE ALSO</H2
+><P
+> <SPAN
+CLASS="CITEREFENTRY"
+><SPAN
+CLASS="REFENTRYTITLE"
+>dnssec-keygen</SPAN
+>(8)</SPAN
+>,
+ <SPAN
+CLASS="CITEREFENTRY"
+><SPAN
+CLASS="REFENTRYTITLE"
+>dnssec-makekeyset</SPAN
+>(8)</SPAN
+>,
+ <SPAN
+CLASS="CITEREFENTRY"
+><SPAN
+CLASS="REFENTRYTITLE"
+>dnssec-signzone</SPAN
+>(8)</SPAN
+>.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN128"
+></A
+><H2
+>AUTHOR</H2
+><P
+> Internet Software Consortium
+ </P
+></DIV
+></BODY
+></HTML
+> \ No newline at end of file
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-signzone.8 b/usr.sbin/bind/bin/dnssec/dnssec-signzone.8
new file mode 100644
index 00000000000..b3960998b0d
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-signzone.8
@@ -0,0 +1,154 @@
+.\"
+.\" Copyright (C) 2000, 2001 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
+.\" copyright notice and this permission notice appear in all copies.
+.\"
+.\" THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+.\" DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+.\" INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+.\" INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+.\" FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+.\" NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+.\" WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+.\"
+.TH "DNSSEC-SIGNZONE" "8" "June 30, 2000" "BIND9" ""
+.SH NAME
+dnssec-signzone \- DNSSEC zone signing tool
+.SH SYNOPSIS
+.sp
+\fBdnssec-signzone\fR [ \fB-a\fR ] [ \fB-c \fIclass\fB\fR ] [ \fB-d \fIdirectory\fB\fR ] [ \fB-s \fIstart-time\fB\fR ] [ \fB-e \fIend-time\fB\fR ] [ \fB-f \fIoutput-file\fB\fR ] [ \fB-h\fR ] [ \fB-i \fIinterval\fB\fR ] [ \fB-n \fInthreads\fB\fR ] [ \fB-o \fIorigin\fB\fR ] [ \fB-p\fR ] [ \fB-r \fIrandomdev\fB\fR ] [ \fB-t\fR ] [ \fB-v \fIlevel\fB\fR ] \fBzonefile\fR [ \fBkey\fR\fI...\fR ]
+.SH "DESCRIPTION"
+.PP
+\fBdnssec-signzone\fR signs a zone. It generates NXT
+and SIG records and produces a signed version of the zone. If there
+is a \fIsignedkey\fR file from the zone's parent,
+the parent's signatures will be incorporated into the generated
+signed zone file. The security status of delegations from the the
+signed zone (that is, whether the child zones are secure or not) is
+determined by the presence or absence of a
+\fIsignedkey\fR file for each child zone.
+.SH "OPTIONS"
+.TP
+\fB-a\fR
+Verify all generated signatures.
+.TP
+\fB-c \fIclass\fB\fR
+Specifies the DNS class of the zone.
+.TP
+\fB-d \fIdirectory\fB\fR
+Look for \fIsignedkey\fR files in
+\fBdirectory\fR as the directory
+.TP
+\fB-s \fIstart-time\fB\fR
+Specify the date and time when the generated SIG records
+become valid. This can be either an absolute or relative
+time. An absolute start time is indicated by a number
+in YYYYMMDDHHMMSS notation; 20000530144500 denotes
+14:45:00 UTC on May 30th, 2000. A relative start time is
+indicated by +N, which is N seconds from the current time.
+If no \fBstart-time\fR is specified, the current
+time is used.
+.TP
+\fB-e \fIend-time\fB\fR
+Specify the date and time when the generated SIG records
+expire. As with \fBstart-time\fR, an absolute
+time is indicated in YYYYMMDDHHMMSS notation. A time relative
+to the start time is indicated with +N, which is N seconds from
+the start time. A time realtive to the current time is
+indicated with now+N. If no \fBend-time\fR is
+specified, 30 days from the start time is used as a default.
+.TP
+\fB-f \fIoutput-file\fB\fR
+The name of the output file containing the signed zone. The
+default is to append \fI.signed\fR to the
+input file.
+.TP
+\fB-h\fR
+Prints a short summary of the options and arguments to
+\fBdnssec-signzone\fR.
+.TP
+\fB-i \fIinterval\fB\fR
+When a previously signed zone is passed as input, records
+may be resigned. The \fBinterval\fR option
+specifies the cycle interval as an offset from the current
+time (in seconds). If a SIG record expires after the
+cycle interval, it is retained. Otherwise, it is considered
+to be expiring soon, and it will be replaced.
+
+The default cycle interval is one quarter of the difference
+between the signature end and start times. So if neither
+\fBend-time\fR or \fBstart-time\fR
+are specified, \fBdnssec-signzone\fR generates
+signatures that are valid for 30 days, with a cycle
+interval of 7.5 days. Therefore, if any existing SIG records
+are due to expire in less than 7.5 days, they would be
+replaced.
+.TP
+\fB-n \fIncpus\fB\fR
+Specifies the number of threads to use. By default, one
+thread is started for each detected CPU.
+.TP
+\fB-o \fIorigin\fB\fR
+The zone origin. If not specified, the name of the zone file
+is assumed to be the origin.
+.TP
+\fB-p\fR
+Use pseudo-random data when signing the zone. This is faster,
+but less secure, than using real random data. This option
+may be useful when signing large zones or when the entropy
+source is limited.
+.TP
+\fB-r \fIrandomdev\fB\fR
+Specifies the source of randomness. If the operating
+system does not provide a \fI/dev/random\fR
+or equivalent device, the default source of randomness
+is keyboard input. \fIrandomdev\fR specifies
+the name of a character device or file containing random
+data to be used instead of the default. The special value
+\fIkeyboard\fR indicates that keyboard
+input should be used.
+.TP
+\fB-t\fR
+Print statistics at completion.
+.TP
+\fB-v \fIlevel\fB\fR
+Sets the debugging level.
+.TP
+\fBzonefile\fR
+The file containing the zone to be signed.
+Sets the debugging level.
+.TP
+\fBkey\fR
+The keys used to sign the zone. If no keys are specified, the
+default all zone keys that have private key files in the
+current directory.
+.SH "EXAMPLE"
+.PP
+The following command signs the \fBexample.com\fR
+zone with the DSA key generated in the \fBdnssec-keygen\fR
+man page. The zone's keys must be in the zone. If there are
+\fIsignedkey\fR files associated with this zone
+or any child zones, they must be in the current directory.
+\fBexample.com\fR, the following command would be
+issued:
+.PP
+\fBdnssec-signzone -o example.com db.example.com Kexample.com.+003+26160\fR
+.PP
+The command would print a string of the form:
+.PP
+In this example, \fBdnssec-signzone\fR creates
+the file \fIdb.example.com.signed\fR. This file
+should be referenced in a zone statement in a
+\fInamed.conf\fR file.
+.SH "SEE ALSO"
+.PP
+\fBdnssec-keygen\fR(8),
+\fBdnssec-signkey\fR(8),
+\fIBIND 9 Administrator Reference Manual\fR,
+\fIRFC 2535\fR.
+.SH "AUTHOR"
+.PP
+Internet Software Consortium
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-signzone.c b/usr.sbin/bind/bin/dnssec/dnssec-signzone.c
new file mode 100644
index 00000000000..0df17946293
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-signzone.c
@@ -0,0 +1,1860 @@
+/*
+ * Portions Copyright (C) 1999-2001 Internet Software Consortium.
+ * Portions Copyright (C) 1995-2000 by Network Associates, Inc.
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM AND
+ * NETWORK ASSOCIATES DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS. IN NO EVENT SHALL INTERNET SOFTWARE CONSORTIUM OR NETWORK
+ * ASSOCIATES BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF
+ * USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
+ * OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/* $ISC: dnssec-signzone.c,v 1.139.2.1 2001/10/05 00:21:48 bwelling Exp $ */
+
+#include <config.h>
+
+#include <stdlib.h>
+#include <time.h>
+
+#include <isc/app.h>
+#include <isc/commandline.h>
+#include <isc/entropy.h>
+#include <isc/event.h>
+#include <isc/file.h>
+#include <isc/mem.h>
+#include <isc/mutex.h>
+#include <isc/os.h>
+#include <isc/stdio.h>
+#include <isc/string.h>
+#include <isc/task.h>
+#include <isc/util.h>
+#include <isc/time.h>
+
+#include <dns/db.h>
+#include <dns/dbiterator.h>
+#include <dns/diff.h>
+#include <dns/dnssec.h>
+#include <dns/fixedname.h>
+#include <dns/keyvalues.h>
+#include <dns/log.h>
+#include <dns/master.h>
+#include <dns/masterdump.h>
+#include <dns/nxt.h>
+#include <dns/rdata.h>
+#include <dns/rdataset.h>
+#include <dns/rdataclass.h>
+#include <dns/rdatasetiter.h>
+#include <dns/rdatastruct.h>
+#include <dns/rdatatype.h>
+#include <dns/result.h>
+#include <dns/secalg.h>
+#include <dns/time.h>
+
+#include <dst/dst.h>
+#include <dst/result.h>
+
+#include "dnssectool.h"
+
+const char *program = "dnssec-signzone";
+int verbose;
+
+#define BUFSIZE 2048
+
+typedef struct signer_key_struct signer_key_t;
+
+struct signer_key_struct {
+ dst_key_t *key;
+ isc_boolean_t isdefault;
+ unsigned int position;
+ ISC_LINK(signer_key_t) link;
+};
+
+#define SIGNER_EVENTCLASS ISC_EVENTCLASS(0x4453)
+#define SIGNER_EVENT_WRITE (SIGNER_EVENTCLASS + 0)
+#define SIGNER_EVENT_WORK (SIGNER_EVENTCLASS + 1)
+
+typedef struct signer_event sevent_t;
+struct signer_event {
+ ISC_EVENT_COMMON(sevent_t);
+ dns_fixedname_t *fname;
+ dns_fixedname_t *fnextname;
+ dns_dbnode_t *node;
+};
+
+static ISC_LIST(signer_key_t) keylist;
+static unsigned int keycount = 0;
+static isc_stdtime_t starttime = 0, endtime = 0, now;
+static int cycle = -1;
+static isc_boolean_t tryverify = ISC_FALSE;
+static isc_boolean_t printstats = ISC_FALSE;
+static isc_mem_t *mctx = NULL;
+static isc_entropy_t *ectx = NULL;
+static dns_ttl_t zonettl;
+static FILE *fp;
+static char *tempfile = NULL;
+static const dns_master_style_t *masterstyle;
+static unsigned int nsigned = 0, nretained = 0, ndropped = 0;
+static unsigned int nverified = 0, nverifyfailed = 0;
+static const char *directory;
+static isc_mutex_t namelock, statslock;
+static isc_taskmgr_t *taskmgr = NULL;
+static dns_db_t *gdb; /* The database */
+static dns_dbversion_t *gversion; /* The database version */
+static dns_dbiterator_t *gdbiter; /* The database iterator */
+static dns_name_t *gorigin; /* The database origin */
+static dns_dbnode_t *gnode = NULL; /* The "current" database node */
+static dns_name_t *lastzonecut;
+static isc_task_t *master = NULL;
+static unsigned int ntasks = 0;
+static isc_boolean_t shuttingdown = ISC_FALSE, finished = ISC_FALSE;
+static unsigned int assigned = 0, completed = 0;
+static isc_boolean_t nokeys = ISC_FALSE;
+static isc_boolean_t removefile = ISC_FALSE;
+
+#define INCSTAT(counter) \
+ if (printstats) { \
+ LOCK(&statslock); \
+ counter++; \
+ UNLOCK(&statslock); \
+ }
+
+static void
+sign(isc_task_t *task, isc_event_t *event);
+
+
+static inline void
+set_bit(unsigned char *array, unsigned int index, unsigned int bit) {
+ unsigned int shift, mask;
+
+ shift = 7 - (index % 8);
+ mask = 1 << shift;
+
+ if (bit != 0)
+ array[index / 8] |= mask;
+ else
+ array[index / 8] &= (~mask & 0xFF);
+}
+
+static signer_key_t *
+newkeystruct(dst_key_t *dstkey, isc_boolean_t isdefault) {
+ signer_key_t *key;
+
+ key = isc_mem_get(mctx, sizeof(signer_key_t));
+ if (key == NULL)
+ fatal("out of memory");
+ key->key = dstkey;
+ key->isdefault = isdefault;
+ key->position = keycount++;
+ ISC_LINK_INIT(key, link);
+ return (key);
+}
+
+static void
+signwithkey(dns_name_t *name, dns_rdataset_t *rdataset, dns_rdata_t *rdata,
+ dst_key_t *key, isc_buffer_t *b)
+{
+ isc_result_t result;
+
+ result = dns_dnssec_sign(name, rdataset, key, &starttime, &endtime,
+ mctx, b, rdata);
+ isc_entropy_stopcallbacksources(ectx);
+ if (result != ISC_R_SUCCESS) {
+ char keystr[KEY_FORMATSIZE];
+ key_format(key, keystr, sizeof keystr);
+ fatal("key '%s' failed to sign data: %s",
+ keystr, isc_result_totext(result));
+ }
+ INCSTAT(nsigned);
+
+ if (tryverify) {
+ result = dns_dnssec_verify(name, rdataset, key,
+ ISC_TRUE, mctx, rdata);
+ if (result == ISC_R_SUCCESS) {
+ vbprintf(3, "\tsignature verified\n");
+ INCSTAT(nverified);
+ } else {
+ vbprintf(3, "\tsignature failed to verify\n");
+ INCSTAT(nverifyfailed);
+ }
+ }
+}
+
+static inline isc_boolean_t
+issigningkey(signer_key_t *key) {
+ return (key->isdefault);
+}
+
+static inline isc_boolean_t
+iszonekey(signer_key_t *key) {
+ return (ISC_TF(dns_name_equal(dst_key_name(key->key), gorigin) &&
+ dst_key_iszonekey(key->key)));
+}
+
+/*
+ * Finds the key that generated a SIG, if possible. First look at the keys
+ * that we've loaded already, and then see if there's a key on disk.
+ */
+static signer_key_t *
+keythatsigned(dns_rdata_sig_t *sig) {
+ isc_result_t result;
+ dst_key_t *pubkey = NULL, *privkey = NULL;
+ signer_key_t *key;
+
+ key = ISC_LIST_HEAD(keylist);
+ while (key != NULL) {
+ if (sig->keyid == dst_key_id(key->key) &&
+ sig->algorithm == dst_key_alg(key->key) &&
+ dns_name_equal(&sig->signer, dst_key_name(key->key)))
+ return key;
+ key = ISC_LIST_NEXT(key, link);
+ }
+
+ result = dst_key_fromfile(&sig->signer, sig->keyid, sig->algorithm,
+ DST_TYPE_PUBLIC, NULL, mctx, &pubkey);
+ if (result != ISC_R_SUCCESS)
+ return (NULL);
+
+ result = dst_key_fromfile(&sig->signer, sig->keyid, sig->algorithm,
+ DST_TYPE_PUBLIC | DST_TYPE_PRIVATE,
+ NULL, mctx, &privkey);
+ if (result == ISC_R_SUCCESS) {
+ dst_key_free(&pubkey);
+ key = newkeystruct(privkey, ISC_FALSE);
+ } else
+ key = newkeystruct(pubkey, ISC_FALSE);
+ ISC_LIST_APPEND(keylist, key, link);
+ return (key);
+}
+
+/*
+ * Check to see if we expect to find a key at this name. If we see a SIG
+ * and can't find the signing key that we expect to find, we drop the sig.
+ * I'm not sure if this is completely correct, but it seems to work.
+ */
+static isc_boolean_t
+expecttofindkey(dns_name_t *name) {
+ unsigned int options = DNS_DBFIND_NOWILD;
+ dns_fixedname_t fname;
+ isc_result_t result;
+ char namestr[DNS_NAME_FORMATSIZE];
+
+ dns_fixedname_init(&fname);
+ result = dns_db_find(gdb, name, gversion, dns_rdatatype_key, options,
+ 0, NULL, dns_fixedname_name(&fname), NULL, NULL);
+ switch (result) {
+ case ISC_R_SUCCESS:
+ case DNS_R_NXDOMAIN:
+ case DNS_R_NXRRSET:
+ return (ISC_TRUE);
+ case DNS_R_DELEGATION:
+ case DNS_R_CNAME:
+ case DNS_R_DNAME:
+ return (ISC_FALSE);
+ }
+ dns_name_format(name, namestr, sizeof namestr);
+ fatal("failure looking for '%s KEY' in database: %s",
+ namestr, isc_result_totext(result));
+ return (ISC_FALSE); /* removes a warning */
+}
+
+static inline isc_boolean_t
+setverifies(dns_name_t *name, dns_rdataset_t *set, signer_key_t *key,
+ dns_rdata_t *sig)
+{
+ isc_result_t result;
+ result = dns_dnssec_verify(name, set, key->key, ISC_FALSE, mctx, sig);
+ if (result == ISC_R_SUCCESS) {
+ INCSTAT(nverified);
+ return (ISC_TRUE);
+ } else {
+ INCSTAT(nverifyfailed);
+ return (ISC_FALSE);
+ }
+}
+
+/*
+ * Signs a set. Goes through contortions to decide if each SIG should
+ * be dropped or retained, and then determines if any new SIGs need to
+ * be generated.
+ */
+static void
+signset(dns_diff_t *diff, dns_dbnode_t *node, dns_name_t *name,
+ dns_rdataset_t *set)
+{
+ dns_rdataset_t sigset;
+ dns_rdata_t sigrdata = DNS_RDATA_INIT;
+ dns_rdata_sig_t sig;
+ signer_key_t *key;
+ isc_result_t result;
+ isc_boolean_t nosigs = ISC_FALSE;
+ isc_boolean_t *wassignedby, *nowsignedby;
+ int arraysize;
+ dns_difftuple_t *tuple;
+ dns_ttl_t ttl;
+ int i;
+ char namestr[DNS_NAME_FORMATSIZE];
+ char typestr[TYPE_FORMATSIZE];
+ char sigstr[SIG_FORMATSIZE];
+
+ dns_name_format(name, namestr, sizeof namestr);
+ type_format(set->type, typestr, sizeof typestr);
+
+ ttl = ISC_MIN(set->ttl, endtime - starttime);
+
+ dns_rdataset_init(&sigset);
+ result = dns_db_findrdataset(gdb, node, gversion, dns_rdatatype_sig,
+ set->type, 0, &sigset, NULL);
+ if (result == ISC_R_NOTFOUND) {
+ result = ISC_R_SUCCESS;
+ nosigs = ISC_TRUE;
+ }
+ if (result != ISC_R_SUCCESS)
+ fatal("failed while looking for '%s SIG %s': %s",
+ namestr, typestr, isc_result_totext(result));
+
+ vbprintf(1, "%s/%s:\n", namestr, typestr);
+
+ arraysize = keycount;
+ if (!nosigs)
+ arraysize += dns_rdataset_count(&sigset);
+ wassignedby = isc_mem_get(mctx, arraysize * sizeof(isc_boolean_t));
+ nowsignedby = isc_mem_get(mctx, arraysize * sizeof(isc_boolean_t));
+ if (wassignedby == NULL || nowsignedby == NULL)
+ fatal("out of memory");
+
+ for (i = 0; i < arraysize; i++)
+ wassignedby[i] = nowsignedby[i] = ISC_FALSE;
+
+ if (nosigs)
+ result = ISC_R_NOMORE;
+ else
+ result = dns_rdataset_first(&sigset);
+
+ while (result == ISC_R_SUCCESS) {
+ isc_boolean_t expired, future;
+ isc_boolean_t keep = ISC_FALSE, resign = ISC_FALSE;
+
+ dns_rdataset_current(&sigset, &sigrdata);
+
+ result = dns_rdata_tostruct(&sigrdata, &sig, NULL);
+ check_result(result, "dns_rdata_tostruct");
+
+ expired = ISC_TF(now + cycle > sig.timeexpire);
+ future = ISC_TF(now < sig.timesigned);
+
+ key = keythatsigned(&sig);
+ sig_format(&sig, sigstr, sizeof sigstr);
+
+ if (sig.timesigned > sig.timeexpire) {
+ /* sig is dropped and not replaced */
+ vbprintf(2, "\tsig by %s dropped - "
+ "invalid validity period\n",
+ sigstr);
+ } else if (key == NULL && !future &&
+ expecttofindkey(&sig.signer))
+ {
+ /* sig is dropped and not replaced */
+ vbprintf(2, "\tsig by %s dropped - "
+ "private key not found\n",
+ sigstr);
+ } else if (key == NULL || future) {
+ vbprintf(2, "\tsig by %s %s - key not found\n",
+ expired ? "retained" : "dropped", sigstr);
+ if (!expired)
+ keep = ISC_TRUE;
+ } else if (issigningkey(key)) {
+ if (!expired && setverifies(name, set, key, &sigrdata))
+ {
+ vbprintf(2, "\tsig by %s retained\n", sigstr);
+ keep = ISC_TRUE;
+ wassignedby[key->position] = ISC_TRUE;
+ nowsignedby[key->position] = ISC_TRUE;
+ } else {
+ vbprintf(2, "\tsig by %s dropped - %s\n",
+ sigstr,
+ expired ? "expired" :
+ "failed to verify");
+ wassignedby[key->position] = ISC_TRUE;
+ resign = ISC_TRUE;
+ }
+ } else if (iszonekey(key)) {
+ if (!expired && setverifies(name, set, key, &sigrdata))
+ {
+ vbprintf(2, "\tsig by %s retained\n", sigstr);
+ keep = ISC_TRUE;
+ wassignedby[key->position] = ISC_TRUE;
+ nowsignedby[key->position] = ISC_TRUE;
+ } else {
+ vbprintf(2, "\tsig by %s dropped - %s\n",
+ sigstr,
+ expired ? "expired" :
+ "failed to verify");
+ wassignedby[key->position] = ISC_TRUE;
+ }
+ } else if (!expired) {
+ vbprintf(2, "\tsig by %s retained\n", sigstr);
+ keep = ISC_TRUE;
+ } else {
+ vbprintf(2, "\tsig by %s expired\n", sigstr);
+ }
+
+ if (keep) {
+ nowsignedby[key->position] = ISC_TRUE;
+ INCSTAT(nretained);
+ } else {
+ tuple = NULL;
+ result = dns_difftuple_create(mctx, DNS_DIFFOP_DEL,
+ name, sigset.ttl,
+ &sigrdata, &tuple);
+ check_result(result, "dns_difftuple_create");
+ dns_diff_append(diff, &tuple);
+ INCSTAT(ndropped);
+ }
+
+ if (resign) {
+ isc_buffer_t b;
+ dns_rdata_t trdata = DNS_RDATA_INIT;
+ unsigned char array[BUFSIZE];
+ char keystr[KEY_FORMATSIZE];
+
+ key_format(key->key, keystr, sizeof keystr);
+ vbprintf(1, "\tresigning with key %s\n", keystr);
+ isc_buffer_init(&b, array, sizeof(array));
+ signwithkey(name, set, &trdata, key->key, &b);
+ nowsignedby[key->position] = ISC_TRUE;
+ tuple = NULL;
+ result = dns_difftuple_create(mctx, DNS_DIFFOP_ADD,
+ name, ttl, &trdata,
+ &tuple);
+ check_result(result, "dns_difftuple_create");
+ dns_diff_append(diff, &tuple);
+ }
+
+ dns_rdata_reset(&sigrdata);
+ dns_rdata_freestruct(&sig);
+ result = dns_rdataset_next(&sigset);
+ }
+ if (result == ISC_R_NOMORE)
+ result = ISC_R_SUCCESS;
+
+ check_result(result, "dns_rdataset_first/next");
+ if (dns_rdataset_isassociated(&sigset))
+ dns_rdataset_disassociate(&sigset);
+
+ key = ISC_LIST_HEAD(keylist);
+ while (key != NULL) {
+ if (key->isdefault && !nowsignedby[key->position]) {
+ isc_buffer_t b;
+ dns_rdata_t trdata = DNS_RDATA_INIT;
+ unsigned char array[BUFSIZE];
+ char keystr[KEY_FORMATSIZE];
+
+ key_format(key->key, keystr, sizeof keystr);
+ vbprintf(1, "\tsigning with key %s\n", keystr);
+ isc_buffer_init(&b, array, sizeof(array));
+ signwithkey(name, set, &trdata, key->key, &b);
+ tuple = NULL;
+ result = dns_difftuple_create(mctx, DNS_DIFFOP_ADD,
+ name, ttl, &trdata,
+ &tuple);
+ check_result(result, "dns_difftuple_create");
+ dns_diff_append(diff, &tuple);
+ }
+ key = ISC_LIST_NEXT(key, link);
+ }
+
+ isc_mem_put(mctx, wassignedby, arraysize * sizeof(isc_boolean_t));
+ isc_mem_put(mctx, nowsignedby, arraysize * sizeof(isc_boolean_t));
+}
+
+/* Determine if a KEY set contains a null key */
+static isc_boolean_t
+hasnullkey(dns_rdataset_t *rdataset) {
+ isc_result_t result;
+ dns_rdata_t rdata = DNS_RDATA_INIT;
+ isc_boolean_t found = ISC_FALSE;
+
+ result = dns_rdataset_first(rdataset);
+ while (result == ISC_R_SUCCESS) {
+ dst_key_t *key = NULL;
+
+ dns_rdata_reset(&rdata);
+ dns_rdataset_current(rdataset, &rdata);
+ result = dns_dnssec_keyfromrdata(dns_rootname,
+ &rdata, mctx, &key);
+ if (result != ISC_R_SUCCESS)
+ fatal("could not convert KEY into internal format: %s",
+ isc_result_totext(result));
+ if (dst_key_isnullkey(key))
+ found = ISC_TRUE;
+ dst_key_free(&key);
+ if (found == ISC_TRUE)
+ return (ISC_TRUE);
+ result = dns_rdataset_next(rdataset);
+ }
+ if (result != ISC_R_NOMORE)
+ fatal("failure looking for null keys");
+ return (ISC_FALSE);
+}
+
+static void
+opendb(const char *prefix, dns_name_t *name, dns_rdataclass_t rdclass,
+ dns_db_t **dbp)
+{
+ char filename[256];
+ isc_buffer_t b;
+ isc_result_t result;
+
+ isc_buffer_init(&b, filename, sizeof(filename));
+ if (directory != NULL) {
+ isc_buffer_putstr(&b, directory);
+ if (directory[strlen(directory) - 1] != '/')
+ isc_buffer_putstr(&b, "/");
+ }
+ isc_buffer_putstr(&b, prefix);
+ result = dns_name_tofilenametext(name, ISC_FALSE, &b);
+ check_result(result, "dns_name_tofilenametext()");
+ if (isc_buffer_availablelength(&b) == 0) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ dns_name_format(name, namestr, sizeof namestr);
+ fatal("name '%s' is too long", namestr);
+ }
+ isc_buffer_putuint8(&b, 0);
+
+ result = dns_db_create(mctx, "rbt", dns_rootname, dns_dbtype_zone,
+ rdclass, 0, NULL, dbp);
+ check_result(result, "dns_db_create()");
+
+ result = dns_db_load(*dbp, filename);
+ if (result != ISC_R_SUCCESS && result != DNS_R_SEENINCLUDE)
+ dns_db_detach(dbp);
+}
+
+/*
+ * Looks for signatures of the zone keys by the parent, and imports them
+ * if found.
+ */
+static void
+importparentsig(dns_diff_t *diff, dns_name_t *name, dns_rdataset_t *set) {
+ dns_db_t *newdb = NULL;
+ dns_dbnode_t *newnode = NULL;
+ dns_rdataset_t newset, sigset;
+ dns_rdata_t rdata = DNS_RDATA_INIT, newrdata = DNS_RDATA_INIT;
+ isc_result_t result;
+
+ dns_rdataset_init(&newset);
+ dns_rdataset_init(&sigset);
+
+ opendb("signedkey-", name, dns_db_class(gdb), &newdb);
+ if (newdb == NULL)
+ return;
+
+ result = dns_db_findnode(newdb, name, ISC_FALSE, &newnode);
+ if (result != ISC_R_SUCCESS)
+ goto failure;
+ result = dns_db_findrdataset(newdb, newnode, NULL, dns_rdatatype_key,
+ 0, 0, &newset, &sigset);
+ if (result != ISC_R_SUCCESS)
+ goto failure;
+
+ if (!dns_rdataset_isassociated(&newset) ||
+ !dns_rdataset_isassociated(&sigset))
+ goto failure;
+
+ if (dns_rdataset_count(set) != dns_rdataset_count(&newset)) {
+ result = DNS_R_BADDB;
+ goto failure;
+ }
+
+ result = dns_rdataset_first(set);
+ check_result(result, "dns_rdataset_first()");
+ for (; result == ISC_R_SUCCESS; result = dns_rdataset_next(set)) {
+ dns_rdataset_current(set, &rdata);
+ result = dns_rdataset_first(&newset);
+ check_result(result, "dns_rdataset_first()");
+ for (;
+ result == ISC_R_SUCCESS;
+ result = dns_rdataset_next(&newset))
+ {
+ dns_rdataset_current(&newset, &newrdata);
+ if (dns_rdata_compare(&rdata, &newrdata) == 0)
+ break;
+ dns_rdata_reset(&newrdata);
+ }
+ dns_rdata_reset(&newrdata);
+ dns_rdata_reset(&rdata);
+ if (result != ISC_R_SUCCESS)
+ break;
+ }
+ if (result != ISC_R_NOMORE)
+ goto failure;
+
+ vbprintf(2, "found the parent's signature of our zone key\n");
+
+ result = dns_rdataset_first(&sigset);
+ while (result == ISC_R_SUCCESS) {
+ dns_difftuple_t *tuple = NULL;
+
+ dns_rdataset_current(&sigset, &rdata);
+ result = dns_difftuple_create(mctx, DNS_DIFFOP_ADD, name,
+ sigset.ttl, &rdata, &tuple);
+ check_result(result, "dns_difftuple_create");
+ dns_diff_append(diff, &tuple);
+ result = dns_rdataset_next(&sigset);
+ dns_rdata_reset(&rdata);
+ }
+ if (result == ISC_R_NOMORE)
+ result = ISC_R_SUCCESS;
+
+ failure:
+ if (dns_rdataset_isassociated(&newset))
+ dns_rdataset_disassociate(&newset);
+ if (dns_rdataset_isassociated(&sigset))
+ dns_rdataset_disassociate(&sigset);
+ if (newnode != NULL)
+ dns_db_detachnode(newdb, &newnode);
+ if (newdb != NULL)
+ dns_db_detach(&newdb);
+ if (result != ISC_R_SUCCESS)
+ fatal("zone signedkey file is invalid or does not match zone");
+}
+
+/*
+ * Looks for our signatures of child keys. If present, inform the caller.
+ */
+static isc_boolean_t
+haschildkey(dns_name_t *name) {
+ dns_db_t *newdb = NULL;
+ dns_dbnode_t *newnode = NULL;
+ dns_rdataset_t set, sigset;
+ dns_rdata_t sigrdata = DNS_RDATA_INIT;
+ isc_result_t result;
+ isc_boolean_t found = ISC_FALSE;
+ dns_rdata_sig_t sig;
+ signer_key_t *key;
+
+ dns_rdataset_init(&set);
+ dns_rdataset_init(&sigset);
+
+ opendb("signedkey-", name, dns_db_class(gdb), &newdb);
+ if (newdb == NULL)
+ return (ISC_FALSE);
+
+ result = dns_db_findnode(newdb, name, ISC_FALSE, &newnode);
+ if (result != ISC_R_SUCCESS)
+ goto failure;
+ result = dns_db_findrdataset(newdb, newnode, NULL, dns_rdatatype_key,
+ 0, 0, &set, &sigset);
+ if (result != ISC_R_SUCCESS)
+ goto failure;
+
+ if (!dns_rdataset_isassociated(&set) ||
+ !dns_rdataset_isassociated(&sigset))
+ goto failure;
+
+ result = dns_rdataset_first(&sigset);
+ check_result(result, "dns_rdataset_first()");
+ dns_rdata_init(&sigrdata);
+ for (; result == ISC_R_SUCCESS; result = dns_rdataset_next(&sigset)) {
+ dns_rdataset_current(&sigset, &sigrdata);
+ result = dns_rdata_tostruct(&sigrdata, &sig, NULL);
+ if (result != ISC_R_SUCCESS)
+ goto failure;
+ key = keythatsigned(&sig);
+ dns_rdata_freestruct(&sig);
+ if (key == NULL) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ dns_name_format(name, namestr, sizeof namestr);
+ fprintf(stderr,
+ "creating KEY from signedkey file for %s: "
+ "%s\n",
+ namestr, isc_result_totext(result));
+ goto failure;
+ }
+ result = dns_dnssec_verify(name, &set, key->key,
+ ISC_FALSE, mctx, &sigrdata);
+ if (result == ISC_R_SUCCESS) {
+ found = ISC_TRUE;
+ break;
+ } else {
+ char namestr[DNS_NAME_FORMATSIZE];
+ dns_name_format(name, namestr, sizeof namestr);
+ fprintf(stderr,
+ "verifying SIG in signedkey file for %s: %s\n",
+ namestr, isc_result_totext(result));
+ }
+ dns_rdata_reset(&sigrdata);
+ }
+
+ failure:
+ if (dns_rdataset_isassociated(&set))
+ dns_rdataset_disassociate(&set);
+ if (dns_rdataset_isassociated(&sigset))
+ dns_rdataset_disassociate(&sigset);
+ if (newnode != NULL)
+ dns_db_detachnode(newdb, &newnode);
+ if (newdb != NULL)
+ dns_db_detach(&newdb);
+
+ return (found);
+}
+
+/*
+ * There probably should be a dns_nxt_setbit, but it can get complicated if
+ * the length of the bit set needs to be increased. In this case, since the
+ * NXT bit is set and both SIG and KEY are less than NXT, the easy way works.
+ */
+static void
+nxt_setbit(dns_rdataset_t *rdataset, dns_rdatatype_t type) {
+ isc_result_t result;
+ dns_rdata_t rdata = DNS_RDATA_INIT;
+ dns_rdata_nxt_t nxt;
+
+ result = dns_rdataset_first(rdataset);
+ check_result(result, "dns_rdataset_first()");
+ dns_rdataset_current(rdataset, &rdata);
+ result = dns_rdata_tostruct(&rdata, &nxt, NULL);
+ check_result(result, "dns_rdata_tostruct");
+ set_bit(nxt.typebits, type, 1);
+ dns_rdata_freestruct(&nxt);
+}
+
+static void
+createnullkey(dns_db_t *db, dns_dbversion_t *version, dns_name_t *name,
+ dns_ttl_t ttl)
+{
+ unsigned char keydata[4];
+ dns_rdata_t keyrdata = DNS_RDATA_INIT;
+ dns_rdata_key_t key;
+ dns_diff_t diff;
+ dns_difftuple_t *tuple = NULL;
+ isc_buffer_t b;
+ isc_result_t result;
+ char namestr[DNS_NAME_FORMATSIZE];
+
+ dns_name_format(name, namestr, sizeof namestr);
+ vbprintf(2, "adding null key at %s\n", namestr);
+
+ key.common.rdclass = dns_db_class(db);
+ key.common.rdtype = dns_rdatatype_key;
+ ISC_LINK_INIT(&key.common, link);
+ key.mctx = NULL;
+ key.flags = DNS_KEYTYPE_NOKEY | DNS_KEYOWNER_ZONE;
+ key.protocol = DNS_KEYPROTO_DNSSEC;
+ key.algorithm = DNS_KEYALG_DSA;
+ key.datalen = 0;
+ key.data = NULL;
+ isc_buffer_init(&b, keydata, sizeof keydata);
+ result = dns_rdata_fromstruct(&keyrdata, dns_db_class(db),
+ dns_rdatatype_key, &key, &b);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to build null key");
+
+ dns_diff_init(mctx, &diff);
+
+ result = dns_difftuple_create(mctx, DNS_DIFFOP_ADD, name, ttl,
+ &keyrdata, &tuple);
+ check_result(result, "dns_difftuple_create");
+
+ dns_diff_append(&diff, &tuple);
+
+ result = dns_diff_apply(&diff, db, version);
+ check_result(result, "dns_diff_apply");
+
+ dns_diff_clear(&diff);
+}
+
+/*
+ * Signs all records at a name. This mostly just signs each set individually,
+ * but also adds the SIG bit to any NXTs generated earlier, deals with
+ * parent/child KEY signatures, and handles other exceptional cases.
+ */
+static void
+signname(dns_dbnode_t *node, dns_name_t *name) {
+ isc_result_t result;
+ dns_rdataset_t rdataset;
+ dns_rdatasetiter_t *rdsiter;
+ isc_boolean_t isdelegation = ISC_FALSE;
+ isc_boolean_t childkey = ISC_FALSE;
+ static int warnwild = 0;
+ isc_boolean_t atorigin;
+ isc_boolean_t neednullkey = ISC_FALSE;
+ dns_diff_t diff;
+
+ if (dns_name_iswildcard(name)) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ dns_name_format(name, namestr, sizeof namestr);
+ if (warnwild++ == 0) {
+ fprintf(stderr, "%s: warning: BIND 9 doesn't properly "
+ "handle wildcards in secure zones:\n",
+ program);
+ fprintf(stderr, "\t- wildcard nonexistence proof is "
+ "not generated by the server\n");
+ fprintf(stderr, "\t- wildcard nonexistence proof is "
+ "not required by the resolver\n");
+ }
+ fprintf(stderr, "%s: warning: wildcard name seen: %s\n",
+ program, namestr);
+ }
+
+ atorigin = dns_name_equal(name, gorigin);
+
+ /*
+ * If this is not the origin, determine if it's a delegation point.
+ */
+ if (!atorigin) {
+ dns_rdataset_t nsset;
+
+ dns_rdataset_init(&nsset);
+ result = dns_db_findrdataset(gdb, node, gversion,
+ dns_rdatatype_ns, 0, 0, &nsset,
+ NULL);
+ /* Is this a delegation point? */
+ if (result == ISC_R_SUCCESS) {
+ isdelegation = ISC_TRUE;
+ dns_rdataset_disassociate(&nsset);
+ }
+ }
+
+ /*
+ * If this is a delegation point, determine if we need to generate
+ * a null key.
+ */
+ if (isdelegation) {
+ dns_rdataset_t keyset;
+ dns_ttl_t nullkeyttl;
+
+ childkey = haschildkey(name);
+ neednullkey = ISC_TRUE;
+ nullkeyttl = zonettl;
+
+ dns_rdataset_init(&keyset);
+ result = dns_db_findrdataset(gdb, node, gversion,
+ dns_rdatatype_key, 0, 0, &keyset,
+ NULL);
+ if (result == ISC_R_SUCCESS && childkey) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ dns_name_format(name, namestr, sizeof namestr);
+ if (hasnullkey(&keyset)) {
+ fatal("%s has both a signedkey file and "
+ "null keys in the zone. Aborting.",
+ namestr);
+ }
+ vbprintf(2, "child key for %s found\n", namestr);
+ neednullkey = ISC_FALSE;
+ dns_rdataset_disassociate(&keyset);
+ }
+ else if (result == ISC_R_SUCCESS) {
+ if (hasnullkey(&keyset))
+ neednullkey = ISC_FALSE;
+ nullkeyttl = keyset.ttl;
+ dns_rdataset_disassociate(&keyset);
+ } else if (childkey) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ dns_name_format(name, namestr, sizeof namestr);
+ vbprintf(2, "child key for %s found\n", namestr);
+ neednullkey = ISC_FALSE;
+ }
+
+ if (neednullkey)
+ createnullkey(gdb, gversion, name, nullkeyttl);
+ }
+
+ /*
+ * Now iterate through the rdatasets.
+ */
+ dns_diff_init(mctx, &diff);
+ dns_rdataset_init(&rdataset);
+ rdsiter = NULL;
+ result = dns_db_allrdatasets(gdb, node, gversion, 0, &rdsiter);
+ check_result(result, "dns_db_allrdatasets()");
+ result = dns_rdatasetiter_first(rdsiter);
+ while (result == ISC_R_SUCCESS) {
+ dns_rdatasetiter_current(rdsiter, &rdataset);
+
+ /* If this is a SIG set, skip it. */
+ if (rdataset.type == dns_rdatatype_sig)
+ goto skip;
+
+ /*
+ * If this is a KEY set at the apex, look for a signedkey file.
+ */
+ if (atorigin && rdataset.type == dns_rdatatype_key) {
+ importparentsig(&diff, name, &rdataset);
+ goto skip;
+ }
+
+ /*
+ * If this name is a delegation point, skip all records
+ * except an NXT set a KEY set containing a null key.
+ */
+ if (isdelegation) {
+ if (!(rdataset.type == dns_rdatatype_nxt ||
+ (rdataset.type == dns_rdatatype_key &&
+ hasnullkey(&rdataset))))
+ goto skip;
+ }
+
+ if (rdataset.type == dns_rdatatype_nxt) {
+ if (!nokeys)
+ nxt_setbit(&rdataset, dns_rdatatype_sig);
+ if (neednullkey)
+ nxt_setbit(&rdataset, dns_rdatatype_key);
+ }
+
+ signset(&diff, node, name, &rdataset);
+
+ skip:
+ dns_rdataset_disassociate(&rdataset);
+ result = dns_rdatasetiter_next(rdsiter);
+ }
+ if (result != ISC_R_NOMORE) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ dns_name_format(name, namestr, sizeof namestr);
+ fatal("rdataset iteration for name '%s' failed: %s",
+ namestr, isc_result_totext(result));
+ }
+ dns_rdatasetiter_destroy(&rdsiter);
+
+ result = dns_diff_apply(&diff, gdb, gversion);
+ if (result != ISC_R_SUCCESS) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ dns_name_format(name, namestr, sizeof namestr);
+ fatal("failed to add SIGs at node '%s': %s",
+ namestr, isc_result_totext(result));
+ }
+ dns_diff_clear(&diff);
+}
+
+static inline isc_boolean_t
+active_node(dns_dbnode_t *node) {
+ dns_rdatasetiter_t *rdsiter;
+ isc_boolean_t active = ISC_FALSE;
+ isc_result_t result;
+ dns_rdataset_t rdataset;
+
+ dns_rdataset_init(&rdataset);
+ rdsiter = NULL;
+ result = dns_db_allrdatasets(gdb, node, gversion, 0, &rdsiter);
+ check_result(result, "dns_db_allrdatasets()");
+ result = dns_rdatasetiter_first(rdsiter);
+ while (result == ISC_R_SUCCESS) {
+ dns_rdatasetiter_current(rdsiter, &rdataset);
+ if (rdataset.type != dns_rdatatype_nxt)
+ active = ISC_TRUE;
+ dns_rdataset_disassociate(&rdataset);
+ if (!active)
+ result = dns_rdatasetiter_next(rdsiter);
+ else
+ result = ISC_R_NOMORE;
+ }
+ if (result != ISC_R_NOMORE)
+ fatal("rdataset iteration failed: %s",
+ isc_result_totext(result));
+ dns_rdatasetiter_destroy(&rdsiter);
+
+ if (!active) {
+ /*
+ * Make sure there is no NXT record for this node.
+ */
+ result = dns_db_deleterdataset(gdb, node, gversion,
+ dns_rdatatype_nxt, 0);
+ if (result == DNS_R_UNCHANGED)
+ result = ISC_R_SUCCESS;
+ check_result(result, "dns_db_deleterdataset");
+ }
+
+ return (active);
+}
+
+static inline isc_result_t
+next_active(dns_name_t *name, dns_dbnode_t **nodep) {
+ isc_result_t result;
+ isc_boolean_t active;
+
+ do {
+ active = ISC_FALSE;
+ result = dns_dbiterator_current(gdbiter, nodep, name);
+ if (result == ISC_R_SUCCESS) {
+ active = active_node(*nodep);
+ if (!active) {
+ dns_db_detachnode(gdb, nodep);
+ result = dns_dbiterator_next(gdbiter);
+ }
+ }
+ } while (result == ISC_R_SUCCESS && !active);
+
+ return (result);
+}
+
+static inline isc_result_t
+next_nonglue(dns_name_t *name, dns_dbnode_t **nodep, dns_name_t *origin,
+ dns_name_t *lastcut)
+{
+ isc_result_t result;
+
+ do {
+ result = next_active(name, nodep);
+ if (result == ISC_R_SUCCESS) {
+ if (dns_name_issubdomain(name, origin) &&
+ (lastcut == NULL ||
+ !dns_name_issubdomain(name, lastcut)))
+ return (ISC_R_SUCCESS);
+ result = dns_master_dumpnodetostream(mctx, gdb,
+ gversion,
+ *nodep, name,
+ masterstyle, fp);
+ check_result(result, "dns_master_dumpnodetostream");
+ dns_db_detachnode(gdb, nodep);
+ result = dns_dbiterator_next(gdbiter);
+ }
+ } while (result == ISC_R_SUCCESS);
+ return (result);
+}
+
+/*
+ * Extracts the TTL from the SOA.
+ */
+static dns_ttl_t
+soattl(void) {
+ dns_rdataset_t soaset;
+ dns_fixedname_t fname;
+ dns_name_t *name;
+ isc_result_t result;
+ dns_ttl_t ttl;
+
+ dns_fixedname_init(&fname);
+ name = dns_fixedname_name(&fname);
+ dns_rdataset_init(&soaset);
+ result = dns_db_find(gdb, gorigin, gversion, dns_rdatatype_soa,
+ 0, 0, NULL, name, &soaset, NULL);
+ if (result != ISC_R_SUCCESS) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ dns_name_format(name, namestr, sizeof namestr);
+ fatal("failed to find '%s SOA' in the zone: %s",
+ namestr, isc_result_totext(result));
+ }
+ ttl = soaset.ttl;
+ dns_rdataset_disassociate(&soaset);
+ return (ttl);
+}
+
+/*
+ * Delete any SIG records at a node.
+ */
+static void
+cleannode(dns_db_t *db, dns_dbversion_t *version, dns_dbnode_t *node) {
+ dns_rdatasetiter_t *rdsiter = NULL;
+ dns_rdataset_t set;
+ isc_result_t result, dresult;
+
+ dns_rdataset_init(&set);
+ result = dns_db_allrdatasets(db, node, version, 0, &rdsiter);
+ check_result(result, "dns_db_allrdatasets");
+ result = dns_rdatasetiter_first(rdsiter);
+ while (result == ISC_R_SUCCESS) {
+ isc_boolean_t destroy = ISC_FALSE;
+ dns_rdatatype_t covers = 0;
+ dns_rdatasetiter_current(rdsiter, &set);
+ if (set.type == dns_rdatatype_sig) {
+ covers = set.covers;
+ destroy = ISC_TRUE;
+ }
+ dns_rdataset_disassociate(&set);
+ result = dns_rdatasetiter_next(rdsiter);
+ if (destroy) {
+ dresult = dns_db_deleterdataset(db, node, version,
+ dns_rdatatype_sig,
+ covers);
+ check_result(dresult, "dns_db_deleterdataset");
+ }
+ }
+ if (result != ISC_R_NOMORE)
+ fatal("rdataset iteration failed: %s",
+ isc_result_totext(result));
+ dns_rdatasetiter_destroy(&rdsiter);
+}
+
+/*
+ * Set up the iterator and global state before starting the tasks.
+ */
+static void
+presign(void) {
+ isc_result_t result;
+
+ gdbiter = NULL;
+ result = dns_db_createiterator(gdb, ISC_FALSE, &gdbiter);
+ check_result(result, "dns_db_createiterator()");
+
+ result = dns_dbiterator_first(gdbiter);
+ check_result(result, "dns_dbiterator_first()");
+
+ lastzonecut = NULL;
+
+ zonettl = soattl();
+
+}
+
+/*
+ * Clean up the iterator and global state after the tasks complete.
+ */
+static void
+postsign(void) {
+ if (lastzonecut != NULL) {
+ dns_name_free(lastzonecut, mctx);
+ isc_mem_put(mctx, lastzonecut, sizeof(dns_name_t));
+ }
+ dns_dbiterator_destroy(&gdbiter);
+}
+
+/*
+ * Find the next name to nxtify & sign
+ */
+static isc_result_t
+getnextname(dns_name_t *name, dns_name_t *nextname, dns_dbnode_t **nodep) {
+ isc_result_t result;
+ dns_dbnode_t *nextnode, *curnode;
+
+ LOCK(&namelock);
+
+ if (shuttingdown || finished) {
+ result = ISC_R_NOMORE;
+ if (gnode != NULL)
+ dns_db_detachnode(gdb, &gnode);
+ goto out;
+ }
+
+ if (gnode == NULL) {
+ dns_fixedname_t ftname;
+ dns_name_t *tname;
+
+ dns_fixedname_init(&ftname);
+ tname = dns_fixedname_name(&ftname);
+
+ result = next_nonglue(tname, &gnode, gorigin, lastzonecut);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to iterate through the zone");
+ }
+
+ nextnode = NULL;
+ curnode = NULL;
+ dns_dbiterator_current(gdbiter, &curnode, name);
+ if (!dns_name_equal(name, gorigin)) {
+ dns_rdatasetiter_t *rdsiter = NULL;
+ dns_rdataset_t set;
+
+ dns_rdataset_init(&set);
+ result = dns_db_allrdatasets(gdb, curnode, gversion, 0,
+ &rdsiter);
+ check_result(result, "dns_db_allrdatasets");
+ result = dns_rdatasetiter_first(rdsiter);
+ while (result == ISC_R_SUCCESS) {
+ dns_rdatasetiter_current(rdsiter, &set);
+ if (set.type == dns_rdatatype_ns) {
+ dns_rdataset_disassociate(&set);
+ break;
+ }
+ dns_rdataset_disassociate(&set);
+ result = dns_rdatasetiter_next(rdsiter);
+ }
+ if (result != ISC_R_SUCCESS && result != ISC_R_NOMORE)
+ fatal("rdataset iteration failed: %s",
+ isc_result_totext(result));
+ if (result == ISC_R_SUCCESS) {
+ if (lastzonecut != NULL)
+ dns_name_free(lastzonecut, mctx);
+ else {
+ lastzonecut = isc_mem_get(mctx,
+ sizeof(dns_name_t));
+ if (lastzonecut == NULL)
+ fatal("out of memory");
+ }
+ dns_name_init(lastzonecut, NULL);
+ result = dns_name_dup(name, mctx, lastzonecut);
+ check_result(result, "dns_name_dup()");
+ }
+ dns_rdatasetiter_destroy(&rdsiter);
+ }
+ result = dns_dbiterator_next(gdbiter);
+ if (result == ISC_R_SUCCESS)
+ result = next_nonglue(nextname, &nextnode, gorigin,
+ lastzonecut);
+ if (result == ISC_R_NOMORE) {
+ dns_name_clone(gorigin, nextname);
+ finished = ISC_TRUE;
+ result = ISC_R_SUCCESS;
+ } else if (result != ISC_R_SUCCESS)
+ fatal("iterating through the database failed: %s",
+ isc_result_totext(result));
+ dns_db_detachnode(gdb, &curnode);
+
+ *nodep = gnode;
+ gnode = nextnode;
+
+ out:
+ UNLOCK(&namelock);
+ return (result);
+}
+
+/*
+ * Assigns a node to a worker thread. This is protected by the master task's
+ * lock.
+ */
+static void
+assignwork(isc_task_t *task, isc_task_t *worker) {
+ dns_fixedname_t *fname, *fnextname;
+ dns_dbnode_t *node;
+ sevent_t *sevent;
+ isc_result_t result;
+
+ fname = isc_mem_get(mctx, sizeof(dns_fixedname_t));
+ fnextname = isc_mem_get(mctx, sizeof(dns_fixedname_t));
+ if (fname == NULL || fnextname == NULL)
+ fatal("out of memory");
+ dns_fixedname_init(fname);
+ dns_fixedname_init(fnextname);
+ node = NULL;
+ result = getnextname(dns_fixedname_name(fname),
+ dns_fixedname_name(fnextname), &node);
+ if (result == ISC_R_NOMORE) {
+ isc_mem_put(mctx, fname, sizeof(dns_fixedname_t));
+ isc_mem_put(mctx, fnextname, sizeof(dns_fixedname_t));
+ if (assigned == completed) {
+ isc_task_detach(&task);
+ isc_app_shutdown();
+ }
+ return;
+ }
+ sevent = (sevent_t *)
+ isc_event_allocate(mctx, task, SIGNER_EVENT_WORK,
+ sign, NULL, sizeof(sevent_t));
+ if (sevent == NULL)
+ fatal("failed to allocate event\n");
+
+ sevent->node = node;
+ sevent->fname = fname;
+ sevent->fnextname = fnextname;
+ isc_task_send(worker, (isc_event_t **)&sevent);
+ assigned++;
+}
+
+/*
+ * Start a worker task
+ */
+static void
+startworker(isc_task_t *task, isc_event_t *event) {
+ isc_task_t *worker;
+
+ worker = (isc_task_t *)event->ev_arg;
+ assignwork(task, worker);
+ isc_event_free(&event);
+}
+
+/*
+ * Write a node to the output file, and restart the worker task.
+ */
+static void
+writenode(isc_task_t *task, isc_event_t *event) {
+ isc_result_t result;
+ isc_task_t *worker;
+ sevent_t *sevent = (sevent_t *)event;
+
+ completed++;
+ worker = (isc_task_t *)event->ev_sender;
+ result = dns_master_dumpnodetostream(mctx, gdb, gversion,
+ sevent->node,
+ dns_fixedname_name(sevent->fname),
+ masterstyle, fp);
+ check_result(result, "dns_master_dumpnodetostream");
+ cleannode(gdb, gversion, sevent->node);
+ dns_db_detachnode(gdb, &sevent->node);
+ isc_mem_put(mctx, sevent->fname, sizeof(dns_fixedname_t));
+ assignwork(task, worker);
+ isc_event_free(&event);
+}
+
+/*
+ * Sign and nxtify a database node.
+ */
+static void
+sign(isc_task_t *task, isc_event_t *event) {
+ dns_fixedname_t *fname, *fnextname;
+ dns_dbnode_t *node;
+ sevent_t *sevent, *wevent;
+ isc_result_t result;
+
+ sevent = (sevent_t *)event;
+ node = sevent->node;
+ fname = sevent->fname;
+ fnextname = sevent->fnextname;
+ isc_event_free(&event);
+
+ result = dns_nxt_build(gdb, gversion, node,
+ dns_fixedname_name(fnextname), zonettl);
+ check_result(result, "dns_nxt_build()");
+ isc_mem_put(mctx, fnextname, sizeof(dns_fixedname_t));
+ signname(node, dns_fixedname_name(fname));
+ wevent = (sevent_t *)
+ isc_event_allocate(mctx, task, SIGNER_EVENT_WRITE,
+ writenode, NULL, sizeof(sevent_t));
+ if (wevent == NULL)
+ fatal("failed to allocate event\n");
+ wevent->node = node;
+ wevent->fname = fname;
+ isc_task_send(master, (isc_event_t **)&wevent);
+}
+
+/*
+ * Load the zone file from disk
+ */
+static void
+loadzone(char *file, char *origin, dns_rdataclass_t rdclass, dns_db_t **db) {
+ isc_buffer_t b;
+ int len;
+ dns_fixedname_t fname;
+ dns_name_t *name;
+ isc_result_t result;
+
+ len = strlen(origin);
+ isc_buffer_init(&b, origin, len);
+ isc_buffer_add(&b, len);
+
+ dns_fixedname_init(&fname);
+ name = dns_fixedname_name(&fname);
+ result = dns_name_fromtext(name, &b, dns_rootname, ISC_FALSE, NULL);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed converting name '%s' to dns format: %s",
+ origin, isc_result_totext(result));
+
+ result = dns_db_create(mctx, "rbt", name, dns_dbtype_zone,
+ rdclass, 0, NULL, db);
+ check_result(result, "dns_db_create()");
+
+ result = dns_db_load(*db, file);
+ if (result != ISC_R_SUCCESS && result != DNS_R_SEENINCLUDE)
+ fatal("failed loading zone from '%s': %s",
+ file, isc_result_totext(result));
+}
+
+/*
+ * Finds all public zone keys in the zone, and attempts to load the
+ * private keys from disk.
+ */
+static void
+loadzonekeys(dns_db_t *db) {
+ dns_dbnode_t *node;
+ dns_dbversion_t *currentversion;
+ isc_result_t result;
+ dst_key_t *keys[20];
+ unsigned int nkeys, i;
+
+ currentversion = NULL;
+ dns_db_currentversion(db, &currentversion);
+
+ node = NULL;
+ result = dns_db_findnode(db, gorigin, ISC_FALSE, &node);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to find the zone's origin: %s",
+ isc_result_totext(result));
+
+ result = dns_dnssec_findzonekeys(db, currentversion, node, gorigin,
+ mctx, 20, keys, &nkeys);
+ if (result == ISC_R_NOTFOUND)
+ result = ISC_R_SUCCESS;
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to find the zone keys: %s",
+ isc_result_totext(result));
+
+ for (i = 0; i < nkeys; i++) {
+ signer_key_t *key;
+
+ key = newkeystruct(keys[i], ISC_FALSE);
+ ISC_LIST_APPEND(keylist, key, link);
+ }
+ dns_db_detachnode(db, &node);
+ dns_db_closeversion(db, &currentversion, ISC_FALSE);
+}
+
+/*
+ * Finds all public zone keys in the zone.
+ */
+static void
+loadzonepubkeys(dns_db_t *db) {
+ dns_dbversion_t *currentversion = NULL;
+ dns_dbnode_t *node = NULL;
+ dns_rdataset_t rdataset;
+ dns_rdata_t rdata = DNS_RDATA_INIT;
+ dst_key_t *pubkey;
+ signer_key_t *key;
+ isc_result_t result;
+
+ dns_db_currentversion(db, &currentversion);
+
+ result = dns_db_findnode(db, gorigin, ISC_FALSE, &node);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to find the zone's origin: %s",
+ isc_result_totext(result));
+
+ dns_rdataset_init(&rdataset);
+ result = dns_db_findrdataset(db, node, currentversion,
+ dns_rdatatype_key, 0, 0, &rdataset, NULL);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to find keys at the zone apex: %s",
+ isc_result_totext(result));
+ result = dns_rdataset_first(&rdataset);
+ check_result(result, "dns_rdataset_first");
+ while (result == ISC_R_SUCCESS) {
+ pubkey = NULL;
+ dns_rdata_reset(&rdata);
+ dns_rdataset_current(&rdataset, &rdata);
+ result = dns_dnssec_keyfromrdata(gorigin, &rdata, mctx,
+ &pubkey);
+ if (result != ISC_R_SUCCESS)
+ goto next;
+ if (!dst_key_iszonekey(pubkey)) {
+ dst_key_free(&pubkey);
+ goto next;
+ }
+
+ key = newkeystruct(pubkey, ISC_FALSE);
+ ISC_LIST_APPEND(keylist, key, link);
+ next:
+ result = dns_rdataset_next(&rdataset);
+ }
+ dns_rdataset_disassociate(&rdataset);
+ dns_db_detachnode(db, &node);
+ dns_db_closeversion(db, &currentversion, ISC_FALSE);
+}
+
+static void
+print_time(FILE *fp) {
+ time_t currenttime;
+
+ currenttime = time(NULL);
+ fprintf(fp, "; File written on %s", ctime(&currenttime));
+}
+
+static void
+print_version(FILE *fp) {
+ fprintf(fp, "; dnssec_signzone version " VERSION "\n");
+}
+
+static void
+usage(void) {
+ fprintf(stderr, "Usage:\n");
+ fprintf(stderr, "\t%s [options] zonefile [keys]\n", program);
+
+ fprintf(stderr, "\n");
+
+ fprintf(stderr, "Options: (default value in parenthesis) \n");
+ fprintf(stderr, "\t-c class (IN)\n");
+ fprintf(stderr, "\t-d directory\n");
+ fprintf(stderr, "\t\tdirectory to find signedkey files (.)\n");
+ fprintf(stderr, "\t-s YYYYMMDDHHMMSS|+offset:\n");
+ fprintf(stderr, "\t\tSIG start time - absolute|offset (now)\n");
+ fprintf(stderr, "\t-e YYYYMMDDHHMMSS|+offset|\"now\"+offset]:\n");
+ fprintf(stderr, "\t\tSIG end time - absolute|from start|from now "
+ "(now + 30 days)\n");
+ fprintf(stderr, "\t-i interval:\n");
+ fprintf(stderr, "\t\tcycle interval - resign "
+ "if < interval from end ( (end-start)/4 )\n");
+ fprintf(stderr, "\t-v debuglevel (0)\n");
+ fprintf(stderr, "\t-o origin:\n");
+ fprintf(stderr, "\t\tzone origin (name of zonefile)\n");
+ fprintf(stderr, "\t-f outfile:\n");
+ fprintf(stderr, "\t\tfile the signed zone is written in "
+ "(zonefile + .signed)\n");
+ fprintf(stderr, "\t-r randomdev:\n");
+ fprintf(stderr, "\t\ta file containing random data\n");
+ fprintf(stderr, "\t-a:\t");
+ fprintf(stderr, "verify generated signatures\n");
+ fprintf(stderr, "\t-p:\t");
+ fprintf(stderr, "use pseudorandom data (faster but less secure)\n");
+ fprintf(stderr, "\t-t:\t");
+ fprintf(stderr, "print statistics\n");
+ fprintf(stderr, "\t-n ncpus (number of cpus present)\n");
+
+ fprintf(stderr, "\n");
+
+ fprintf(stderr, "Signing Keys: ");
+ fprintf(stderr, "(default: all zone keys that have private keys)\n");
+ fprintf(stderr, "\tkeyfile (Kname+alg+tag)\n");
+ exit(0);
+}
+
+static void
+removetempfile(void) {
+ if (removefile)
+ isc_file_remove(tempfile);
+}
+
+int
+main(int argc, char *argv[]) {
+ int i, ch;
+ char *startstr = NULL, *endstr = NULL, *classname = NULL;
+ char *origin = NULL, *file = NULL, *output = NULL;
+ char *randomfile = NULL;
+ char *endp;
+ isc_time_t timer_start, timer_finish;
+ signer_key_t *key;
+ isc_result_t result;
+ isc_log_t *log = NULL;
+ isc_boolean_t pseudorandom = ISC_FALSE;
+ unsigned int eflags;
+ isc_boolean_t free_output = ISC_FALSE;
+ int tempfilelen;
+ dns_rdataclass_t rdclass;
+ isc_textregion_t r;
+ isc_task_t **tasks = NULL;
+ masterstyle = &dns_master_style_explicitttl;
+
+ check_result(isc_app_start(), "isc_app_start");
+
+ result = isc_mem_create(0, 0, &mctx);
+ if (result != ISC_R_SUCCESS)
+ fatal("out of memory");
+
+ dns_result_register();
+
+ while ((ch = isc_commandline_parse(argc, argv,
+ "c:s:e:i:v:o:f:ahpr:td:n:"))
+ != -1) {
+ switch (ch) {
+ case 'c':
+ classname = isc_commandline_argument;
+ break;
+
+ case 's':
+ startstr = isc_commandline_argument;
+ break;
+
+ case 'e':
+ endstr = isc_commandline_argument;
+ break;
+
+ case 'i':
+ endp = NULL;
+ cycle = strtol(isc_commandline_argument, &endp, 0);
+ if (*endp != '\0' || cycle < 0)
+ fatal("cycle period must be numeric and "
+ "positive");
+ break;
+
+ case 'p':
+ pseudorandom = ISC_TRUE;
+ break;
+
+ case 'r':
+ randomfile = isc_commandline_argument;
+ break;
+
+ case 'v':
+ endp = NULL;
+ verbose = strtol(isc_commandline_argument, &endp, 0);
+ if (*endp != '\0')
+ fatal("verbose level must be numeric");
+ break;
+
+ case 'o':
+ origin = isc_commandline_argument;
+ break;
+
+ case 'f':
+ output = isc_commandline_argument;
+ break;
+
+ case 'a':
+ tryverify = ISC_TRUE;
+ break;
+
+ case 't':
+ printstats = ISC_TRUE;
+ break;
+
+ case 'd':
+ directory = isc_commandline_argument;
+ break;
+
+ case 'n':
+ endp = NULL;
+ ntasks = strtol(isc_commandline_argument, &endp, 0);
+ if (*endp != '\0' || ntasks > ISC_INT32_MAX)
+ fatal("number of cpus must be numeric");
+ break;
+
+ case 'h':
+ default:
+ usage();
+
+ }
+ }
+
+ setup_entropy(mctx, randomfile, &ectx);
+ eflags = ISC_ENTROPY_BLOCKING;
+ if (!pseudorandom)
+ eflags |= ISC_ENTROPY_GOODONLY;
+ result = dst_lib_init(mctx, ectx, eflags);
+ if (result != ISC_R_SUCCESS)
+ fatal("could not initialize dst");
+
+ isc_stdtime_get(&now);
+
+ if (startstr != NULL)
+ starttime = strtotime(startstr, now, now);
+ else
+ starttime = now;
+
+ if (endstr != NULL)
+ endtime = strtotime(endstr, now, starttime);
+ else
+ endtime = starttime + (30 * 24 * 60 * 60);
+
+ if (cycle == -1)
+ cycle = (endtime - starttime) / 4;
+
+ if (ntasks == 0)
+ ntasks = isc_os_ncpus();
+ vbprintf(4, "using %d cpus\n", ntasks);
+
+
+ if (classname != NULL) {
+ r.base = classname;
+ r.length = strlen(classname);
+ result = dns_rdataclass_fromtext(&rdclass, &r);
+ if (result != ISC_R_SUCCESS)
+ fatal("unknown class %s",classname);
+ } else
+ rdclass = dns_rdataclass_in;
+
+ setup_logging(verbose, mctx, &log);
+
+ argc -= isc_commandline_index;
+ argv += isc_commandline_index;
+
+ if (argc < 1)
+ usage();
+
+ file = argv[0];
+
+ argc -= 1;
+ argv += 1;
+
+ if (output == NULL) {
+ free_output = ISC_TRUE;
+ output = isc_mem_allocate(mctx,
+ strlen(file) + strlen(".signed") + 1);
+ if (output == NULL)
+ fatal("out of memory");
+ sprintf(output, "%s.signed", file);
+ }
+
+ if (origin == NULL)
+ origin = file;
+
+ gdb = NULL;
+ isc_time_now(&timer_start);
+ loadzone(file, origin, rdclass, &gdb);
+ gorigin = dns_db_origin(gdb);
+
+ ISC_LIST_INIT(keylist);
+
+ if (argc == 0) {
+ signer_key_t *key;
+
+ loadzonekeys(gdb);
+
+ key = ISC_LIST_HEAD(keylist);
+ while (key != NULL) {
+ key->isdefault = ISC_TRUE;
+ key = ISC_LIST_NEXT(key, link);
+ }
+ } else {
+ for (i = 0; i < argc; i++) {
+ dst_key_t *newkey = NULL;
+
+ result = dst_key_fromnamedfile(argv[i],
+ DST_TYPE_PUBLIC |
+ DST_TYPE_PRIVATE,
+ mctx, &newkey);
+ if (result != ISC_R_SUCCESS)
+ fatal("cannot load key %s: %s", argv[i],
+ isc_result_totext(result));
+
+ key = ISC_LIST_HEAD(keylist);
+ while (key != NULL) {
+ dst_key_t *dkey = key->key;
+ if (dst_key_id(dkey) == dst_key_id(newkey) &&
+ dst_key_alg(dkey) == dst_key_alg(newkey) &&
+ dns_name_equal(dst_key_name(dkey),
+ dst_key_name(newkey)))
+ {
+ key->isdefault = ISC_TRUE;
+ if (!dst_key_isprivate(dkey))
+ fatal("cannot sign zone with "
+ "non-private key %s",
+ argv[i]);
+ break;
+ }
+ key = ISC_LIST_NEXT(key, link);
+ }
+ if (key == NULL) {
+ key = newkeystruct(newkey, ISC_TRUE);
+ ISC_LIST_APPEND(keylist, key, link);
+ } else
+ dst_key_free(&newkey);
+ }
+
+ loadzonepubkeys(gdb);
+ }
+
+ if (ISC_LIST_EMPTY(keylist)) {
+ fprintf(stderr, "%s: warning: No keys specified or found\n",
+ program);
+ nokeys = ISC_TRUE;
+ }
+
+ gversion = NULL;
+ result = dns_db_newversion(gdb, &gversion);
+ check_result(result, "dns_db_newversion()");
+
+ tempfilelen = strlen(output) + 20;
+ tempfile = isc_mem_get(mctx, tempfilelen);
+ if (tempfile == NULL)
+ fatal("out of memory");
+
+ result = isc_file_mktemplate(output, tempfile, tempfilelen);
+ check_result(result, "isc_file_mktemplate");
+
+ fp = NULL;
+ result = isc_file_openunique(tempfile, &fp);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to open temporary output file: %s",
+ isc_result_totext(result));
+ removefile = ISC_TRUE;
+ setfatalcallback(&removetempfile);
+
+ print_time(fp);
+ print_version(fp);
+
+ result = isc_taskmgr_create(mctx, ntasks, 0, &taskmgr);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to create task manager: %s",
+ isc_result_totext(result));
+
+ master = NULL;
+ result = isc_task_create(taskmgr, 0, &master);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to create task: %s", isc_result_totext(result));
+
+ tasks = isc_mem_get(mctx, ntasks * sizeof(isc_task_t *));
+ if (tasks == NULL)
+ fatal("out of memory");
+ for (i = 0; i < (int)ntasks; i++) {
+ tasks[i] = NULL;
+ result = isc_task_create(taskmgr, 0, &tasks[i]);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to create task: %s",
+ isc_result_totext(result));
+ result = isc_app_onrun(mctx, master, startworker, tasks[i]);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to start task: %s",
+ isc_result_totext(result));
+ }
+
+ RUNTIME_CHECK(isc_mutex_init(&namelock) == ISC_R_SUCCESS);
+ if (printstats)
+ RUNTIME_CHECK(isc_mutex_init(&statslock) == ISC_R_SUCCESS);
+
+ presign();
+ (void)isc_app_run();
+ if (!finished)
+ fatal("process aborted by user");
+ shuttingdown = ISC_TRUE;
+ for (i = 0; i < (int)ntasks; i++)
+ isc_task_detach(&tasks[i]);
+ isc_taskmgr_destroy(&taskmgr);
+ isc_mem_put(mctx, tasks, ntasks * sizeof(isc_task_t *));
+ postsign();
+
+ result = isc_stdio_close(fp);
+ check_result(result, "isc_stdio_close");
+ removefile = ISC_FALSE;
+
+ result = isc_file_rename(tempfile, output);
+ if (result != ISC_R_SUCCESS)
+ fatal("failed to rename temp file to %s: %s\n",
+ output, isc_result_totext(result));
+
+ DESTROYLOCK(&namelock);
+ if (printstats)
+ DESTROYLOCK(&statslock);
+
+ printf("%s\n", output);
+
+ dns_db_closeversion(gdb, &gversion, ISC_FALSE);
+
+ dns_db_detach(&gdb);
+
+ while (!ISC_LIST_EMPTY(keylist)) {
+ key = ISC_LIST_HEAD(keylist);
+ ISC_LIST_UNLINK(keylist, key, link);
+ dst_key_free(&key->key);
+ isc_mem_put(mctx, key, sizeof(signer_key_t));
+ }
+
+ isc_mem_put(mctx, tempfile, tempfilelen);
+
+ if (free_output)
+ isc_mem_free(mctx, output);
+
+ cleanup_logging(&log);
+ dst_lib_destroy();
+ cleanup_entropy(&ectx);
+ if (verbose > 10)
+ isc_mem_stats(mctx, stdout);
+ isc_mem_destroy(&mctx);
+
+ (void) isc_app_finish();
+
+ if (printstats) {
+ isc_uint64_t runtime_us; /* Runtime in microseconds */
+ isc_uint64_t runtime_ms; /* Runtime in milliseconds */
+ isc_uint64_t sig_ms; /* Signatures per millisecond */
+
+ isc_time_now(&timer_finish);
+
+ runtime_us = isc_time_microdiff(&timer_finish, &timer_start);
+
+ printf("Signatures generated: %10d\n",
+ nsigned);
+ printf("Signatures retained: %10d\n",
+ nretained);
+ printf("Signatures dropped: %10d\n",
+ ndropped);
+ printf("Signatures successfully verified: %10d\n",
+ nverified);
+ printf("Signatures unsuccessfully verified: %10d\n",
+ nverifyfailed);
+ runtime_ms = runtime_us / 1000;
+ printf("Runtime in seconds: %7u.%03u\n",
+ (unsigned int) (runtime_ms / 1000),
+ (unsigned int) (runtime_ms % 1000));
+ if (runtime_us > 0) {
+ sig_ms = ((isc_uint64_t)nsigned * 1000000000) /
+ runtime_us;
+ printf("Signatures per second: %7u.%03u\n",
+ (unsigned int) sig_ms / 1000,
+ (unsigned int) sig_ms % 1000);
+ }
+ }
+
+ return (0);
+}
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-signzone.docbook b/usr.sbin/bind/bin/dnssec/dnssec-signzone.docbook
new file mode 100644
index 00000000000..3f9a2a9276f
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-signzone.docbook
@@ -0,0 +1,325 @@
+<!DOCTYPE refentry PUBLIC "-//OASIS//DTD DocBook V4.1//EN">
+<!--
+ - Copyright (C) 2001 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
+ - copyright notice and this permission notice appear in all copies.
+ -
+ - THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+ - DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+ - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+ - INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+ - INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+ - FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ - NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ - WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+-->
+
+<!-- $ISC: dnssec-signzone.docbook,v 1.2 2001/04/10 21:50:37 bwelling Exp $ -->
+
+<refentry>
+ <refentryinfo>
+ <date>June 30, 2000</date>
+ </refentryinfo>
+
+ <refmeta>
+ <refentrytitle><application>dnssec-signzone</application></refentrytitle>
+ <manvolnum>8</manvolnum>
+ <refmiscinfo>BIND9</refmiscinfo>
+ </refmeta>
+
+ <refnamediv>
+ <refname><application>dnssec-signzone</application></refname>
+ <refpurpose>DNSSEC zone signing tool</refpurpose>
+ </refnamediv>
+
+ <refsynopsisdiv>
+ <cmdsynopsis>
+ <command>dnssec-signzone</command>
+ <arg><option>-a</option></arg>
+ <arg><option>-c <replaceable class="parameter">class</replaceable></option></arg>
+ <arg><option>-d <replaceable class="parameter">directory</replaceable></option></arg>
+ <arg><option>-s <replaceable class="parameter">start-time</replaceable></option></arg>
+ <arg><option>-e <replaceable class="parameter">end-time</replaceable></option></arg>
+ <arg><option>-f <replaceable class="parameter">output-file</replaceable></option></arg>
+ <arg><option>-h</option></arg>
+ <arg><option>-i <replaceable class="parameter">interval</replaceable></option></arg>
+ <arg><option>-n <replaceable class="parameter">nthreads</replaceable></option></arg>
+ <arg><option>-o <replaceable class="parameter">origin</replaceable></option></arg>
+ <arg><option>-p</option></arg>
+ <arg><option>-r <replaceable class="parameter">randomdev</replaceable></option></arg>
+ <arg><option>-t</option></arg>
+ <arg><option>-v <replaceable class="parameter">level</replaceable></option></arg>
+ <arg choice="req">zonefile</arg>
+ <arg rep="repeat">key</arg>
+ </cmdsynopsis>
+ </refsynopsisdiv>
+
+ <refsect1>
+ <title>DESCRIPTION</title>
+ <para>
+ <command>dnssec-signzone</command> signs a zone. It generates NXT
+ and SIG records and produces a signed version of the zone. If there
+ is a <filename>signedkey</filename> file from the zone's parent,
+ the parent's signatures will be incorporated into the generated
+ signed zone file. The security status of delegations from the the
+ signed zone (that is, whether the child zones are secure or not) is
+ determined by the presence or absence of a
+ <filename>signedkey</filename> file for each child zone.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>OPTIONS</title>
+
+ <variablelist>
+ <varlistentry>
+ <term>-a</term>
+ <listitem>
+ <para>
+ Verify all generated signatures.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-c <replaceable class="parameter">class</replaceable></term>
+ <listitem>
+ <para>
+ Specifies the DNS class of the zone.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-d <replaceable class="parameter">directory</replaceable></term>
+ <listitem>
+ <para>
+ Look for <filename>signedkey</filename> files in
+ <option>directory</option> as the directory
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-s <replaceable class="parameter">start-time</replaceable></term>
+ <listitem>
+ <para>
+ Specify the date and time when the generated SIG records
+ become valid. This can be either an absolute or relative
+ time. An absolute start time is indicated by a number
+ in YYYYMMDDHHMMSS notation; 20000530144500 denotes
+ 14:45:00 UTC on May 30th, 2000. A relative start time is
+ indicated by +N, which is N seconds from the current time.
+ If no <option>start-time</option> is specified, the current
+ time is used.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-e <replaceable class="parameter">end-time</replaceable></term>
+ <listitem>
+ <para>
+ Specify the date and time when the generated SIG records
+ expire. As with <option>start-time</option>, an absolute
+ time is indicated in YYYYMMDDHHMMSS notation. A time relative
+ to the start time is indicated with +N, which is N seconds from
+ the start time. A time realtive to the current time is
+ indicated with now+N. If no <option>end-time</option> is
+ specified, 30 days from the start time is used as a default.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-f <replaceable class="parameter">output-file</replaceable></term>
+ <listitem>
+ <para>
+ The name of the output file containing the signed zone. The
+ default is to append <filename>.signed</filename> to the
+ input file.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-h</term>
+ <listitem>
+ <para>
+ Prints a short summary of the options and arguments to
+ <command>dnssec-signzone</command>.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-i <replaceable class="parameter">interval</replaceable></term>
+ <listitem>
+ <para>
+ When a previously signed zone is passed as input, records
+ may be resigned. The <option>interval</option> option
+ specifies the cycle interval as an offset from the current
+ time (in seconds). If a SIG record expires after the
+ cycle interval, it is retained. Otherwise, it is considered
+ to be expiring soon, and it will be replaced.
+ </para>
+ <para>
+ The default cycle interval is one quarter of the difference
+ between the signature end and start times. So if neither
+ <option>end-time</option> or <option>start-time</option>
+ are specified, <command>dnssec-signzone</command> generates
+ signatures that are valid for 30 days, with a cycle
+ interval of 7.5 days. Therefore, if any existing SIG records
+ are due to expire in less than 7.5 days, they would be
+ replaced.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-n <replaceable class="parameter">ncpus</replaceable></term>
+ <listitem>
+ <para>
+ Specifies the number of threads to use. By default, one
+ thread is started for each detected CPU.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-o <replaceable class="parameter">origin</replaceable></term>
+ <listitem>
+ <para>
+ The zone origin. If not specified, the name of the zone file
+ is assumed to be the origin.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-p</term>
+ <listitem>
+ <para>
+ Use pseudo-random data when signing the zone. This is faster,
+ but less secure, than using real random data. This option
+ may be useful when signing large zones or when the entropy
+ source is limited.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-r <replaceable class="parameter">randomdev</replaceable></term>
+ <listitem>
+ <para>
+ Specifies the source of randomness. If the operating
+ system does not provide a <filename>/dev/random</filename>
+ or equivalent device, the default source of randomness
+ is keyboard input. <filename>randomdev</filename> specifies
+ the name of a character device or file containing random
+ data to be used instead of the default. The special value
+ <filename>keyboard</filename> indicates that keyboard
+ input should be used.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-t</term>
+ <listitem>
+ <para>
+ Print statistics at completion.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>-v <replaceable class="parameter">level</replaceable></term>
+ <listitem>
+ <para>
+ Sets the debugging level.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>zonefile</term>
+ <listitem>
+ <para>
+ The file containing the zone to be signed.
+ Sets the debugging level.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>key</term>
+ <listitem>
+ <para>
+ The keys used to sign the zone. If no keys are specified, the
+ default all zone keys that have private key files in the
+ current directory.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ </variablelist>
+ </refsect1>
+
+ <refsect1>
+ <title>EXAMPLE</title>
+ <para>
+ The following command signs the <userinput>example.com</userinput>
+ zone with the DSA key generated in the <command>dnssec-keygen</command>
+ man page. The zone's keys must be in the zone. If there are
+ <filename>signedkey</filename> files associated with this zone
+ or any child zones, they must be in the current directory.
+ <userinput>example.com</userinput>, the following command would be
+ issued:
+ </para>
+ <para>
+ <userinput>dnssec-signzone -o example.com db.example.com Kexample.com.+003+26160</userinput>
+ </para>
+ <para>
+ The command would print a string of the form:
+ </para>
+ <para>
+ In this example, <command>dnssec-signzone</command> creates
+ the file <filename>db.example.com.signed</filename>. This file
+ should be referenced in a zone statement in a
+ <filename>named.conf</filename> file.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>SEE ALSO</title>
+ <para>
+ <citerefentry>
+ <refentrytitle>dnssec-keygen</refentrytitle>
+ <manvolnum>8</manvolnum>
+ </citerefentry>,
+ <citerefentry>
+ <refentrytitle>dnssec-signkey</refentrytitle>
+ <manvolnum>8</manvolnum>
+ </citerefentry>,
+ <citetitle>BIND 9 Administrator Reference Manual</citetitle>,
+ <citetitle>RFC 2535</citetitle>.
+ </para>
+ </refsect1>
+
+ <refsect1>
+ <title>AUTHOR</title>
+ <para>
+ <corpauthor>Internet Software Consortium</corpauthor>
+ </para>
+ </refsect1>
+
+</refentry>
+
+<!--
+ - Local variables:
+ - mode: sgml
+ - End:
+-->
diff --git a/usr.sbin/bind/bin/dnssec/dnssec-signzone.html b/usr.sbin/bind/bin/dnssec/dnssec-signzone.html
new file mode 100644
index 00000000000..ed3ba8e7a63
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssec-signzone.html
@@ -0,0 +1,553 @@
+<!--
+ - Copyright (C) 2000, 2001 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
+ - copyright notice and this permission notice appear in all copies.
+ -
+ - THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+ - DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+ - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+ - INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+ - INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+ - FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ - NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ - WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+-->
+<HTML
+><HEAD
+><TITLE
+>dnssec-signzone</TITLE
+><META
+NAME="GENERATOR"
+CONTENT="Modular DocBook HTML Stylesheet Version 1.61
+"></HEAD
+><BODY
+CLASS="REFENTRY"
+BGCOLOR="#FFFFFF"
+TEXT="#000000"
+LINK="#0000FF"
+VLINK="#840084"
+ALINK="#0000FF"
+><H1
+><A
+NAME="AEN1"
+><SPAN
+CLASS="APPLICATION"
+>dnssec-signzone</SPAN
+></A
+></H1
+><DIV
+CLASS="REFNAMEDIV"
+><A
+NAME="AEN9"
+></A
+><H2
+>Name</H2
+><SPAN
+CLASS="APPLICATION"
+>dnssec-signzone</SPAN
+>&nbsp;--&nbsp;DNSSEC zone signing tool</DIV
+><DIV
+CLASS="REFSYNOPSISDIV"
+><A
+NAME="AEN13"
+></A
+><H2
+>Synopsis</H2
+><P
+><B
+CLASS="COMMAND"
+>dnssec-signzone</B
+> [<TT
+CLASS="OPTION"
+>-a</TT
+>] [<TT
+CLASS="OPTION"
+>-c <TT
+CLASS="REPLACEABLE"
+><I
+>class</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-d <TT
+CLASS="REPLACEABLE"
+><I
+>directory</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-s <TT
+CLASS="REPLACEABLE"
+><I
+>start-time</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-e <TT
+CLASS="REPLACEABLE"
+><I
+>end-time</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-f <TT
+CLASS="REPLACEABLE"
+><I
+>output-file</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-h</TT
+>] [<TT
+CLASS="OPTION"
+>-i <TT
+CLASS="REPLACEABLE"
+><I
+>interval</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-n <TT
+CLASS="REPLACEABLE"
+><I
+>nthreads</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-o <TT
+CLASS="REPLACEABLE"
+><I
+>origin</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-p</TT
+>] [<TT
+CLASS="OPTION"
+>-r <TT
+CLASS="REPLACEABLE"
+><I
+>randomdev</I
+></TT
+></TT
+>] [<TT
+CLASS="OPTION"
+>-t</TT
+>] [<TT
+CLASS="OPTION"
+>-v <TT
+CLASS="REPLACEABLE"
+><I
+>level</I
+></TT
+></TT
+>] {zonefile} [key...]</P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN56"
+></A
+><H2
+>DESCRIPTION</H2
+><P
+> <B
+CLASS="COMMAND"
+>dnssec-signzone</B
+> signs a zone. It generates NXT
+ and SIG records and produces a signed version of the zone. If there
+ is a <TT
+CLASS="FILENAME"
+>signedkey</TT
+> file from the zone's parent,
+ the parent's signatures will be incorporated into the generated
+ signed zone file. The security status of delegations from the the
+ signed zone (that is, whether the child zones are secure or not) is
+ determined by the presence or absence of a
+ <TT
+CLASS="FILENAME"
+>signedkey</TT
+> file for each child zone.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN62"
+></A
+><H2
+>OPTIONS</H2
+><P
+></P
+><DIV
+CLASS="VARIABLELIST"
+><DL
+><DT
+>-a</DT
+><DD
+><P
+> Verify all generated signatures.
+ </P
+></DD
+><DT
+>-c <TT
+CLASS="REPLACEABLE"
+><I
+>class</I
+></TT
+></DT
+><DD
+><P
+> Specifies the DNS class of the zone.
+ </P
+></DD
+><DT
+>-d <TT
+CLASS="REPLACEABLE"
+><I
+>directory</I
+></TT
+></DT
+><DD
+><P
+> Look for <TT
+CLASS="FILENAME"
+>signedkey</TT
+> files in
+ <TT
+CLASS="OPTION"
+>directory</TT
+> as the directory
+ </P
+></DD
+><DT
+>-s <TT
+CLASS="REPLACEABLE"
+><I
+>start-time</I
+></TT
+></DT
+><DD
+><P
+> Specify the date and time when the generated SIG records
+ become valid. This can be either an absolute or relative
+ time. An absolute start time is indicated by a number
+ in YYYYMMDDHHMMSS notation; 20000530144500 denotes
+ 14:45:00 UTC on May 30th, 2000. A relative start time is
+ indicated by +N, which is N seconds from the current time.
+ If no <TT
+CLASS="OPTION"
+>start-time</TT
+> is specified, the current
+ time is used.
+ </P
+></DD
+><DT
+>-e <TT
+CLASS="REPLACEABLE"
+><I
+>end-time</I
+></TT
+></DT
+><DD
+><P
+> Specify the date and time when the generated SIG records
+ expire. As with <TT
+CLASS="OPTION"
+>start-time</TT
+>, an absolute
+ time is indicated in YYYYMMDDHHMMSS notation. A time relative
+ to the start time is indicated with +N, which is N seconds from
+ the start time. A time realtive to the current time is
+ indicated with now+N. If no <TT
+CLASS="OPTION"
+>end-time</TT
+> is
+ specified, 30 days from the start time is used as a default.
+ </P
+></DD
+><DT
+>-f <TT
+CLASS="REPLACEABLE"
+><I
+>output-file</I
+></TT
+></DT
+><DD
+><P
+> The name of the output file containing the signed zone. The
+ default is to append <TT
+CLASS="FILENAME"
+>.signed</TT
+> to the
+ input file.
+ </P
+></DD
+><DT
+>-h</DT
+><DD
+><P
+> Prints a short summary of the options and arguments to
+ <B
+CLASS="COMMAND"
+>dnssec-signzone</B
+>.
+ </P
+></DD
+><DT
+>-i <TT
+CLASS="REPLACEABLE"
+><I
+>interval</I
+></TT
+></DT
+><DD
+><P
+> When a previously signed zone is passed as input, records
+ may be resigned. The <TT
+CLASS="OPTION"
+>interval</TT
+> option
+ specifies the cycle interval as an offset from the current
+ time (in seconds). If a SIG record expires after the
+ cycle interval, it is retained. Otherwise, it is considered
+ to be expiring soon, and it will be replaced.
+ </P
+><P
+> The default cycle interval is one quarter of the difference
+ between the signature end and start times. So if neither
+ <TT
+CLASS="OPTION"
+>end-time</TT
+> or <TT
+CLASS="OPTION"
+>start-time</TT
+>
+ are specified, <B
+CLASS="COMMAND"
+>dnssec-signzone</B
+> generates
+ signatures that are valid for 30 days, with a cycle
+ interval of 7.5 days. Therefore, if any existing SIG records
+ are due to expire in less than 7.5 days, they would be
+ replaced.
+ </P
+></DD
+><DT
+>-n <TT
+CLASS="REPLACEABLE"
+><I
+>ncpus</I
+></TT
+></DT
+><DD
+><P
+> Specifies the number of threads to use. By default, one
+ thread is started for each detected CPU.
+ </P
+></DD
+><DT
+>-o <TT
+CLASS="REPLACEABLE"
+><I
+>origin</I
+></TT
+></DT
+><DD
+><P
+> The zone origin. If not specified, the name of the zone file
+ is assumed to be the origin.
+ </P
+></DD
+><DT
+>-p</DT
+><DD
+><P
+> Use pseudo-random data when signing the zone. This is faster,
+ but less secure, than using real random data. This option
+ may be useful when signing large zones or when the entropy
+ source is limited.
+ </P
+></DD
+><DT
+>-r <TT
+CLASS="REPLACEABLE"
+><I
+>randomdev</I
+></TT
+></DT
+><DD
+><P
+> Specifies the source of randomness. If the operating
+ system does not provide a <TT
+CLASS="FILENAME"
+>/dev/random</TT
+>
+ or equivalent device, the default source of randomness
+ is keyboard input. <TT
+CLASS="FILENAME"
+>randomdev</TT
+> specifies
+ the name of a character device or file containing random
+ data to be used instead of the default. The special value
+ <TT
+CLASS="FILENAME"
+>keyboard</TT
+> indicates that keyboard
+ input should be used.
+ </P
+></DD
+><DT
+>-t</DT
+><DD
+><P
+> Print statistics at completion.
+ </P
+></DD
+><DT
+>-v <TT
+CLASS="REPLACEABLE"
+><I
+>level</I
+></TT
+></DT
+><DD
+><P
+> Sets the debugging level.
+ </P
+></DD
+><DT
+>zonefile</DT
+><DD
+><P
+> The file containing the zone to be signed.
+ Sets the debugging level.
+ </P
+></DD
+><DT
+>key</DT
+><DD
+><P
+> The keys used to sign the zone. If no keys are specified, the
+ default all zone keys that have private key files in the
+ current directory.
+ </P
+></DD
+></DL
+></DIV
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN154"
+></A
+><H2
+>EXAMPLE</H2
+><P
+> The following command signs the <TT
+CLASS="USERINPUT"
+><B
+>example.com</B
+></TT
+>
+ zone with the DSA key generated in the <B
+CLASS="COMMAND"
+>dnssec-keygen</B
+>
+ man page. The zone's keys must be in the zone. If there are
+ <TT
+CLASS="FILENAME"
+>signedkey</TT
+> files associated with this zone
+ or any child zones, they must be in the current directory.
+ <TT
+CLASS="USERINPUT"
+><B
+>example.com</B
+></TT
+>, the following command would be
+ issued:
+ </P
+><P
+> <TT
+CLASS="USERINPUT"
+><B
+>dnssec-signzone -o example.com db.example.com Kexample.com.+003+26160</B
+></TT
+>
+ </P
+><P
+> The command would print a string of the form:
+ </P
+><P
+> In this example, <B
+CLASS="COMMAND"
+>dnssec-signzone</B
+> creates
+ the file <TT
+CLASS="FILENAME"
+>db.example.com.signed</TT
+>. This file
+ should be referenced in a zone statement in a
+ <TT
+CLASS="FILENAME"
+>named.conf</TT
+> file.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN168"
+></A
+><H2
+>SEE ALSO</H2
+><P
+> <SPAN
+CLASS="CITEREFENTRY"
+><SPAN
+CLASS="REFENTRYTITLE"
+>dnssec-keygen</SPAN
+>(8)</SPAN
+>,
+ <SPAN
+CLASS="CITEREFENTRY"
+><SPAN
+CLASS="REFENTRYTITLE"
+>dnssec-signkey</SPAN
+>(8)</SPAN
+>,
+ <I
+CLASS="CITETITLE"
+>BIND 9 Administrator Reference Manual</I
+>,
+ <I
+CLASS="CITETITLE"
+>RFC 2535</I
+>.
+ </P
+></DIV
+><DIV
+CLASS="REFSECT1"
+><A
+NAME="AEN179"
+></A
+><H2
+>AUTHOR</H2
+><P
+> Internet Software Consortium
+ </P
+></DIV
+></BODY
+></HTML
+> \ No newline at end of file
diff --git a/usr.sbin/bind/bin/dnssec/dnssectool.c b/usr.sbin/bind/bin/dnssec/dnssectool.c
new file mode 100644
index 00000000000..cdbd54e489e
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssectool.c
@@ -0,0 +1,260 @@
+/*
+ * Copyright (C) 2000, 2001 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
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+ * DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+ * INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+ * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+ * FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/* $ISC: dnssectool.c,v 1.31.2.2 2001/11/27 22:41:49 gson Exp $ */
+
+#include <config.h>
+
+#include <stdlib.h>
+
+#include <isc/buffer.h>
+#include <isc/entropy.h>
+#include <isc/string.h>
+#include <isc/time.h>
+#include <isc/util.h>
+#include <isc/print.h>
+
+#include <dns/log.h>
+#include <dns/name.h>
+#include <dns/rdatastruct.h>
+#include <dns/rdatatype.h>
+#include <dns/result.h>
+#include <dns/secalg.h>
+#include <dns/time.h>
+
+#include "dnssectool.h"
+
+extern int verbose;
+extern const char *program;
+
+static isc_entropysource_t *source = NULL;
+static fatalcallback_t *fatalcallback = NULL;
+
+void
+fatal(const char *format, ...) {
+ va_list args;
+
+ fprintf(stderr, "%s: ", program);
+ va_start(args, format);
+ vfprintf(stderr, format, args);
+ va_end(args);
+ fprintf(stderr, "\n");
+ if (fatalcallback != NULL)
+ (*fatalcallback)();
+ exit(1);
+}
+
+void
+setfatalcallback(fatalcallback_t *callback) {
+ fatalcallback = callback;
+}
+
+void
+check_result(isc_result_t result, const char *message) {
+ if (result != ISC_R_SUCCESS)
+ fatal("%s: %s", message, isc_result_totext(result));
+}
+
+void
+vbprintf(int level, const char *fmt, ...) {
+ va_list ap;
+ if (level > verbose)
+ return;
+ va_start(ap, fmt);
+ fprintf(stderr, "%s: ", program);
+ vfprintf(stderr, fmt, ap);
+ va_end(ap);
+}
+
+void
+type_format(const dns_rdatatype_t type, char *cp, unsigned int size) {
+ isc_buffer_t b;
+ isc_region_t r;
+ isc_result_t result;
+
+ isc_buffer_init(&b, cp, size - 1);
+ result = dns_rdatatype_totext(type, &b);
+ check_result(result, "dns_rdatatype_totext()");
+ isc_buffer_usedregion(&b, &r);
+ r.base[r.length] = 0;
+}
+
+void
+alg_format(const dns_secalg_t alg, char *cp, unsigned int size) {
+ isc_buffer_t b;
+ isc_region_t r;
+ isc_result_t result;
+
+ isc_buffer_init(&b, cp, size - 1);
+ result = dns_secalg_totext(alg, &b);
+ check_result(result, "dns_secalg_totext()");
+ isc_buffer_usedregion(&b, &r);
+ r.base[r.length] = 0;
+}
+
+void
+sig_format(dns_rdata_sig_t *sig, char *cp, unsigned int size) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ char algstr[DNS_NAME_FORMATSIZE];
+
+ dns_name_format(&sig->signer, namestr, sizeof namestr);
+ alg_format(sig->algorithm, algstr, sizeof algstr);
+ snprintf(cp, size, "%s/%s/%d", namestr, algstr, sig->keyid);
+}
+
+void
+key_format(const dst_key_t *key, char *cp, unsigned int size) {
+ char namestr[DNS_NAME_FORMATSIZE];
+ char algstr[DNS_NAME_FORMATSIZE];
+
+ dns_name_format(dst_key_name(key), namestr, sizeof namestr);
+ alg_format((dns_secalg_t) dst_key_alg(key), algstr, sizeof algstr);
+ snprintf(cp, size, "%s/%s/%d", namestr, algstr, dst_key_id(key));
+}
+
+void
+setup_logging(int verbose, isc_mem_t *mctx, isc_log_t **logp) {
+ isc_result_t result;
+ isc_logdestination_t destination;
+ isc_logconfig_t *logconfig = NULL;
+ isc_log_t *log = NULL;
+ int level;
+
+ switch (verbose) {
+ case 0:
+ /*
+ * We want to see warnings about things like out-of-zone
+ * data in the master file even when not verbose.
+ */
+ level = ISC_LOG_WARNING;
+ break;
+ case 1:
+ level = ISC_LOG_INFO;
+ break;
+ default:
+ level = ISC_LOG_DEBUG(verbose - 2 + 1);
+ break;
+ }
+
+ RUNTIME_CHECK(isc_log_create(mctx, &log, &logconfig) == ISC_R_SUCCESS);
+ isc_log_setcontext(log);
+ dns_log_init(log);
+ dns_log_setcontext(log);
+
+ RUNTIME_CHECK(isc_log_settag(logconfig, program) == ISC_R_SUCCESS);
+
+ /*
+ * Set up a channel similar to default_stderr except:
+ * - the logging level is passed in
+ * - the program name and logging level are printed
+ * - no time stamp is printed
+ */
+ destination.file.stream = stderr;
+ destination.file.name = NULL;
+ destination.file.versions = ISC_LOG_ROLLNEVER;
+ destination.file.maximum_size = 0;
+ result = isc_log_createchannel(logconfig, "stderr",
+ ISC_LOG_TOFILEDESC,
+ level,
+ &destination,
+ ISC_LOG_PRINTTAG|ISC_LOG_PRINTLEVEL);
+ check_result(result, "isc_log_createchannel()");
+
+ RUNTIME_CHECK(isc_log_usechannel(logconfig, "stderr",
+ NULL, NULL) == ISC_R_SUCCESS);
+
+ *logp = log;
+}
+
+void
+cleanup_logging(isc_log_t **logp) {
+ isc_log_t *log;
+
+ REQUIRE(logp != NULL);
+
+ log = *logp;
+ if (log == NULL)
+ return;
+ isc_log_destroy(&log);
+ isc_log_setcontext(NULL);
+ dns_log_setcontext(NULL);
+ logp = NULL;
+}
+
+void
+setup_entropy(isc_mem_t *mctx, const char *randomfile, isc_entropy_t **ectx) {
+ isc_result_t result;
+ int usekeyboard = ISC_ENTROPY_KEYBOARDMAYBE;
+
+ REQUIRE(ectx != NULL);
+
+ if (*ectx == NULL) {
+ result = isc_entropy_create(mctx, ectx);
+ if (result != ISC_R_SUCCESS)
+ fatal("could not create entropy object");
+ }
+
+ if (randomfile != NULL && strcmp(randomfile, "keyboard") == 0) {
+ usekeyboard = ISC_ENTROPY_KEYBOARDYES;
+ randomfile = NULL;
+ }
+
+ result = isc_entropy_usebestsource(*ectx, &source, randomfile,
+ usekeyboard);
+
+ if (result != ISC_R_SUCCESS)
+ fatal("could not initialize entropy source: %s",
+ isc_result_totext(result));
+}
+
+void
+cleanup_entropy(isc_entropy_t **ectx) {
+ if (source != NULL)
+ isc_entropy_destroysource(&source);
+ isc_entropy_detach(ectx);
+}
+
+isc_stdtime_t
+strtotime(char *str, isc_int64_t now, isc_int64_t base) {
+ isc_int64_t val, offset;
+ isc_result_t result;
+ char *endp;
+
+ if (str[0] == '+') {
+ offset = strtol(str + 1, &endp, 0);
+ if (*endp != '\0')
+ fatal("time value %s is invalid", str);
+ val = base + offset;
+ } else if (strncmp(str, "now+", 4) == 0) {
+ offset = strtol(str + 4, &endp, 0);
+ if (*endp != '\0')
+ fatal("time value %s is invalid", str);
+ val = now + offset;
+ } else if (strlen(str) == 8) {
+ char timestr[15];
+ sprintf(timestr, "%s000000", str);
+ result = dns_time64_fromtext(timestr, &val);
+ if (result != ISC_R_SUCCESS)
+ fatal("time value %s is invalid", str);
+ } else {
+ result = dns_time64_fromtext(str, &val);
+ if (result != ISC_R_SUCCESS)
+ fatal("time value %s is invalid", str);
+ }
+
+ return ((isc_stdtime_t) val);
+}
diff --git a/usr.sbin/bind/bin/dnssec/dnssectool.h b/usr.sbin/bind/bin/dnssec/dnssectool.h
new file mode 100644
index 00000000000..86dff8a502b
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/dnssectool.h
@@ -0,0 +1,73 @@
+/*
+ * Copyright (C) 2000, 2001 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
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+ * DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+ * INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+ * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+ * FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/* $ISC: dnssectool.h,v 1.15 2001/08/08 22:54:16 gson Exp $ */
+
+#ifndef DNSSECTOOL_H
+#define DNSSECTOOL_H 1
+
+#include <isc/log.h>
+#include <isc/stdtime.h>
+#include <dns/rdatastruct.h>
+#include <dst/dst.h>
+
+typedef void (fatalcallback_t)(void);
+
+void
+fatal(const char *format, ...) ISC_FORMAT_PRINTF(1, 2);
+
+void
+setfatalcallback(fatalcallback_t *callback);
+
+void
+check_result(isc_result_t result, const char *message);
+
+void
+vbprintf(int level, const char *fmt, ...) ISC_FORMAT_PRINTF(2, 3);
+
+void
+type_format(const dns_rdatatype_t type, char *cp, unsigned int size);
+#define TYPE_FORMATSIZE 10
+
+void
+alg_format(const dns_secalg_t alg, char *cp, unsigned int size);
+#define ALG_FORMATSIZE 10
+
+void
+sig_format(dns_rdata_sig_t *sig, char *cp, unsigned int size);
+#define SIG_FORMATSIZE (DNS_NAME_FORMATSIZE + ALG_FORMATSIZE + sizeof("65535"))
+
+void
+key_format(const dst_key_t *key, char *cp, unsigned int size);
+#define KEY_FORMATSIZE (DNS_NAME_FORMATSIZE + ALG_FORMATSIZE + sizeof("65535"))
+
+void
+setup_logging(int verbose, isc_mem_t *mctx, isc_log_t **logp);
+
+void
+cleanup_logging(isc_log_t **logp);
+
+void
+setup_entropy(isc_mem_t *mctx, const char *randomfile, isc_entropy_t **ectx);
+
+void
+cleanup_entropy(isc_entropy_t **ectx);
+
+isc_stdtime_t
+strtotime(char *str, isc_int64_t now, isc_int64_t base);
+
+#endif /* DNSSEC_DNSSECTOOL_H */
diff --git a/usr.sbin/bind/bin/dnssec/win32/keygen.dsp b/usr.sbin/bind/bin/dnssec/win32/keygen.dsp
new file mode 100644
index 00000000000..f27b42d819e
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/keygen.dsp
@@ -0,0 +1,107 @@
+# Microsoft Developer Studio Project File - Name="keygen" - Package Owner=<4>
+# Microsoft Developer Studio Generated Build File, Format Version 6.00
+# ** DO NOT EDIT **
+
+# TARGTYPE "Win32 (x86) Console Application" 0x0103
+
+CFG=keygen - Win32 Debug
+!MESSAGE This is not a valid makefile. To build this project using NMAKE,
+!MESSAGE use the Export Makefile command and run
+!MESSAGE
+!MESSAGE NMAKE /f "keygen.mak".
+!MESSAGE
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "keygen.mak" CFG="keygen - Win32 Debug"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "keygen - Win32 Release" (based on "Win32 (x86) Console Application")
+!MESSAGE "keygen - Win32 Debug" (based on "Win32 (x86) Console Application")
+!MESSAGE
+
+# Begin Project
+# PROP AllowPerConfigDependencies 0
+# PROP Scc_ProjName ""
+# PROP Scc_LocalPath ""
+CPP=cl.exe
+RSC=rc.exe
+
+!IF "$(CFG)" == "keygen - Win32 Release"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 0
+# PROP BASE Output_Dir "Release"
+# PROP BASE Intermediate_Dir "Release"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 0
+# PROP Output_Dir "Release"
+# PROP Intermediate_Dir "Release"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
+# ADD CPP /nologo /MT /W3 /GX /O2 /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "NDEBUG" /D "__STDC__" /D "WIN32" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
+# ADD BASE RSC /l 0x409 /d "NDEBUG"
+# ADD RSC /l 0x409 /d "NDEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386
+# ADD LINK32 user32.lib advapi32.lib ../../../lib/isc/win32/Release/libisc.lib ../../../lib/dns/win32/Release/libdns.lib /nologo /subsystem:console /machine:I386 /out:"../../../Build/Release/dnssec-keygen.exe"
+
+!ELSEIF "$(CFG)" == "keygen - Win32 Debug"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 1
+# PROP BASE Output_Dir "Debug"
+# PROP BASE Intermediate_Dir "Debug"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 1
+# PROP Output_Dir "Debug"
+# PROP Intermediate_Dir "Debug"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /GZ /c
+# ADD CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "_DEBUG" /D "WIN32" /D "__STDC__" /D "_CONSOLE" /D "_MBCS" /FR /FD /GZ /c
+# SUBTRACT CPP /X /YX
+# ADD BASE RSC /l 0x409 /d "_DEBUG"
+# ADD RSC /l 0x409 /d "_DEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept
+# ADD LINK32 user32.lib advapi32.lib ../../../lib/isc/win32/Debug/libisc.lib ../../../lib/dns/win32/Debug/libdns.lib /nologo /subsystem:console /debug /machine:I386 /out:"../../../Build/Debug/dnssec-keygen.exe" /pdbtype:sept
+
+!ENDIF
+
+# Begin Target
+
+# Name "keygen - Win32 Release"
+# Name "keygen - Win32 Debug"
+# Begin Group "Source Files"
+
+# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
+# Begin Source File
+
+SOURCE="..\dnssec-keygen.c"
+# End Source File
+# Begin Source File
+
+SOURCE=..\dnssectool.c
+# End Source File
+# End Group
+# Begin Group "Header Files"
+
+# PROP Default_Filter "h;hpp;hxx;hm;inl"
+# End Group
+# Begin Group "Resource Files"
+
+# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
+# End Group
+# End Target
+# End Project
diff --git a/usr.sbin/bind/bin/dnssec/win32/keygen.dsw b/usr.sbin/bind/bin/dnssec/win32/keygen.dsw
new file mode 100644
index 00000000000..bdd633e4e95
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/keygen.dsw
@@ -0,0 +1,29 @@
+Microsoft Developer Studio Workspace File, Format Version 6.00
+# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE!
+
+###############################################################################
+
+Project: "keygen"=".\keygen.dsp" - Package Owner=<4>
+
+Package=<5>
+{{{
+}}}
+
+Package=<4>
+{{{
+}}}
+
+###############################################################################
+
+Global:
+
+Package=<5>
+{{{
+}}}
+
+Package=<3>
+{{{
+}}}
+
+###############################################################################
+
diff --git a/usr.sbin/bind/bin/dnssec/win32/keygen.mak b/usr.sbin/bind/bin/dnssec/win32/keygen.mak
new file mode 100644
index 00000000000..7cd0dc19621
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/keygen.mak
@@ -0,0 +1,227 @@
+# Microsoft Developer Studio Generated NMAKE File, Based on keygen.dsp
+!IF "$(CFG)" == ""
+CFG=keygen - Win32 Debug
+!MESSAGE No configuration specified. Defaulting to keygen - Win32 Debug.
+!ENDIF
+
+!IF "$(CFG)" != "keygen - Win32 Release" && "$(CFG)" != "keygen - Win32 Debug"
+!MESSAGE Invalid configuration "$(CFG)" specified.
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "keygen.mak" CFG="keygen - Win32 Debug"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "keygen - Win32 Release" (based on "Win32 (x86) Console Application")
+!MESSAGE "keygen - Win32 Debug" (based on "Win32 (x86) Console Application")
+!MESSAGE
+!ERROR An invalid configuration is specified.
+!ENDIF
+
+!IF "$(OS)" == "Windows_NT"
+NULL=
+!ELSE
+NULL=nul
+!ENDIF
+
+!IF "$(CFG)" == "keygen - Win32 Release"
+
+OUTDIR=.\Release
+INTDIR=.\Release
+
+ALL : "..\..\..\Build\Release\dnssec-keygen.exe"
+
+
+CLEAN :
+ -@erase "$(INTDIR)\dnssec-keygen.obj"
+ -@erase "$(INTDIR)\dnssectool.obj"
+ -@erase "$(INTDIR)\vc60.idb"
+ -@erase "..\..\..\Build\Release\dnssec-keygen.exe"
+
+"$(OUTDIR)" :
+ if not exist "$(OUTDIR)/$(NULL)" mkdir "$(OUTDIR)"
+
+CPP=cl.exe
+CPP_PROJ=/nologo /MT /W3 /GX /O2 /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "NDEBUG" /D "__STDC__" /D "WIN32" /D "_CONSOLE" /D "_MBCS" /Fp"$(INTDIR)\keygen.pch" /YX /Fo"$(INTDIR)\\" /Fd"$(INTDIR)\\" /FD /c
+
+.c{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.c{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+RSC=rc.exe
+BSC32=bscmake.exe
+BSC32_FLAGS=/nologo /o"$(OUTDIR)\keygen.bsc"
+BSC32_SBRS= \
+
+LINK32=link.exe
+LINK32_FLAGS=user32.lib advapi32.lib ../../../lib/isc/win32/Release/libisc.lib ../../../lib/dns/win32/Release/libdns.lib /nologo /subsystem:console /incremental:no /pdb:"$(OUTDIR)\dnssec-keygen.pdb" /machine:I386 /out:"../../../Build/Release/dnssec-keygen.exe"
+LINK32_OBJS= \
+ "$(INTDIR)\dnssec-keygen.obj" \
+ "$(INTDIR)\dnssectool.obj"
+
+"..\..\..\Build\Release\dnssec-keygen.exe" : "$(OUTDIR)" $(DEF_FILE) $(LINK32_OBJS)
+ $(LINK32) @<<
+ $(LINK32_FLAGS) $(LINK32_OBJS)
+<<
+
+!ELSEIF "$(CFG)" == "keygen - Win32 Debug"
+
+OUTDIR=.\Debug
+INTDIR=.\Debug
+# Begin Custom Macros
+OutDir=.\Debug
+# End Custom Macros
+
+ALL : "..\..\..\Build\Debug\dnssec-keygen.exe" "$(OUTDIR)\keygen.bsc"
+
+
+CLEAN :
+ -@erase "$(INTDIR)\dnssec-keygen.obj"
+ -@erase "$(INTDIR)\dnssec-keygen.sbr"
+ -@erase "$(INTDIR)\dnssectool.obj"
+ -@erase "$(INTDIR)\dnssectool.sbr"
+ -@erase "$(INTDIR)\vc60.idb"
+ -@erase "$(INTDIR)\vc60.pdb"
+ -@erase "$(OUTDIR)\dnssec-keygen.pdb"
+ -@erase "$(OUTDIR)\keygen.bsc"
+ -@erase "..\..\..\Build\Debug\dnssec-keygen.exe"
+ -@erase "..\..\..\Build\Debug\dnssec-keygen.ilk"
+
+"$(OUTDIR)" :
+ if not exist "$(OUTDIR)/$(NULL)" mkdir "$(OUTDIR)"
+
+CPP=cl.exe
+CPP_PROJ=/nologo /MTd /W3 /Gm /GX /ZI /Od /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "_DEBUG" /D "WIN32" /D "__STDC__" /D "_CONSOLE" /D "_MBCS" /FR"$(INTDIR)\\" /Fo"$(INTDIR)\\" /Fd"$(INTDIR)\\" /FD /GZ /c
+
+.c{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.c{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+RSC=rc.exe
+BSC32=bscmake.exe
+BSC32_FLAGS=/nologo /o"$(OUTDIR)\keygen.bsc"
+BSC32_SBRS= \
+ "$(INTDIR)\dnssec-keygen.sbr" \
+ "$(INTDIR)\dnssectool.sbr"
+
+"$(OUTDIR)\keygen.bsc" : "$(OUTDIR)" $(BSC32_SBRS)
+ $(BSC32) @<<
+ $(BSC32_FLAGS) $(BSC32_SBRS)
+<<
+
+LINK32=link.exe
+LINK32_FLAGS=user32.lib advapi32.lib ../../../lib/isc/win32/Debug/libisc.lib ../../../lib/dns/win32/Debug/libdns.lib /nologo /subsystem:console /incremental:yes /pdb:"$(OUTDIR)\dnssec-keygen.pdb" /debug /machine:I386 /out:"../../../Build/Debug/dnssec-keygen.exe" /pdbtype:sept
+LINK32_OBJS= \
+ "$(INTDIR)\dnssec-keygen.obj" \
+ "$(INTDIR)\dnssectool.obj"
+
+"..\..\..\Build\Debug\dnssec-keygen.exe" : "$(OUTDIR)" $(DEF_FILE) $(LINK32_OBJS)
+ $(LINK32) @<<
+ $(LINK32_FLAGS) $(LINK32_OBJS)
+<<
+
+!ENDIF
+
+
+!IF "$(NO_EXTERNAL_DEPS)" != "1"
+!IF EXISTS("keygen.dep")
+!INCLUDE "keygen.dep"
+!ELSE
+!MESSAGE Warning: cannot find "keygen.dep"
+!ENDIF
+!ENDIF
+
+
+!IF "$(CFG)" == "keygen - Win32 Release" || "$(CFG)" == "keygen - Win32 Debug"
+SOURCE="..\dnssec-keygen.c"
+
+!IF "$(CFG)" == "keygen - Win32 Release"
+
+
+"$(INTDIR)\dnssec-keygen.obj" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ELSEIF "$(CFG)" == "keygen - Win32 Debug"
+
+
+"$(INTDIR)\dnssec-keygen.obj" "$(INTDIR)\dnssec-keygen.sbr" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ENDIF
+
+SOURCE=..\dnssectool.c
+
+!IF "$(CFG)" == "keygen - Win32 Release"
+
+
+"$(INTDIR)\dnssectool.obj" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ELSEIF "$(CFG)" == "keygen - Win32 Debug"
+
+
+"$(INTDIR)\dnssectool.obj" "$(INTDIR)\dnssectool.sbr" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ENDIF
+
+
+!ENDIF
+
diff --git a/usr.sbin/bind/bin/dnssec/win32/makekeyset.dsp b/usr.sbin/bind/bin/dnssec/win32/makekeyset.dsp
new file mode 100644
index 00000000000..718db7818d7
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/makekeyset.dsp
@@ -0,0 +1,107 @@
+# Microsoft Developer Studio Project File - Name="makekeyset" - Package Owner=<4>
+# Microsoft Developer Studio Generated Build File, Format Version 6.00
+# ** DO NOT EDIT **
+
+# TARGTYPE "Win32 (x86) Console Application" 0x0103
+
+CFG=makekeyset - Win32 Debug
+!MESSAGE This is not a valid makefile. To build this project using NMAKE,
+!MESSAGE use the Export Makefile command and run
+!MESSAGE
+!MESSAGE NMAKE /f "makekeyset.mak".
+!MESSAGE
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "makekeyset.mak" CFG="makekeyset - Win32 Debug"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "makekeyset - Win32 Release" (based on "Win32 (x86) Console Application")
+!MESSAGE "makekeyset - Win32 Debug" (based on "Win32 (x86) Console Application")
+!MESSAGE
+
+# Begin Project
+# PROP AllowPerConfigDependencies 0
+# PROP Scc_ProjName ""
+# PROP Scc_LocalPath ""
+CPP=cl.exe
+RSC=rc.exe
+
+!IF "$(CFG)" == "makekeyset - Win32 Release"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 0
+# PROP BASE Output_Dir "Release"
+# PROP BASE Intermediate_Dir "Release"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 0
+# PROP Output_Dir "Release"
+# PROP Intermediate_Dir "Release"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
+# ADD CPP /nologo /MT /W3 /GX /O2 /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "NDEBUG" /D "__STDC__" /D "WIN32" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
+# ADD BASE RSC /l 0x409 /d "NDEBUG"
+# ADD RSC /l 0x409 /d "NDEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386
+# ADD LINK32 user32.lib advapi32.lib ../../../lib/isc/win32/Release/libisc.lib ../../../lib/dns/win32/Release/libdns.lib /nologo /subsystem:console /machine:I386 /out:"../../../Build/Release/dnssec-makekeyset.exe"
+
+!ELSEIF "$(CFG)" == "makekeyset - Win32 Debug"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 1
+# PROP BASE Output_Dir "Debug"
+# PROP BASE Intermediate_Dir "Debug"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 1
+# PROP Output_Dir "Debug"
+# PROP Intermediate_Dir "Debug"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /GZ /c
+# ADD CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "_DEBUG" /D "WIN32" /D "__STDC__" /D "_CONSOLE" /D "_MBCS" /FR /FD /GZ /c
+# SUBTRACT CPP /X /YX
+# ADD BASE RSC /l 0x409 /d "_DEBUG"
+# ADD RSC /l 0x409 /d "_DEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept
+# ADD LINK32 user32.lib advapi32.lib ../../../lib/isc/win32/Debug/libisc.lib ../../../lib/dns/win32/Debug/libdns.lib /nologo /subsystem:console /debug /machine:I386 /out:"../../../Build/Debug/dnssec-makekeyset.exe" /pdbtype:sept
+
+!ENDIF
+
+# Begin Target
+
+# Name "makekeyset - Win32 Release"
+# Name "makekeyset - Win32 Debug"
+# Begin Group "Source Files"
+
+# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
+# Begin Source File
+
+SOURCE="..\dnssec-makekeyset.c"
+# End Source File
+# Begin Source File
+
+SOURCE=..\dnssectool.c
+# End Source File
+# End Group
+# Begin Group "Header Files"
+
+# PROP Default_Filter "h;hpp;hxx;hm;inl"
+# End Group
+# Begin Group "Resource Files"
+
+# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
+# End Group
+# End Target
+# End Project
diff --git a/usr.sbin/bind/bin/dnssec/win32/makekeyset.dsw b/usr.sbin/bind/bin/dnssec/win32/makekeyset.dsw
new file mode 100644
index 00000000000..c829ce002b1
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/makekeyset.dsw
@@ -0,0 +1,29 @@
+Microsoft Developer Studio Workspace File, Format Version 6.00
+# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE!
+
+###############################################################################
+
+Project: "makekeyset"=".\makekeyset.dsp" - Package Owner=<4>
+
+Package=<5>
+{{{
+}}}
+
+Package=<4>
+{{{
+}}}
+
+###############################################################################
+
+Global:
+
+Package=<5>
+{{{
+}}}
+
+Package=<3>
+{{{
+}}}
+
+###############################################################################
+
diff --git a/usr.sbin/bind/bin/dnssec/win32/makekeyset.mak b/usr.sbin/bind/bin/dnssec/win32/makekeyset.mak
new file mode 100644
index 00000000000..c73753ce501
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/makekeyset.mak
@@ -0,0 +1,227 @@
+# Microsoft Developer Studio Generated NMAKE File, Based on makekeyset.dsp
+!IF "$(CFG)" == ""
+CFG=makekeyset - Win32 Debug
+!MESSAGE No configuration specified. Defaulting to makekeyset - Win32 Debug.
+!ENDIF
+
+!IF "$(CFG)" != "makekeyset - Win32 Release" && "$(CFG)" != "makekeyset - Win32 Debug"
+!MESSAGE Invalid configuration "$(CFG)" specified.
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "makekeyset.mak" CFG="makekeyset - Win32 Debug"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "makekeyset - Win32 Release" (based on "Win32 (x86) Console Application")
+!MESSAGE "makekeyset - Win32 Debug" (based on "Win32 (x86) Console Application")
+!MESSAGE
+!ERROR An invalid configuration is specified.
+!ENDIF
+
+!IF "$(OS)" == "Windows_NT"
+NULL=
+!ELSE
+NULL=nul
+!ENDIF
+
+!IF "$(CFG)" == "makekeyset - Win32 Release"
+
+OUTDIR=.\Release
+INTDIR=.\Release
+
+ALL : "..\..\..\Build\Release\dnssec-makekeyset.exe"
+
+
+CLEAN :
+ -@erase "$(INTDIR)\dnssec-makekeyset.obj"
+ -@erase "$(INTDIR)\dnssectool.obj"
+ -@erase "$(INTDIR)\vc60.idb"
+ -@erase "..\..\..\Build\Release\dnssec-makekeyset.exe"
+
+"$(OUTDIR)" :
+ if not exist "$(OUTDIR)/$(NULL)" mkdir "$(OUTDIR)"
+
+CPP=cl.exe
+CPP_PROJ=/nologo /MT /W3 /GX /O2 /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "NDEBUG" /D "__STDC__" /D "WIN32" /D "_CONSOLE" /D "_MBCS" /Fp"$(INTDIR)\makekeyset.pch" /YX /Fo"$(INTDIR)\\" /Fd"$(INTDIR)\\" /FD /c
+
+.c{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.c{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+RSC=rc.exe
+BSC32=bscmake.exe
+BSC32_FLAGS=/nologo /o"$(OUTDIR)\makekeyset.bsc"
+BSC32_SBRS= \
+
+LINK32=link.exe
+LINK32_FLAGS=user32.lib advapi32.lib ../../../lib/isc/win32/Release/libisc.lib ../../../lib/dns/win32/Release/libdns.lib /nologo /subsystem:console /incremental:no /pdb:"$(OUTDIR)\dnssec-makekeyset.pdb" /machine:I386 /out:"../../../Build/Release/dnssec-makekeyset.exe"
+LINK32_OBJS= \
+ "$(INTDIR)\dnssec-makekeyset.obj" \
+ "$(INTDIR)\dnssectool.obj"
+
+"..\..\..\Build\Release\dnssec-makekeyset.exe" : "$(OUTDIR)" $(DEF_FILE) $(LINK32_OBJS)
+ $(LINK32) @<<
+ $(LINK32_FLAGS) $(LINK32_OBJS)
+<<
+
+!ELSEIF "$(CFG)" == "makekeyset - Win32 Debug"
+
+OUTDIR=.\Debug
+INTDIR=.\Debug
+# Begin Custom Macros
+OutDir=.\Debug
+# End Custom Macros
+
+ALL : "..\..\..\Build\Debug\dnssec-makekeyset.exe" "$(OUTDIR)\makekeyset.bsc"
+
+
+CLEAN :
+ -@erase "$(INTDIR)\dnssec-makekeyset.obj"
+ -@erase "$(INTDIR)\dnssec-makekeyset.sbr"
+ -@erase "$(INTDIR)\dnssectool.obj"
+ -@erase "$(INTDIR)\dnssectool.sbr"
+ -@erase "$(INTDIR)\vc60.idb"
+ -@erase "$(INTDIR)\vc60.pdb"
+ -@erase "$(OUTDIR)\dnssec-makekeyset.pdb"
+ -@erase "$(OUTDIR)\makekeyset.bsc"
+ -@erase "..\..\..\Build\Debug\dnssec-makekeyset.exe"
+ -@erase "..\..\..\Build\Debug\dnssec-makekeyset.ilk"
+
+"$(OUTDIR)" :
+ if not exist "$(OUTDIR)/$(NULL)" mkdir "$(OUTDIR)"
+
+CPP=cl.exe
+CPP_PROJ=/nologo /MTd /W3 /Gm /GX /ZI /Od /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "_DEBUG" /D "WIN32" /D "__STDC__" /D "_CONSOLE" /D "_MBCS" /FR"$(INTDIR)\\" /Fo"$(INTDIR)\\" /Fd"$(INTDIR)\\" /FD /GZ /c
+
+.c{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.c{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+RSC=rc.exe
+BSC32=bscmake.exe
+BSC32_FLAGS=/nologo /o"$(OUTDIR)\makekeyset.bsc"
+BSC32_SBRS= \
+ "$(INTDIR)\dnssec-makekeyset.sbr" \
+ "$(INTDIR)\dnssectool.sbr"
+
+"$(OUTDIR)\makekeyset.bsc" : "$(OUTDIR)" $(BSC32_SBRS)
+ $(BSC32) @<<
+ $(BSC32_FLAGS) $(BSC32_SBRS)
+<<
+
+LINK32=link.exe
+LINK32_FLAGS=user32.lib advapi32.lib ../../../lib/isc/win32/Debug/libisc.lib ../../../lib/dns/win32/Debug/libdns.lib /nologo /subsystem:console /incremental:yes /pdb:"$(OUTDIR)\dnssec-makekeyset.pdb" /debug /machine:I386 /out:"../../../Build/Debug/dnssec-makekeyset.exe" /pdbtype:sept
+LINK32_OBJS= \
+ "$(INTDIR)\dnssec-makekeyset.obj" \
+ "$(INTDIR)\dnssectool.obj"
+
+"..\..\..\Build\Debug\dnssec-makekeyset.exe" : "$(OUTDIR)" $(DEF_FILE) $(LINK32_OBJS)
+ $(LINK32) @<<
+ $(LINK32_FLAGS) $(LINK32_OBJS)
+<<
+
+!ENDIF
+
+
+!IF "$(NO_EXTERNAL_DEPS)" != "1"
+!IF EXISTS("makekeyset.dep")
+!INCLUDE "makekeyset.dep"
+!ELSE
+!MESSAGE Warning: cannot find "makekeyset.dep"
+!ENDIF
+!ENDIF
+
+
+!IF "$(CFG)" == "makekeyset - Win32 Release" || "$(CFG)" == "makekeyset - Win32 Debug"
+SOURCE="..\dnssec-makekeyset.c"
+
+!IF "$(CFG)" == "makekeyset - Win32 Release"
+
+
+"$(INTDIR)\dnssec-makekeyset.obj" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ELSEIF "$(CFG)" == "makekeyset - Win32 Debug"
+
+
+"$(INTDIR)\dnssec-makekeyset.obj" "$(INTDIR)\dnssec-makekeyset.sbr" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ENDIF
+
+SOURCE=..\dnssectool.c
+
+!IF "$(CFG)" == "makekeyset - Win32 Release"
+
+
+"$(INTDIR)\dnssectool.obj" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ELSEIF "$(CFG)" == "makekeyset - Win32 Debug"
+
+
+"$(INTDIR)\dnssectool.obj" "$(INTDIR)\dnssectool.sbr" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ENDIF
+
+
+!ENDIF
+
diff --git a/usr.sbin/bind/bin/dnssec/win32/nsupdate.dsp b/usr.sbin/bind/bin/dnssec/win32/nsupdate.dsp
new file mode 100644
index 00000000000..fc16c0189d5
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/nsupdate.dsp
@@ -0,0 +1,103 @@
+# Microsoft Developer Studio Project File - Name="nsupdate" - Package Owner=<4>
+# Microsoft Developer Studio Generated Build File, Format Version 6.00
+# ** DO NOT EDIT **
+
+# TARGTYPE "Win32 (x86) Console Application" 0x0103
+
+CFG=nsupdate - Win32 Debug
+!MESSAGE This is not a valid makefile. To build this project using NMAKE,
+!MESSAGE use the Export Makefile command and run
+!MESSAGE
+!MESSAGE NMAKE /f "nsupdate.mak".
+!MESSAGE
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "nsupdate.mak" CFG="nsupdate - Win32 Debug"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "nsupdate - Win32 Release" (based on "Win32 (x86) Console Application")
+!MESSAGE "nsupdate - Win32 Debug" (based on "Win32 (x86) Console Application")
+!MESSAGE
+
+# Begin Project
+# PROP AllowPerConfigDependencies 0
+# PROP Scc_ProjName ""
+# PROP Scc_LocalPath ""
+CPP=cl.exe
+RSC=rc.exe
+
+!IF "$(CFG)" == "nsupdate - Win32 Release"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 0
+# PROP BASE Output_Dir "Release"
+# PROP BASE Intermediate_Dir "Release"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 0
+# PROP Output_Dir "Release"
+# PROP Intermediate_Dir "Release"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
+# ADD CPP /nologo /MT /W3 /GX /O2 /I "./" /I "../include" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/lwres/win32/include" /I "../../../lib/lwres/include" /I "../../../lib/lwres/win32/include/lwres" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "WIN32" /D "__STDC__" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
+# ADD BASE RSC /l 0x409 /d "NDEBUG"
+# ADD RSC /l 0x409 /d "NDEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386
+# ADD LINK32 ../../../lib/isc/win32/Release/libisc.lib ../../../lib/dns/win32/Release/libdns.lib ../../../lib/lwres/win32/Release/liblwres.lib user32.lib advapi32.lib ws2_32.lib /nologo /subsystem:console /machine:I386 /out:"../../../Build/Release/nsupdate.exe"
+
+!ELSEIF "$(CFG)" == "nsupdate - Win32 Debug"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 1
+# PROP BASE Output_Dir "Debug"
+# PROP BASE Intermediate_Dir "Debug"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 1
+# PROP Output_Dir "Debug"
+# PROP Intermediate_Dir "Debug"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /GZ /c
+# ADD CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /I "./" /I "../include" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/lwres/win32/include" /I "../../../lib/lwres/include" /I "../../../lib/lwres/win32/include/lwres" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /FR /FD /GZ /c
+# SUBTRACT CPP /X /u /YX
+# ADD BASE RSC /l 0x409 /d "_DEBUG"
+# ADD RSC /l 0x409 /d "_DEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept
+# ADD LINK32 ../../../lib/isc/win32/Debug/libisc.lib ../../../lib/dns/win32/Debug/libdns.lib ../../../lib/lwres/win32/Debug/liblwres.lib user32.lib advapi32.lib ws2_32.lib /nologo /subsystem:console /debug /machine:I386 /out:"../../../Build/Debug/nsupdate.exe" /pdbtype:sept
+
+!ENDIF
+
+# Begin Target
+
+# Name "nsupdate - Win32 Release"
+# Name "nsupdate - Win32 Debug"
+# Begin Group "Source Files"
+
+# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
+# Begin Source File
+
+SOURCE=..\nsupdate.c
+# End Source File
+# End Group
+# Begin Group "Header Files"
+
+# PROP Default_Filter "h;hpp;hxx;hm;inl"
+# End Group
+# Begin Group "Resource Files"
+
+# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
+# End Group
+# End Target
+# End Project
diff --git a/usr.sbin/bind/bin/dnssec/win32/nsupdate.dsw b/usr.sbin/bind/bin/dnssec/win32/nsupdate.dsw
new file mode 100644
index 00000000000..e3b777225a0
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/nsupdate.dsw
@@ -0,0 +1,29 @@
+Microsoft Developer Studio Workspace File, Format Version 6.00
+# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE!
+
+###############################################################################
+
+Project: "nsupdate"=".\nsupdate.dsp" - Package Owner=<4>
+
+Package=<5>
+{{{
+}}}
+
+Package=<4>
+{{{
+}}}
+
+###############################################################################
+
+Global:
+
+Package=<5>
+{{{
+}}}
+
+Package=<3>
+{{{
+}}}
+
+###############################################################################
+
diff --git a/usr.sbin/bind/bin/dnssec/win32/signkey.dsp b/usr.sbin/bind/bin/dnssec/win32/signkey.dsp
new file mode 100644
index 00000000000..411fb6ac695
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/signkey.dsp
@@ -0,0 +1,107 @@
+# Microsoft Developer Studio Project File - Name="signkey" - Package Owner=<4>
+# Microsoft Developer Studio Generated Build File, Format Version 6.00
+# ** DO NOT EDIT **
+
+# TARGTYPE "Win32 (x86) Console Application" 0x0103
+
+CFG=signkey - Win32 Debug
+!MESSAGE This is not a valid makefile. To build this project using NMAKE,
+!MESSAGE use the Export Makefile command and run
+!MESSAGE
+!MESSAGE NMAKE /f "signkey.mak".
+!MESSAGE
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "signkey.mak" CFG="signkey - Win32 Debug"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "signkey - Win32 Release" (based on "Win32 (x86) Console Application")
+!MESSAGE "signkey - Win32 Debug" (based on "Win32 (x86) Console Application")
+!MESSAGE
+
+# Begin Project
+# PROP AllowPerConfigDependencies 0
+# PROP Scc_ProjName ""
+# PROP Scc_LocalPath ""
+CPP=cl.exe
+RSC=rc.exe
+
+!IF "$(CFG)" == "signkey - Win32 Release"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 0
+# PROP BASE Output_Dir "Release"
+# PROP BASE Intermediate_Dir "Release"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 0
+# PROP Output_Dir "Release"
+# PROP Intermediate_Dir "Release"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
+# ADD CPP /nologo /MT /W3 /GX /O2 /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "NDEBUG" /D "__STDC__" /D "WIN32" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
+# ADD BASE RSC /l 0x409 /d "NDEBUG"
+# ADD RSC /l 0x409 /d "NDEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386
+# ADD LINK32 user32.lib advapi32.lib ../../../lib/isc/win32/Release/libisc.lib ../../../lib/dns/win32/Release/libdns.lib /nologo /subsystem:console /machine:I386 /out:"../../../Build/Release/dnssec-signkey.exe"
+
+!ELSEIF "$(CFG)" == "signkey - Win32 Debug"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 1
+# PROP BASE Output_Dir "Debug"
+# PROP BASE Intermediate_Dir "Debug"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 1
+# PROP Output_Dir "Debug"
+# PROP Intermediate_Dir "Debug"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /GZ /c
+# ADD CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "_DEBUG" /D "WIN32" /D "__STDC__" /D "_CONSOLE" /D "_MBCS" /FR /FD /GZ /c
+# SUBTRACT CPP /X /YX
+# ADD BASE RSC /l 0x409 /d "_DEBUG"
+# ADD RSC /l 0x409 /d "_DEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept
+# ADD LINK32 user32.lib advapi32.lib ../../../lib/isc/win32/Debug/libisc.lib ../../../lib/dns/win32/Debug/libdns.lib /nologo /subsystem:console /debug /machine:I386 /out:"../../../Build/Debug/dnssec-signkey.exe" /pdbtype:sept
+
+!ENDIF
+
+# Begin Target
+
+# Name "signkey - Win32 Release"
+# Name "signkey - Win32 Debug"
+# Begin Group "Source Files"
+
+# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
+# Begin Source File
+
+SOURCE="..\dnssec-signkey.c"
+# End Source File
+# Begin Source File
+
+SOURCE=..\dnssectool.c
+# End Source File
+# End Group
+# Begin Group "Header Files"
+
+# PROP Default_Filter "h;hpp;hxx;hm;inl"
+# End Group
+# Begin Group "Resource Files"
+
+# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
+# End Group
+# End Target
+# End Project
diff --git a/usr.sbin/bind/bin/dnssec/win32/signkey.dsw b/usr.sbin/bind/bin/dnssec/win32/signkey.dsw
new file mode 100644
index 00000000000..b4a3fc8aad1
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/signkey.dsw
@@ -0,0 +1,29 @@
+Microsoft Developer Studio Workspace File, Format Version 6.00
+# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE!
+
+###############################################################################
+
+Project: "signkey"=".\signkey.dsp" - Package Owner=<4>
+
+Package=<5>
+{{{
+}}}
+
+Package=<4>
+{{{
+}}}
+
+###############################################################################
+
+Global:
+
+Package=<5>
+{{{
+}}}
+
+Package=<3>
+{{{
+}}}
+
+###############################################################################
+
diff --git a/usr.sbin/bind/bin/dnssec/win32/signkey.mak b/usr.sbin/bind/bin/dnssec/win32/signkey.mak
new file mode 100644
index 00000000000..02db29df98f
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/signkey.mak
@@ -0,0 +1,227 @@
+# Microsoft Developer Studio Generated NMAKE File, Based on signkey.dsp
+!IF "$(CFG)" == ""
+CFG=signkey - Win32 Debug
+!MESSAGE No configuration specified. Defaulting to signkey - Win32 Debug.
+!ENDIF
+
+!IF "$(CFG)" != "signkey - Win32 Release" && "$(CFG)" != "signkey - Win32 Debug"
+!MESSAGE Invalid configuration "$(CFG)" specified.
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "signkey.mak" CFG="signkey - Win32 Debug"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "signkey - Win32 Release" (based on "Win32 (x86) Console Application")
+!MESSAGE "signkey - Win32 Debug" (based on "Win32 (x86) Console Application")
+!MESSAGE
+!ERROR An invalid configuration is specified.
+!ENDIF
+
+!IF "$(OS)" == "Windows_NT"
+NULL=
+!ELSE
+NULL=nul
+!ENDIF
+
+!IF "$(CFG)" == "signkey - Win32 Release"
+
+OUTDIR=.\Release
+INTDIR=.\Release
+
+ALL : "..\..\..\Build\Release\dnssec-signkey.exe"
+
+
+CLEAN :
+ -@erase "$(INTDIR)\dnssec-signkey.obj"
+ -@erase "$(INTDIR)\dnssectool.obj"
+ -@erase "$(INTDIR)\vc60.idb"
+ -@erase "..\..\..\Build\Release\dnssec-signkey.exe"
+
+"$(OUTDIR)" :
+ if not exist "$(OUTDIR)/$(NULL)" mkdir "$(OUTDIR)"
+
+CPP=cl.exe
+CPP_PROJ=/nologo /MT /W3 /GX /O2 /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "NDEBUG" /D "__STDC__" /D "WIN32" /D "_CONSOLE" /D "_MBCS" /Fp"$(INTDIR)\signkey.pch" /YX /Fo"$(INTDIR)\\" /Fd"$(INTDIR)\\" /FD /c
+
+.c{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.c{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+RSC=rc.exe
+BSC32=bscmake.exe
+BSC32_FLAGS=/nologo /o"$(OUTDIR)\signkey.bsc"
+BSC32_SBRS= \
+
+LINK32=link.exe
+LINK32_FLAGS=user32.lib advapi32.lib ../../../lib/isc/win32/Release/libisc.lib ../../../lib/dns/win32/Release/libdns.lib /nologo /subsystem:console /incremental:no /pdb:"$(OUTDIR)\dnssec-signkey.pdb" /machine:I386 /out:"../../../Build/Release/dnssec-signkey.exe"
+LINK32_OBJS= \
+ "$(INTDIR)\dnssec-signkey.obj" \
+ "$(INTDIR)\dnssectool.obj"
+
+"..\..\..\Build\Release\dnssec-signkey.exe" : "$(OUTDIR)" $(DEF_FILE) $(LINK32_OBJS)
+ $(LINK32) @<<
+ $(LINK32_FLAGS) $(LINK32_OBJS)
+<<
+
+!ELSEIF "$(CFG)" == "signkey - Win32 Debug"
+
+OUTDIR=.\Debug
+INTDIR=.\Debug
+# Begin Custom Macros
+OutDir=.\Debug
+# End Custom Macros
+
+ALL : "..\..\..\Build\Debug\dnssec-signkey.exe" "$(OUTDIR)\signkey.bsc"
+
+
+CLEAN :
+ -@erase "$(INTDIR)\dnssec-signkey.obj"
+ -@erase "$(INTDIR)\dnssec-signkey.sbr"
+ -@erase "$(INTDIR)\dnssectool.obj"
+ -@erase "$(INTDIR)\dnssectool.sbr"
+ -@erase "$(INTDIR)\vc60.idb"
+ -@erase "$(INTDIR)\vc60.pdb"
+ -@erase "$(OUTDIR)\dnssec-signkey.pdb"
+ -@erase "$(OUTDIR)\signkey.bsc"
+ -@erase "..\..\..\Build\Debug\dnssec-signkey.exe"
+ -@erase "..\..\..\Build\Debug\dnssec-signkey.ilk"
+
+"$(OUTDIR)" :
+ if not exist "$(OUTDIR)/$(NULL)" mkdir "$(OUTDIR)"
+
+CPP=cl.exe
+CPP_PROJ=/nologo /MTd /W3 /Gm /GX /ZI /Od /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "_DEBUG" /D "WIN32" /D "__STDC__" /D "_CONSOLE" /D "_MBCS" /FR"$(INTDIR)\\" /Fo"$(INTDIR)\\" /Fd"$(INTDIR)\\" /FD /GZ /c
+
+.c{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.c{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+RSC=rc.exe
+BSC32=bscmake.exe
+BSC32_FLAGS=/nologo /o"$(OUTDIR)\signkey.bsc"
+BSC32_SBRS= \
+ "$(INTDIR)\dnssec-signkey.sbr" \
+ "$(INTDIR)\dnssectool.sbr"
+
+"$(OUTDIR)\signkey.bsc" : "$(OUTDIR)" $(BSC32_SBRS)
+ $(BSC32) @<<
+ $(BSC32_FLAGS) $(BSC32_SBRS)
+<<
+
+LINK32=link.exe
+LINK32_FLAGS=user32.lib advapi32.lib ../../../lib/isc/win32/Debug/libisc.lib ../../../lib/dns/win32/Debug/libdns.lib /nologo /subsystem:console /incremental:yes /pdb:"$(OUTDIR)\dnssec-signkey.pdb" /debug /machine:I386 /out:"../../../Build/Debug/dnssec-signkey.exe" /pdbtype:sept
+LINK32_OBJS= \
+ "$(INTDIR)\dnssec-signkey.obj" \
+ "$(INTDIR)\dnssectool.obj"
+
+"..\..\..\Build\Debug\dnssec-signkey.exe" : "$(OUTDIR)" $(DEF_FILE) $(LINK32_OBJS)
+ $(LINK32) @<<
+ $(LINK32_FLAGS) $(LINK32_OBJS)
+<<
+
+!ENDIF
+
+
+!IF "$(NO_EXTERNAL_DEPS)" != "1"
+!IF EXISTS("signkey.dep")
+!INCLUDE "signkey.dep"
+!ELSE
+!MESSAGE Warning: cannot find "signkey.dep"
+!ENDIF
+!ENDIF
+
+
+!IF "$(CFG)" == "signkey - Win32 Release" || "$(CFG)" == "signkey - Win32 Debug"
+SOURCE="..\dnssec-signkey.c"
+
+!IF "$(CFG)" == "signkey - Win32 Release"
+
+
+"$(INTDIR)\dnssec-signkey.obj" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ELSEIF "$(CFG)" == "signkey - Win32 Debug"
+
+
+"$(INTDIR)\dnssec-signkey.obj" "$(INTDIR)\dnssec-signkey.sbr" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ENDIF
+
+SOURCE=..\dnssectool.c
+
+!IF "$(CFG)" == "signkey - Win32 Release"
+
+
+"$(INTDIR)\dnssectool.obj" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ELSEIF "$(CFG)" == "signkey - Win32 Debug"
+
+
+"$(INTDIR)\dnssectool.obj" "$(INTDIR)\dnssectool.sbr" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ENDIF
+
+
+!ENDIF
+
diff --git a/usr.sbin/bind/bin/dnssec/win32/signzone.dsp b/usr.sbin/bind/bin/dnssec/win32/signzone.dsp
new file mode 100644
index 00000000000..e5aa3d32dea
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/signzone.dsp
@@ -0,0 +1,107 @@
+# Microsoft Developer Studio Project File - Name="signzone" - Package Owner=<4>
+# Microsoft Developer Studio Generated Build File, Format Version 6.00
+# ** DO NOT EDIT **
+
+# TARGTYPE "Win32 (x86) Console Application" 0x0103
+
+CFG=signzone - Win32 Debug
+!MESSAGE This is not a valid makefile. To build this project using NMAKE,
+!MESSAGE use the Export Makefile command and run
+!MESSAGE
+!MESSAGE NMAKE /f "signzone.mak".
+!MESSAGE
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "signzone.mak" CFG="signzone - Win32 Debug"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "signzone - Win32 Release" (based on "Win32 (x86) Console Application")
+!MESSAGE "signzone - Win32 Debug" (based on "Win32 (x86) Console Application")
+!MESSAGE
+
+# Begin Project
+# PROP AllowPerConfigDependencies 0
+# PROP Scc_ProjName ""
+# PROP Scc_LocalPath ""
+CPP=cl.exe
+RSC=rc.exe
+
+!IF "$(CFG)" == "signzone - Win32 Release"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 0
+# PROP BASE Output_Dir "Release"
+# PROP BASE Intermediate_Dir "Release"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 0
+# PROP Output_Dir "Release"
+# PROP Intermediate_Dir "Release"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
+# ADD CPP /nologo /MT /W3 /GX /O2 /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "NDEBUG" /D "__STDC__" /D "WIN32" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
+# ADD BASE RSC /l 0x409 /d "NDEBUG"
+# ADD RSC /l 0x409 /d "NDEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386
+# ADD LINK32 user32.lib advapi32.lib ../../../lib/isc/win32/Release/libisc.lib ../../../lib/dns/win32/Release/libdns.lib /nologo /subsystem:console /machine:I386 /out:"../../../Build/Release/dnssec-signzone.exe"
+
+!ELSEIF "$(CFG)" == "signzone - Win32 Debug"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 1
+# PROP BASE Output_Dir "Debug"
+# PROP BASE Intermediate_Dir "Debug"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 1
+# PROP Output_Dir "Debug"
+# PROP Intermediate_Dir "Debug"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /GZ /c
+# ADD CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "_DEBUG" /D "WIN32" /D "__STDC__" /D "_CONSOLE" /D "_MBCS" /FR /FD /GZ /c
+# SUBTRACT CPP /X /YX
+# ADD BASE RSC /l 0x409 /d "_DEBUG"
+# ADD RSC /l 0x409 /d "_DEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept
+# ADD LINK32 user32.lib advapi32.lib ../../../lib/isc/win32/Debug/libisc.lib ../../../lib/dns/win32/Debug/libdns.lib /nologo /subsystem:console /debug /machine:I386 /out:"../../../Build/Debug/dnssec-signzone.exe" /pdbtype:sept
+
+!ENDIF
+
+# Begin Target
+
+# Name "signzone - Win32 Release"
+# Name "signzone - Win32 Debug"
+# Begin Group "Source Files"
+
+# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
+# Begin Source File
+
+SOURCE="..\dnssec-signzone.c"
+# End Source File
+# Begin Source File
+
+SOURCE=..\dnssectool.c
+# End Source File
+# End Group
+# Begin Group "Header Files"
+
+# PROP Default_Filter "h;hpp;hxx;hm;inl"
+# End Group
+# Begin Group "Resource Files"
+
+# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
+# End Group
+# End Target
+# End Project
diff --git a/usr.sbin/bind/bin/dnssec/win32/signzone.dsw b/usr.sbin/bind/bin/dnssec/win32/signzone.dsw
new file mode 100644
index 00000000000..67f5647f2e1
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/signzone.dsw
@@ -0,0 +1,29 @@
+Microsoft Developer Studio Workspace File, Format Version 6.00
+# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE!
+
+###############################################################################
+
+Project: "signzone"=".\signzone.dsp" - Package Owner=<4>
+
+Package=<5>
+{{{
+}}}
+
+Package=<4>
+{{{
+}}}
+
+###############################################################################
+
+Global:
+
+Package=<5>
+{{{
+}}}
+
+Package=<3>
+{{{
+}}}
+
+###############################################################################
+
diff --git a/usr.sbin/bind/bin/dnssec/win32/signzone.mak b/usr.sbin/bind/bin/dnssec/win32/signzone.mak
new file mode 100644
index 00000000000..19e604e15f4
--- /dev/null
+++ b/usr.sbin/bind/bin/dnssec/win32/signzone.mak
@@ -0,0 +1,227 @@
+# Microsoft Developer Studio Generated NMAKE File, Based on signzone.dsp
+!IF "$(CFG)" == ""
+CFG=signzone - Win32 Debug
+!MESSAGE No configuration specified. Defaulting to signzone - Win32 Debug.
+!ENDIF
+
+!IF "$(CFG)" != "signzone - Win32 Release" && "$(CFG)" != "signzone - Win32 Debug"
+!MESSAGE Invalid configuration "$(CFG)" specified.
+!MESSAGE You can specify a configuration when running NMAKE
+!MESSAGE by defining the macro CFG on the command line. For example:
+!MESSAGE
+!MESSAGE NMAKE /f "signzone.mak" CFG="signzone - Win32 Debug"
+!MESSAGE
+!MESSAGE Possible choices for configuration are:
+!MESSAGE
+!MESSAGE "signzone - Win32 Release" (based on "Win32 (x86) Console Application")
+!MESSAGE "signzone - Win32 Debug" (based on "Win32 (x86) Console Application")
+!MESSAGE
+!ERROR An invalid configuration is specified.
+!ENDIF
+
+!IF "$(OS)" == "Windows_NT"
+NULL=
+!ELSE
+NULL=nul
+!ENDIF
+
+!IF "$(CFG)" == "signzone - Win32 Release"
+
+OUTDIR=.\Release
+INTDIR=.\Release
+
+ALL : "..\..\..\Build\Release\dnssec-signzone.exe"
+
+
+CLEAN :
+ -@erase "$(INTDIR)\dnssec-signzone.obj"
+ -@erase "$(INTDIR)\dnssectool.obj"
+ -@erase "$(INTDIR)\vc60.idb"
+ -@erase "..\..\..\Build\Release\dnssec-signzone.exe"
+
+"$(OUTDIR)" :
+ if not exist "$(OUTDIR)/$(NULL)" mkdir "$(OUTDIR)"
+
+CPP=cl.exe
+CPP_PROJ=/nologo /MT /W3 /GX /O2 /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "NDEBUG" /D "__STDC__" /D "WIN32" /D "_CONSOLE" /D "_MBCS" /Fp"$(INTDIR)\signzone.pch" /YX /Fo"$(INTDIR)\\" /Fd"$(INTDIR)\\" /FD /c
+
+.c{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.c{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+RSC=rc.exe
+BSC32=bscmake.exe
+BSC32_FLAGS=/nologo /o"$(OUTDIR)\signzone.bsc"
+BSC32_SBRS= \
+
+LINK32=link.exe
+LINK32_FLAGS=user32.lib advapi32.lib ../../../lib/isc/win32/Release/libisc.lib ../../../lib/dns/win32/Release/libdns.lib /nologo /subsystem:console /incremental:no /pdb:"$(OUTDIR)\dnssec-signzone.pdb" /machine:I386 /out:"../../../Build/Release/dnssec-signzone.exe"
+LINK32_OBJS= \
+ "$(INTDIR)\dnssec-signzone.obj" \
+ "$(INTDIR)\dnssectool.obj"
+
+"..\..\..\Build\Release\dnssec-signzone.exe" : "$(OUTDIR)" $(DEF_FILE) $(LINK32_OBJS)
+ $(LINK32) @<<
+ $(LINK32_FLAGS) $(LINK32_OBJS)
+<<
+
+!ELSEIF "$(CFG)" == "signzone - Win32 Debug"
+
+OUTDIR=.\Debug
+INTDIR=.\Debug
+# Begin Custom Macros
+OutDir=.\Debug
+# End Custom Macros
+
+ALL : "..\..\..\Build\Debug\dnssec-signzone.exe" "$(OUTDIR)\signzone.bsc"
+
+
+CLEAN :
+ -@erase "$(INTDIR)\dnssec-signzone.obj"
+ -@erase "$(INTDIR)\dnssec-signzone.sbr"
+ -@erase "$(INTDIR)\dnssectool.obj"
+ -@erase "$(INTDIR)\dnssectool.sbr"
+ -@erase "$(INTDIR)\vc60.idb"
+ -@erase "$(INTDIR)\vc60.pdb"
+ -@erase "$(OUTDIR)\dnssec-signzone.pdb"
+ -@erase "$(OUTDIR)\signzone.bsc"
+ -@erase "..\..\..\Build\Debug\dnssec-signzone.exe"
+ -@erase "..\..\..\Build\Debug\dnssec-signzone.ilk"
+
+"$(OUTDIR)" :
+ if not exist "$(OUTDIR)/$(NULL)" mkdir "$(OUTDIR)"
+
+CPP=cl.exe
+CPP_PROJ=/nologo /MTd /W3 /Gm /GX /ZI /Od /I "./" /I "../../../" /I "../../../lib/isc/win32" /I "../../../lib/isc/win32/include" /I "../../../lib/isc/include" /I "../../../lib/dns/include" /I "../../../lib/dns/sec/dst/include" /D "_DEBUG" /D "WIN32" /D "__STDC__" /D "_CONSOLE" /D "_MBCS" /FR"$(INTDIR)\\" /Fo"$(INTDIR)\\" /Fd"$(INTDIR)\\" /FD /GZ /c
+
+.c{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.obj::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.c{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cpp{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+.cxx{$(INTDIR)}.sbr::
+ $(CPP) @<<
+ $(CPP_PROJ) $<
+<<
+
+RSC=rc.exe
+BSC32=bscmake.exe
+BSC32_FLAGS=/nologo /o"$(OUTDIR)\signzone.bsc"
+BSC32_SBRS= \
+ "$(INTDIR)\dnssec-signzone.sbr" \
+ "$(INTDIR)\dnssectool.sbr"
+
+"$(OUTDIR)\signzone.bsc" : "$(OUTDIR)" $(BSC32_SBRS)
+ $(BSC32) @<<
+ $(BSC32_FLAGS) $(BSC32_SBRS)
+<<
+
+LINK32=link.exe
+LINK32_FLAGS=user32.lib advapi32.lib ../../../lib/isc/win32/Debug/libisc.lib ../../../lib/dns/win32/Debug/libdns.lib /nologo /subsystem:console /incremental:yes /pdb:"$(OUTDIR)\dnssec-signzone.pdb" /debug /machine:I386 /out:"../../../Build/Debug/dnssec-signzone.exe" /pdbtype:sept
+LINK32_OBJS= \
+ "$(INTDIR)\dnssec-signzone.obj" \
+ "$(INTDIR)\dnssectool.obj"
+
+"..\..\..\Build\Debug\dnssec-signzone.exe" : "$(OUTDIR)" $(DEF_FILE) $(LINK32_OBJS)
+ $(LINK32) @<<
+ $(LINK32_FLAGS) $(LINK32_OBJS)
+<<
+
+!ENDIF
+
+
+!IF "$(NO_EXTERNAL_DEPS)" != "1"
+!IF EXISTS("signzone.dep")
+!INCLUDE "signzone.dep"
+!ELSE
+!MESSAGE Warning: cannot find "signzone.dep"
+!ENDIF
+!ENDIF
+
+
+!IF "$(CFG)" == "signzone - Win32 Release" || "$(CFG)" == "signzone - Win32 Debug"
+SOURCE="..\dnssec-signzone.c"
+
+!IF "$(CFG)" == "signzone - Win32 Release"
+
+
+"$(INTDIR)\dnssec-signzone.obj" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ELSEIF "$(CFG)" == "signzone - Win32 Debug"
+
+
+"$(INTDIR)\dnssec-signzone.obj" "$(INTDIR)\dnssec-signzone.sbr" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ENDIF
+
+SOURCE=..\dnssectool.c
+
+!IF "$(CFG)" == "signzone - Win32 Release"
+
+
+"$(INTDIR)\dnssectool.obj" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ELSEIF "$(CFG)" == "signzone - Win32 Debug"
+
+
+"$(INTDIR)\dnssectool.obj" "$(INTDIR)\dnssectool.sbr" : $(SOURCE) "$(INTDIR)"
+ $(CPP) $(CPP_PROJ) $(SOURCE)
+
+
+!ENDIF
+
+
+!ENDIF
+