dst_api.c revision 89bbdd1f694c7237c29e2fefc0eaac47c7fe544f
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews/*
499b34cea04a46823d003d4c0520c8b03e8513cbBrian Wellington * Portions Copyright (C) 2004-2011 Internet Systems Consortium, Inc. ("ISC")
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence * Portions Copyright (C) 1999-2003 Internet Software Consortium.
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews *
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews * Permission to use, copy, modify, and/or distribute this software for any
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews * purpose with or without fee is hereby granted, provided that the above
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence * copyright notice and this permission notice appear in all copies.
15a44745412679c30a6d022733925af70a38b715David Lawrence *
15a44745412679c30a6d022733925af70a38b715David Lawrence * THE SOFTWARE IS PROVIDED "AS IS" AND ISC AND NETWORK ASSOCIATES DISCLAIMS
15a44745412679c30a6d022733925af70a38b715David Lawrence * ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
15a44745412679c30a6d022733925af70a38b715David Lawrence * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE
15a44745412679c30a6d022733925af70a38b715David Lawrence * FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
15a44745412679c30a6d022733925af70a38b715David Lawrence * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15a44745412679c30a6d022733925af70a38b715David Lawrence * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR
15a44745412679c30a6d022733925af70a38b715David Lawrence * IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews *
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews * Portions Copyright (C) 1995-2000 by Network Associates, Inc.
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews *
0c310d16b05ee94743d33f6920907edee6084fc8Michael Graff * Permission to use, copy, modify, and/or distribute this software for any
0c310d16b05ee94743d33f6920907edee6084fc8Michael Graff * purpose with or without fee is hereby granted, provided that the above
de153390f5a1f6d4fa86af91d4cae772d9846ca0Mark Andrews * copyright notice and this permission notice appear in all copies.
0c310d16b05ee94743d33f6920907edee6084fc8Michael Graff *
822f6cdabb1edd44472c7a758b5cae71376fa9beBrian Wellington * THE SOFTWARE IS PROVIDED "AS IS" AND ISC AND NETWORK ASSOCIATES DISCLAIMS
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington * ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence * FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
25a66b4e41e2b0a2af4840749bac80ae78c678bfMark Andrews * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR
973a19342597823f111fce6a8cd5adfd0e2e7c0dMark Andrews * IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
0c310d16b05ee94743d33f6920907edee6084fc8Michael Graff */
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence/*
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence * Principal Author: Brian Wellington
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence * $Id: dst_api.c,v 1.65 2011/10/20 21:20:02 marka Exp $
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence */
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews/*! \file */
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews#include <config.h>
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews#include <stdlib.h>
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson#include <time.h>
5fc7ba3e1ac5d72239e9971e0f469dd5796738f9Andreas Gustafsson
5fc7ba3e1ac5d72239e9971e0f469dd5796738f9Andreas Gustafsson#include <isc/buffer.h>
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#include <isc/dir.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/entropy.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/fsaccess.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/hmacsha.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/lex.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/mem.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/once.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/platform.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/print.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/refcount.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/random.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/string.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/time.h>
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews#include <isc/util.h>
eb6bd543c7d072efdca509eb17f8f301c1467b53Mark Andrews
deaaf94332abbfdb3aff53675546acfed16e5eb6Mark Andrews#include <dns/fixedname.h>
0b056755b2f423ba5f6adac8f7851d78f7d11437David Lawrence#include <dns/keyvalues.h>
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence#include <dns/name.h>
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews#include <dns/rdata.h>
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews#include <dns/rdataclass.h>
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence#include <dns/ttl.h>
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence#include <dns/types.h>
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence#include <dst/result.h>
0b056755b2f423ba5f6adac8f7851d78f7d11437David Lawrence
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence#include "dst_internal.h"
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence#define DST_AS_STR(t) ((t).value.as_textregion.base)
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrencestatic dst_func_t *dst_t_func[DST_MAX_ALGS];
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence#ifdef BIND9
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrencestatic isc_entropy_t *dst_entropy_pool = NULL;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence#endif
0b056755b2f423ba5f6adac8f7851d78f7d11437David Lawrencestatic unsigned int dst_entropy_flags = 0;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrencestatic isc_boolean_t dst_initialized = ISC_FALSE;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrencevoid gss_log(int level, const char *fmt, ...) ISC_FORMAT_PRINTF(2, 3);
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrenceisc_mem_t *dst__memory_pool = NULL;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence/*
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence * Static functions.
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence */
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrencestatic dst_key_t * get_key_struct(dns_name_t *name,
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence unsigned int alg,
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson unsigned int flags,
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence unsigned int protocol,
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson unsigned int bits,
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson dns_rdataclass_t rdclass,
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson dns_ttl_t ttl,
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson isc_mem_t *mctx);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafssonstatic isc_result_t write_public_key(const dst_key_t *key, int type,
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson const char *directory);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafssonstatic isc_result_t buildfilename(dns_name_t *name,
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence dns_keytag_t id,
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson unsigned int alg,
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson unsigned int type,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence const char *directory,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence isc_buffer_t *out);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencestatic isc_result_t computeid(dst_key_t *key);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencestatic isc_result_t frombuffer(dns_name_t *name,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence unsigned int alg,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence unsigned int flags,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence unsigned int protocol,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence dns_rdataclass_t rdclass,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence isc_buffer_t *source,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence isc_mem_t *mctx,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence dst_key_t **keyp);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencestatic isc_result_t algorithm_status(unsigned int alg);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencestatic isc_result_t addsuffix(char *filename, int len,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence const char *dirname, const char *ofilename,
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence const char *suffix);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington#define RETERR(x) \
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington do { \
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington result = (x); \
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence if (result != ISC_R_SUCCESS) \
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence goto out; \
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence } while (0)
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence#define CHECKALG(alg) \
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence do { \
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence isc_result_t _r; \
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence _r = algorithm_status(alg); \
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence if (_r != ISC_R_SUCCESS) \
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence return (_r); \
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence } while (0); \
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence#if defined(OPENSSL) && defined(BIND9)
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencestatic void *
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencedefault_memalloc(void *arg, size_t size) {
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence UNUSED(arg);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence if (size == 0U)
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence size = 1;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence return (malloc(size));
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence}
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencestatic void
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencedefault_memfree(void *arg, void *ptr) {
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence UNUSED(arg);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence free(ptr);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence}
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence#endif
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrenceisc_result_t
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencedst_lib_init(isc_mem_t *mctx, isc_entropy_t *ectx, unsigned int eflags) {
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence return (dst_lib_init2(mctx, ectx, NULL, eflags));
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence}
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrenceisc_result_t
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencedst_lib_init2(isc_mem_t *mctx, isc_entropy_t *ectx,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence const char *engine, unsigned int eflags) {
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence isc_result_t result;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence REQUIRE(mctx != NULL);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence#ifdef BIND9
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence REQUIRE(ectx != NULL);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence#else
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence UNUSED(ectx);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence#endif
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence REQUIRE(dst_initialized == ISC_FALSE);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence#ifndef OPENSSL
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence UNUSED(engine);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence#endif
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence dst__memory_pool = NULL;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence#if defined(OPENSSL) && defined(BIND9)
fd4810861c0c0ccb9aebde94e9d289442b2630dbMark Andrews UNUSED(mctx);
fd4810861c0c0ccb9aebde94e9d289442b2630dbMark Andrews /*
fd4810861c0c0ccb9aebde94e9d289442b2630dbMark Andrews * When using --with-openssl, there seems to be no good way of not
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence * leaking memory due to the openssl error handling mechanism.
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence * Avoid assertions by using a local memory context and not checking
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence * for leaks on exit. Note: as there are leaks we cannot use
7ab0e69f61e61e81d489c95c7ebd981e74e7ef16Andreas Gustafsson * ISC_MEMFLAG_INTERNAL as it will free up memory still being used
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews * by libcrypto.
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews */
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews result = isc_mem_createx2(0, 0, default_memalloc, default_memfree,
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews NULL, &dst__memory_pool, 0);
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews if (result != ISC_R_SUCCESS)
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews return (result);
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews isc_mem_setname(dst__memory_pool, "dst", NULL);
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews#ifndef OPENSSL_LEAKS
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews isc_mem_setdestroycheck(dst__memory_pool, ISC_FALSE);
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews#endif
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews#else
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews isc_mem_attach(mctx, &dst__memory_pool);
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews#endif
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews#ifdef BIND9
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews isc_entropy_attach(ectx, &dst_entropy_pool);
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews#endif
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews dst_entropy_flags = eflags;
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrews dst_result_register();
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews memset(dst_t_func, 0, sizeof(dst_t_func));
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews RETERR(dst__hmacmd5_init(&dst_t_func[DST_ALG_HMACMD5]));
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews RETERR(dst__hmacsha1_init(&dst_t_func[DST_ALG_HMACSHA1]));
78838d3e0cd62423c23de5503910e01884d2104bBrian Wellington RETERR(dst__hmacsha224_init(&dst_t_func[DST_ALG_HMACSHA224]));
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews RETERR(dst__hmacsha256_init(&dst_t_func[DST_ALG_HMACSHA256]));
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews RETERR(dst__hmacsha384_init(&dst_t_func[DST_ALG_HMACSHA384]));
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews RETERR(dst__hmacsha512_init(&dst_t_func[DST_ALG_HMACSHA512]));
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews#ifdef OPENSSL
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews RETERR(dst__openssl_init(engine));
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews RETERR(dst__opensslrsa_init(&dst_t_func[DST_ALG_RSAMD5],
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews DST_ALG_RSAMD5));
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews RETERR(dst__opensslrsa_init(&dst_t_func[DST_ALG_RSASHA1],
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews DST_ALG_RSASHA1));
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews RETERR(dst__opensslrsa_init(&dst_t_func[DST_ALG_NSEC3RSASHA1],
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews DST_ALG_NSEC3RSASHA1));
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews RETERR(dst__opensslrsa_init(&dst_t_func[DST_ALG_RSASHA256],
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews DST_ALG_RSASHA256));
f6407f9a0b890bebbfd5f738d9c4aef3d3315fe9Michael Graff RETERR(dst__opensslrsa_init(&dst_t_func[DST_ALG_RSASHA512],
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews DST_ALG_RSASHA512));
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews#ifdef HAVE_OPENSSL_DSA
2002be4f65776451676df6ee21a2e28f52bcad6dMark Andrews RETERR(dst__openssldsa_init(&dst_t_func[DST_ALG_DSA]));
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews RETERR(dst__openssldsa_init(&dst_t_func[DST_ALG_NSEC3DSA]));
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews#endif
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews RETERR(dst__openssldh_init(&dst_t_func[DST_ALG_DH]));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#ifdef HAVE_OPENSSL_GOST
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews RETERR(dst__opensslgost_init(&dst_t_func[DST_ALG_ECCGOST]));
bed8e84810a80dad3d37870be927d1dfd015f480Mark Andrews#endif
bed8e84810a80dad3d37870be927d1dfd015f480Mark Andrews#ifdef HAVE_OPENSSL_ECDSA
bed8e84810a80dad3d37870be927d1dfd015f480Mark Andrews RETERR(dst__opensslecdsa_init(&dst_t_func[DST_ALG_ECDSA256]));
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews RETERR(dst__opensslecdsa_init(&dst_t_func[DST_ALG_ECDSA384]));
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews#endif
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews#endif /* OPENSSL */
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews#ifdef GSSAPI
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews RETERR(dst__gssapi_init(&dst_t_func[DST_ALG_GSSAPI]));
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews#endif
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews dst_initialized = ISC_TRUE;
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews return (ISC_R_SUCCESS);
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews out:
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews /* avoid immediate crash! */
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews dst_initialized = ISC_TRUE;
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington dst_lib_destroy();
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington return (result);
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington}
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews
613991eef6bb79b9703382aff26cddd0281da915Bob Halleyvoid
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrewsdst_lib_destroy(void) {
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews int i;
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington RUNTIME_CHECK(dst_initialized == ISC_TRUE);
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington dst_initialized = ISC_FALSE;
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington for (i = 0; i < DST_MAX_ALGS; i++)
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington if (dst_t_func[i] != NULL && dst_t_func[i]->cleanup != NULL)
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington dst_t_func[i]->cleanup();
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington#ifdef OPENSSL
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington dst__openssl_destroy();
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington#endif
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington if (dst__memory_pool != NULL)
87ecd67dae468cf5c9bae213c6fa321449b2ebc2Andreas Gustafsson isc_mem_detach(&dst__memory_pool);
87ecd67dae468cf5c9bae213c6fa321449b2ebc2Andreas Gustafsson#ifdef BIND9
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews if (dst_entropy_pool != NULL)
87ecd67dae468cf5c9bae213c6fa321449b2ebc2Andreas Gustafsson isc_entropy_detach(&dst_entropy_pool);
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews#endif
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews}
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrewsisc_boolean_t
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrewsdst_algorithm_supported(unsigned int alg) {
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews REQUIRE(dst_initialized == ISC_TRUE);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
bcd7fdf06ca76eb2f6eb157f56b612c503e062a7Mark Andrews if (alg >= DST_MAX_ALGS || dst_t_func[alg] == NULL)
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews return (ISC_FALSE);
bcd7fdf06ca76eb2f6eb157f56b612c503e062a7Mark Andrews return (ISC_TRUE);
bcd7fdf06ca76eb2f6eb157f56b612c503e062a7Mark Andrews}
bcd7fdf06ca76eb2f6eb157f56b612c503e062a7Mark Andrews
bcd7fdf06ca76eb2f6eb157f56b612c503e062a7Mark Andrewsisc_result_t
bcd7fdf06ca76eb2f6eb157f56b612c503e062a7Mark Andrewsdst_context_create(dst_key_t *key, isc_mem_t *mctx, dst_context_t **dctxp) {
bcd7fdf06ca76eb2f6eb157f56b612c503e062a7Mark Andrews dst_context_t *dctx;
bcd7fdf06ca76eb2f6eb157f56b612c503e062a7Mark Andrews isc_result_t result;
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews REQUIRE(dst_initialized == ISC_TRUE);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson REQUIRE(VALID_KEY(key));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson REQUIRE(mctx != NULL);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson REQUIRE(dctxp != NULL && *dctxp == NULL);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson if (key->func->createctx == NULL)
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (DST_R_UNSUPPORTEDALG);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson if (key->keydata.generic == NULL)
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (DST_R_NULLKEY);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dctx = isc_mem_get(mctx, sizeof(dst_context_t));
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews if (dctx == NULL)
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff return (ISC_R_NOMEMORY);
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews dctx->key = key;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence dctx->mctx = mctx;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence result = key->func->createctx(key, dctx);
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff if (result != ISC_R_SUCCESS) {
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff isc_mem_put(mctx, dctx, sizeof(dst_context_t));
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington return (result);
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington }
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff dctx->magic = CTX_MAGIC;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff *dctxp = dctx;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff return (ISC_R_SUCCESS);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson}
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrencevoid
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssondst_context_destroy(dst_context_t **dctxp) {
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dst_context_t *dctx;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson REQUIRE(dctxp != NULL && VALID_CTX(*dctxp));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dctx = *dctxp;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson INSIST(dctx->key->func->destroyctx != NULL);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dctx->key->func->destroyctx(dctx);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dctx->magic = 0;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_mem_put(dctx->mctx, dctx, sizeof(dst_context_t));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson *dctxp = NULL;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson}
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssonisc_result_t
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssondst_context_adddata(dst_context_t *dctx, const isc_region_t *data) {
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson REQUIRE(VALID_CTX(dctx));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson REQUIRE(data != NULL);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson INSIST(dctx->key->func->adddata != NULL);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (dctx->key->func->adddata(dctx, data));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson}
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssonisc_result_t
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssondst_context_sign(dst_context_t *dctx, isc_buffer_t *sig) {
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dst_key_t *key;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson REQUIRE(VALID_CTX(dctx));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson REQUIRE(sig != NULL);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson key = dctx->key;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson CHECKALG(key->key_alg);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson if (key->keydata.generic == NULL)
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (DST_R_NULLKEY);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence if (key->func->sign == NULL)
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (DST_R_NOTPRIVATEKEY);
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews if (key->func->isprivate == NULL ||
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews key->func->isprivate(key) == ISC_FALSE)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (DST_R_NOTPRIVATEKEY);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (key->func->sign(dctx, sig));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews}
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrewsisc_result_t
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrewsdst_context_verify(dst_context_t *dctx, isc_region_t *sig) {
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews REQUIRE(VALID_CTX(dctx));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews REQUIRE(sig != NULL);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
d981ca645597116d227a48bf37cc5edc061c854dBob Halley CHECKALG(dctx->key->key_alg);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (dctx->key->keydata.generic == NULL)
e6bd97dded968f82e26b270842b789bff7bca422Mark Andrews return (DST_R_NULLKEY);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (dctx->key->func->verify == NULL)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (DST_R_NOTPUBLICKEY);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (dctx->key->func->verify(dctx, sig));
5d2026ea7b5ae43bbd69d98b747f75ba3290bef1Mark Andrews}
f1cae4bcb7ee3060d893f5ab3ba55c1820bf3e4aBrian Wellington
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrewsisc_result_t
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrewsdst_key_computesecret(const dst_key_t *pub, const dst_key_t *priv,
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews isc_buffer_t *secret)
5d2026ea7b5ae43bbd69d98b747f75ba3290bef1Mark Andrews{
6c29053a20f7614167bafa4388c666644a095349Andreas Gustafsson REQUIRE(dst_initialized == ISC_TRUE);
5d2026ea7b5ae43bbd69d98b747f75ba3290bef1Mark Andrews REQUIRE(VALID_KEY(pub) && VALID_KEY(priv));
5d2026ea7b5ae43bbd69d98b747f75ba3290bef1Mark Andrews REQUIRE(secret != NULL);
6c29053a20f7614167bafa4388c666644a095349Andreas Gustafsson
6c29053a20f7614167bafa4388c666644a095349Andreas Gustafsson CHECKALG(pub->key_alg);
5d2026ea7b5ae43bbd69d98b747f75ba3290bef1Mark Andrews CHECKALG(priv->key_alg);
5f7a9845e900bc491db9feab137895721073631fMark Andrews
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews if (pub->keydata.generic == NULL || priv->keydata.generic == NULL)
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews return (DST_R_NULLKEY);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews
389c749a5ee18f1c0d6278ae49f2aae5d5f0d2dcMark Andrews if (pub->key_alg != priv->key_alg ||
368b37b616234fce3d23099eb180f1dd38e1fb62Mark Andrews pub->func->computesecret == NULL ||
389c749a5ee18f1c0d6278ae49f2aae5d5f0d2dcMark Andrews priv->func->computesecret == NULL)
389c749a5ee18f1c0d6278ae49f2aae5d5f0d2dcMark Andrews return (DST_R_KEYCANNOTCOMPUTESECRET);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews
389c749a5ee18f1c0d6278ae49f2aae5d5f0d2dcMark Andrews if (dst_key_isprivate(priv) == ISC_FALSE)
389c749a5ee18f1c0d6278ae49f2aae5d5f0d2dcMark Andrews return (DST_R_NOTPRIVATEKEY);
389c749a5ee18f1c0d6278ae49f2aae5d5f0d2dcMark Andrews
389c749a5ee18f1c0d6278ae49f2aae5d5f0d2dcMark Andrews return (pub->func->computesecret(pub, priv, secret));
389c749a5ee18f1c0d6278ae49f2aae5d5f0d2dcMark Andrews}
389c749a5ee18f1c0d6278ae49f2aae5d5f0d2dcMark Andrews
389c749a5ee18f1c0d6278ae49f2aae5d5f0d2dcMark Andrewsisc_result_t
389c749a5ee18f1c0d6278ae49f2aae5d5f0d2dcMark Andrewsdst_key_tofile(const dst_key_t *key, int type, const char *directory) {
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews isc_result_t ret = ISC_R_SUCCESS;
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews REQUIRE(dst_initialized == ISC_TRUE);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews REQUIRE(VALID_KEY(key));
29c818c7d40fc8898b062903ec703851328a4deaMark Andrews REQUIRE((type & (DST_TYPE_PRIVATE | DST_TYPE_PUBLIC)) != 0);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews CHECKALG(key->key_alg);
f1cae4bcb7ee3060d893f5ab3ba55c1820bf3e4aBrian Wellington
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews if (key->func->tofile == NULL)
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews return (DST_R_UNSUPPORTEDALG);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews if (type & DST_TYPE_PUBLIC) {
29c818c7d40fc8898b062903ec703851328a4deaMark Andrews ret = write_public_key(key, type, directory);
29c818c7d40fc8898b062903ec703851328a4deaMark Andrews if (ret != ISC_R_SUCCESS)
29c818c7d40fc8898b062903ec703851328a4deaMark Andrews return (ret);
29c818c7d40fc8898b062903ec703851328a4deaMark Andrews }
29c818c7d40fc8898b062903ec703851328a4deaMark Andrews
29c818c7d40fc8898b062903ec703851328a4deaMark Andrews if ((type & DST_TYPE_PRIVATE) &&
29c818c7d40fc8898b062903ec703851328a4deaMark Andrews (key->key_flags & DNS_KEYFLAG_TYPEMASK) != DNS_KEYTYPE_NOKEY)
29c818c7d40fc8898b062903ec703851328a4deaMark Andrews return (key->func->tofile(key, directory));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews else
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (ISC_R_SUCCESS);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews}
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrewsisc_result_t
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrencedst_key_fromfile(dns_name_t *name, dns_keytag_t id,
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews unsigned int alg, int type, const char *directory,
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews isc_mem_t *mctx, dst_key_t **keyp)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews{
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews char filename[ISC_DIR_NAMEMAX];
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_buffer_t b;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews dst_key_t *key;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_result_t result;
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews REQUIRE(dst_initialized == ISC_TRUE);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews REQUIRE(dns_name_isabsolute(name));
d981ca645597116d227a48bf37cc5edc061c854dBob Halley REQUIRE((type & (DST_TYPE_PRIVATE | DST_TYPE_PUBLIC)) != 0);
d981ca645597116d227a48bf37cc5edc061c854dBob Halley REQUIRE(mctx != NULL);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews REQUIRE(keyp != NULL && *keyp == NULL);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews CHECKALG(alg);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_buffer_init(&b, filename, sizeof(filename));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews result = buildfilename(name, id, alg, type, directory, &b);
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews if (result != ISC_R_SUCCESS)
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews return (result);
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews key = NULL;
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews result = dst_key_fromnamedfile(filename, NULL, type, mctx, &key);
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews if (result != ISC_R_SUCCESS)
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews return (result);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews result = computeid(key);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (result != ISC_R_SUCCESS) {
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews dst_key_free(&key);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (result);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews }
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (!dns_name_equal(name, key->key_name) || id != key->key_id ||
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews alg != key->key_alg) {
d981ca645597116d227a48bf37cc5edc061c854dBob Halley dst_key_free(&key);
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews return (DST_R_INVALIDPRIVATEKEY);
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews }
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence
19d365e4448f1782611280b020987988b7ac3210Mark Andrews *keyp = key;
f1cae4bcb7ee3060d893f5ab3ba55c1820bf3e4aBrian Wellington return (ISC_R_SUCCESS);
19d365e4448f1782611280b020987988b7ac3210Mark Andrews}
19d365e4448f1782611280b020987988b7ac3210Mark Andrews
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrewsisc_result_t
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrewsdst_key_fromnamedfile(const char *filename, const char *dirname,
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews int type, isc_mem_t *mctx, dst_key_t **keyp)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews{
d981ca645597116d227a48bf37cc5edc061c854dBob Halley isc_result_t result;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews dst_key_t *pubkey = NULL, *key = NULL;
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews char *newfilename = NULL;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews int newfilenamelen = 0;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_lex_t *lex = NULL;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence REQUIRE(dst_initialized == ISC_TRUE);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews REQUIRE(filename != NULL);
19d365e4448f1782611280b020987988b7ac3210Mark Andrews REQUIRE((type & (DST_TYPE_PRIVATE | DST_TYPE_PUBLIC)) != 0);
19d365e4448f1782611280b020987988b7ac3210Mark Andrews REQUIRE(mctx != NULL);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews REQUIRE(keyp != NULL && *keyp == NULL);
19d365e4448f1782611280b020987988b7ac3210Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews /* If an absolute path is specified, don't use the key directory */
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#ifndef WIN32
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (filename[0] == '/')
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews dirname = NULL;
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff#else /* WIN32 */
d981ca645597116d227a48bf37cc5edc061c854dBob Halley if (filename[0] == '/' || filename[0] == '\\')
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews dirname = NULL;
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews#endif
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews newfilenamelen = strlen(filename) + 5;
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff if (dirname != NULL)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews newfilenamelen += strlen(dirname) + 1;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews newfilename = isc_mem_get(mctx, newfilenamelen);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (newfilename == NULL)
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews return (ISC_R_NOMEMORY);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews result = addsuffix(newfilename, newfilenamelen,
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews dirname, filename, ".key");
19d365e4448f1782611280b020987988b7ac3210Mark Andrews INSIST(result == ISC_R_SUCCESS);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews
f1cae4bcb7ee3060d893f5ab3ba55c1820bf3e4aBrian Wellington result = dst_key_read_public(newfilename, type, mctx, &pubkey);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews isc_mem_put(mctx, newfilename, newfilenamelen);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews newfilename = NULL;
19d365e4448f1782611280b020987988b7ac3210Mark Andrews if (result != ISC_R_SUCCESS)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (result);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if ((type & (DST_TYPE_PRIVATE | DST_TYPE_PUBLIC)) == DST_TYPE_PUBLIC ||
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews (pubkey->key_flags & DNS_KEYFLAG_TYPEMASK) == DNS_KEYTYPE_NOKEY) {
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews result = computeid(pubkey);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews if (result != ISC_R_SUCCESS) {
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews dst_key_free(&pubkey);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (result);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews }
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews *keyp = pubkey;
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews return (ISC_R_SUCCESS);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews }
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews result = algorithm_status(pubkey->key_alg);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews if (result != ISC_R_SUCCESS) {
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews dst_key_free(&pubkey);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews return (result);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews }
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence key = get_key_struct(pubkey->key_name, pubkey->key_alg,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence pubkey->key_flags, pubkey->key_proto, 0,
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff pubkey->key_class, pubkey->key_ttl, mctx);
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews if (key == NULL) {
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews dst_key_free(&pubkey);
ad7209ea70d346527ffdcda335153831341d9dcfAndreas Gustafsson return (ISC_R_NOMEMORY);
7d8cdd869ed2162a5befda7cc1600136110f54d6Mark Andrews }
7d8cdd869ed2162a5befda7cc1600136110f54d6Mark Andrews
7d8cdd869ed2162a5befda7cc1600136110f54d6Mark Andrews if (key->func->parse == NULL)
d981ca645597116d227a48bf37cc5edc061c854dBob Halley RETERR(DST_R_UNSUPPORTEDALG);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews newfilenamelen = strlen(filename) + 9;
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff if (dirname != NULL)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews newfilenamelen += strlen(dirname) + 1;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews newfilename = isc_mem_get(mctx, newfilenamelen);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (newfilename == NULL)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews RETERR(ISC_R_NOMEMORY);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews result = addsuffix(newfilename, newfilenamelen,
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews dirname, filename, ".private");
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff INSIST(result == ISC_R_SUCCESS);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
78838d3e0cd62423c23de5503910e01884d2104bBrian Wellington RETERR(isc_lex_create(mctx, 1500, &lex));
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews RETERR(isc_lex_openfile(lex, newfilename));
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff isc_mem_put(mctx, newfilename, newfilenamelen);
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews
f0a5bb8f86631ce638cb2b6c65bbb9bcf9b0cdc0Bob Halley RETERR(key->func->parse(key, lex, pubkey));
52637f592f705ca93fadc218e403fd55e8ce4aeaMark Andrews isc_lex_destroy(&lex);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
19d365e4448f1782611280b020987988b7ac3210Mark Andrews RETERR(computeid(key));
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence if (pubkey->key_id != key->key_id)
693ddf84daa745a0ea8ca311a8154dfa03eabc43Andreas Gustafsson RETERR(DST_R_INVALIDPRIVATEKEY);
693ddf84daa745a0ea8ca311a8154dfa03eabc43Andreas Gustafsson dst_key_free(&pubkey);
693ddf84daa745a0ea8ca311a8154dfa03eabc43Andreas Gustafsson
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews *keyp = key;
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews return (ISC_R_SUCCESS);
693ddf84daa745a0ea8ca311a8154dfa03eabc43Andreas Gustafsson
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews out:
693ddf84daa745a0ea8ca311a8154dfa03eabc43Andreas Gustafsson if (pubkey != NULL)
52637f592f705ca93fadc218e403fd55e8ce4aeaMark Andrews dst_key_free(&pubkey);
19d365e4448f1782611280b020987988b7ac3210Mark Andrews if (newfilename != NULL)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_mem_put(mctx, newfilename, newfilenamelen);
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence if (lex != NULL)
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews isc_lex_destroy(&lex);
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence dst_key_free(&key);
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence return (result);
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff}
f0a5bb8f86631ce638cb2b6c65bbb9bcf9b0cdc0Bob Halley
f0a5bb8f86631ce638cb2b6c65bbb9bcf9b0cdc0Bob Halleyisc_result_t
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graffdst_key_todns(const dst_key_t *key, isc_buffer_t *target) {
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews REQUIRE(dst_initialized == ISC_TRUE);
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff REQUIRE(VALID_KEY(key));
52637f592f705ca93fadc218e403fd55e8ce4aeaMark Andrews REQUIRE(target != NULL);
7c0378745269fe49a05904935afc42b85528f53aDavid Lawrence
7c0378745269fe49a05904935afc42b85528f53aDavid Lawrence CHECKALG(key->key_alg);
52637f592f705ca93fadc218e403fd55e8ce4aeaMark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (key->func->todns == NULL)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (DST_R_UNSUPPORTEDALG);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
7e4cda9965e2edf2ec43c57967eec8eff7061ab0Andreas Gustafsson if (isc_buffer_availablelength(target) < 4)
7e4cda9965e2edf2ec43c57967eec8eff7061ab0Andreas Gustafsson return (ISC_R_NOSPACE);
7e4cda9965e2edf2ec43c57967eec8eff7061ab0Andreas Gustafsson isc_buffer_putuint16(target, (isc_uint16_t)(key->key_flags & 0xffff));
7e4cda9965e2edf2ec43c57967eec8eff7061ab0Andreas Gustafsson isc_buffer_putuint8(target, (isc_uint8_t)key->key_proto);
7e4cda9965e2edf2ec43c57967eec8eff7061ab0Andreas Gustafsson isc_buffer_putuint8(target, (isc_uint8_t)key->key_alg);
3a16668468060842e847ea6556e80e1405d35cd6Brian Wellington
7e4cda9965e2edf2ec43c57967eec8eff7061ab0Andreas Gustafsson if (key->key_flags & DNS_KEYFLAG_EXTENDED) {
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington if (isc_buffer_availablelength(target) < 2)
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews return (ISC_R_NOSPACE);
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington isc_buffer_putuint16(target,
7d8cdd869ed2162a5befda7cc1600136110f54d6Mark Andrews (isc_uint16_t)((key->key_flags >> 16)
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington & 0xffff));
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington }
942d1a339b1fe617f7d17d66cb5fccce798d15aeBrian Wellington
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington if (key->keydata.generic == NULL) /*%< NULL KEY */
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington return (ISC_R_SUCCESS);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington return (key->func->todns(key, target));
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews}
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrewsisc_result_t
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrewsdst_key_fromdns(dns_name_t *name, dns_rdataclass_t rdclass,
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington isc_buffer_t *source, isc_mem_t *mctx, dst_key_t **keyp)
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington{
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington isc_uint8_t alg, proto;
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington isc_uint32_t flags, extflags;
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington dst_key_t *key = NULL;
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington dns_keytag_t id, rid;
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington isc_region_t r;
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington isc_result_t result;
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington REQUIRE(dst_initialized);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington isc_buffer_remainingregion(source, &r);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington if (isc_buffer_remaininglength(source) < 4)
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington return (DST_R_INVALIDPUBLICKEY);
f16495732753175e4a9fc144323a12fdcc29b561Brian Wellington flags = isc_buffer_getuint16(source);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington proto = isc_buffer_getuint8(source);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington alg = isc_buffer_getuint8(source);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington
e086935752b6e2f51ef2985fee21ccfff617b115David Lawrence id = dst_region_computeid(&r, alg);
e086935752b6e2f51ef2985fee21ccfff617b115David Lawrence rid = dst_region_computerid(&r, alg);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington if (flags & DNS_KEYFLAG_EXTENDED) {
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington if (isc_buffer_remaininglength(source) < 2)
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington return (DST_R_INVALIDPUBLICKEY);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington extflags = isc_buffer_getuint16(source);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington flags |= (extflags << 16);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington }
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington
7e4cda9965e2edf2ec43c57967eec8eff7061ab0Andreas Gustafsson result = frombuffer(name, alg, flags, proto, rdclass, source,
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington mctx, &key);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington if (result != ISC_R_SUCCESS)
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington return (result);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington key->key_id = id;
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington key->key_rid = rid;
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington *keyp = key;
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington return (ISC_R_SUCCESS);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington}
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellingtonisc_result_t
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellingtondst_key_frombuffer(dns_name_t *name, unsigned int alg,
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington unsigned int flags, unsigned int protocol,
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington dns_rdataclass_t rdclass,
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington isc_buffer_t *source, isc_mem_t *mctx, dst_key_t **keyp)
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington{
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff dst_key_t *key = NULL;
d981ca645597116d227a48bf37cc5edc061c854dBob Halley isc_result_t result;
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington REQUIRE(dst_initialized);
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews result = frombuffer(name, alg, flags, protocol, rdclass, source,
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff mctx, &key);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (result != ISC_R_SUCCESS)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (result);
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews
f305d86668bfd4d4727c3e0f70e7e97a2fa1b772Bob Halley result = computeid(key);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson if (result != ISC_R_SUCCESS) {
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews dst_key_free(&key);
20b20b23948b90cb2f7d7f402da99d09f837efd0David Lawrence return (result);
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence }
8dd5237a27e2e824d18f835dc711573aeb23a173Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews *keyp = key;
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence return (ISC_R_SUCCESS);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews}
f1cae4bcb7ee3060d893f5ab3ba55c1820bf3e4aBrian Wellington
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrewsisc_result_t
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrewsdst_key_tobuffer(const dst_key_t *key, isc_buffer_t *target) {
19d365e4448f1782611280b020987988b7ac3210Mark Andrews REQUIRE(dst_initialized == ISC_TRUE);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews REQUIRE(VALID_KEY(key));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews REQUIRE(target != NULL);
228c679d7a269423019f7c528db92e855f08240bMark Andrews
228c679d7a269423019f7c528db92e855f08240bMark Andrews CHECKALG(key->key_alg);
228c679d7a269423019f7c528db92e855f08240bMark Andrews
228c679d7a269423019f7c528db92e855f08240bMark Andrews if (key->func->todns == NULL)
228c679d7a269423019f7c528db92e855f08240bMark Andrews return (DST_R_UNSUPPORTEDALG);
228c679d7a269423019f7c528db92e855f08240bMark Andrews
228c679d7a269423019f7c528db92e855f08240bMark Andrews return (key->func->todns(key, target));
228c679d7a269423019f7c528db92e855f08240bMark Andrews}
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellingtonisc_result_t
228c679d7a269423019f7c528db92e855f08240bMark Andrewsdst_key_privatefrombuffer(dst_key_t *key, isc_buffer_t *buffer) {
228c679d7a269423019f7c528db92e855f08240bMark Andrews isc_lex_t *lex = NULL;
228c679d7a269423019f7c528db92e855f08240bMark Andrews isc_result_t result = ISC_R_SUCCESS;
228c679d7a269423019f7c528db92e855f08240bMark Andrews
228c679d7a269423019f7c528db92e855f08240bMark Andrews REQUIRE(dst_initialized == ISC_TRUE);
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington REQUIRE(VALID_KEY(key));
228c679d7a269423019f7c528db92e855f08240bMark Andrews REQUIRE(!dst_key_isprivate(key));
228c679d7a269423019f7c528db92e855f08240bMark Andrews REQUIRE(buffer != NULL);
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington if (key->func->parse == NULL)
93ed317bb43658ed48ee7439f7a36bb9bcf80c94Brian Wellington RETERR(DST_R_UNSUPPORTEDALG);
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington RETERR(isc_lex_create(key->mctx, 1500, &lex));
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington RETERR(isc_lex_openbuffer(lex, buffer));
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews RETERR(key->func->parse(key, lex, NULL));
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews out:
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews if (lex != NULL)
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews isc_lex_destroy(&lex);
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews return (result);
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews}
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrewsgss_ctx_id_t
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrewsdst_key_getgssctx(const dst_key_t *key)
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews{
8dd5237a27e2e824d18f835dc711573aeb23a173Mark Andrews REQUIRE(key != NULL);
8dd5237a27e2e824d18f835dc711573aeb23a173Mark Andrews
8dd5237a27e2e824d18f835dc711573aeb23a173Mark Andrews return (key->keydata.gssctx);
8dd5237a27e2e824d18f835dc711573aeb23a173Mark Andrews}
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrewsisc_result_t
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrewsdst_key_fromgssapi(dns_name_t *name, gss_ctx_id_t gssctx, isc_mem_t *mctx,
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews dst_key_t **keyp, isc_region_t *intoken)
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews{
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews dst_key_t *key;
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff isc_result_t result;
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews REQUIRE(gssctx != NULL);
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews REQUIRE(keyp != NULL && *keyp == NULL);
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews key = get_key_struct(name, DST_ALG_GSSAPI, 0, DNS_KEYPROTO_DNSSEC,
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews 0, dns_rdataclass_in, 0, mctx);
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff if (key == NULL)
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews return (ISC_R_NOMEMORY);
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews
82d05588933a3c765aa8518fe455d6477d640b99Mark Andrews if (intoken != NULL) {
fd4810861c0c0ccb9aebde94e9d289442b2630dbMark Andrews /*
fd4810861c0c0ccb9aebde94e9d289442b2630dbMark Andrews * Keep the token for use by external ssu rules. They may need
fd4810861c0c0ccb9aebde94e9d289442b2630dbMark Andrews * to examine the PAC in the kerberos ticket.
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews */
fd4810861c0c0ccb9aebde94e9d289442b2630dbMark Andrews RETERR(isc_buffer_allocate(key->mctx, &key->key_tkeytoken,
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews intoken->length));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews RETERR(isc_buffer_copyregion(key->key_tkeytoken, intoken));
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff }
7d8cdd869ed2162a5befda7cc1600136110f54d6Mark Andrews
7d8cdd869ed2162a5befda7cc1600136110f54d6Mark Andrews key->keydata.gssctx = gssctx;
7d8cdd869ed2162a5befda7cc1600136110f54d6Mark Andrews *keyp = key;
d981ca645597116d227a48bf37cc5edc061c854dBob Halley result = ISC_R_SUCCESS;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrewsout:
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff return result;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews}
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrewsisc_result_t
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrewsdst_key_fromlabel(dns_name_t *name, int alg, unsigned int flags,
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews unsigned int protocol, dns_rdataclass_t rdclass,
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff const char *engine, const char *label, const char *pin,
ae70d32b67cf30e06553c01479e71c87b21d984cBob Halley isc_mem_t *mctx, dst_key_t **keyp)
ae70d32b67cf30e06553c01479e71c87b21d984cBob Halley{
19d365e4448f1782611280b020987988b7ac3210Mark Andrews dst_key_t *key;
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff isc_result_t result;
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews REQUIRE(dst_initialized == ISC_TRUE);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews REQUIRE(dns_name_isabsolute(name));
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence REQUIRE(mctx != NULL);
19d365e4448f1782611280b020987988b7ac3210Mark Andrews REQUIRE(keyp != NULL && *keyp == NULL);
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence REQUIRE(label != NULL);
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence
19d365e4448f1782611280b020987988b7ac3210Mark Andrews CHECKALG(alg);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence key = get_key_struct(name, alg, flags, protocol, 0, rdclass, 0, mctx);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence if (key == NULL)
b589e90689c6e87bf9608424ca8d99571c18bc61Mark Andrews return (ISC_R_NOMEMORY);
b589e90689c6e87bf9608424ca8d99571c18bc61Mark Andrews
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff if (key->func->fromlabel == NULL) {
b589e90689c6e87bf9608424ca8d99571c18bc61Mark Andrews dst_key_free(&key);
f8aae502686e2448c48f56697c212a50e2a1cbaeAndreas Gustafsson return (DST_R_UNSUPPORTEDALG);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews }
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews result = key->func->fromlabel(key, engine, label, pin);
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington if (result != ISC_R_SUCCESS) {
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington dst_key_free(&key);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews return (result);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews }
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews result = computeid(key);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews if (result != ISC_R_SUCCESS) {
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews dst_key_free(&key);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews return (result);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews }
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews *keyp = key;
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington return (ISC_R_SUCCESS);
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington}
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrewsisc_result_t
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrewsdst_key_generate(dns_name_t *name, unsigned int alg,
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews unsigned int bits, unsigned int param,
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews unsigned int flags, unsigned int protocol,
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews dns_rdataclass_t rdclass,
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews isc_mem_t *mctx, dst_key_t **keyp)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews{
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (dst_key_generate2(name, alg, bits, param, flags, protocol,
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews rdclass, mctx, keyp, NULL));
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff}
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
7ab0e69f61e61e81d489c95c7ebd981e74e7ef16Andreas Gustafssonisc_result_t
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrewsdst_key_generate2(dns_name_t *name, unsigned int alg,
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews unsigned int bits, unsigned int param,
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews unsigned int flags, unsigned int protocol,
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews dns_rdataclass_t rdclass,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence isc_mem_t *mctx, dst_key_t **keyp,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence void (*callback)(int))
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence{
7ab0e69f61e61e81d489c95c7ebd981e74e7ef16Andreas Gustafsson dst_key_t *key;
7ab0e69f61e61e81d489c95c7ebd981e74e7ef16Andreas Gustafsson isc_result_t ret;
7ab0e69f61e61e81d489c95c7ebd981e74e7ef16Andreas Gustafsson
7ab0e69f61e61e81d489c95c7ebd981e74e7ef16Andreas Gustafsson REQUIRE(dst_initialized == ISC_TRUE);
ae70d32b67cf30e06553c01479e71c87b21d984cBob Halley REQUIRE(dns_name_isabsolute(name));
7ab0e69f61e61e81d489c95c7ebd981e74e7ef16Andreas Gustafsson REQUIRE(mctx != NULL);
7ab0e69f61e61e81d489c95c7ebd981e74e7ef16Andreas Gustafsson REQUIRE(keyp != NULL && *keyp == NULL);
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson CHECKALG(alg);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson key = get_key_struct(name, alg, flags, protocol, bits,
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson rdclass, 0, mctx);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews if (key == NULL)
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews return (ISC_R_NOMEMORY);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews if (bits == 0) { /*%< NULL KEY */
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence key->key_flags |= DNS_KEYTYPE_NOKEY;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence *keyp = key;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence return (ISC_R_SUCCESS);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson }
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson if (key->func->generate == NULL) {
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson dst_key_free(&key);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson return (DST_R_UNSUPPORTEDALG);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson }
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson ret = key->func->generate(key, param, callback);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson if (ret != ISC_R_SUCCESS) {
ae70d32b67cf30e06553c01479e71c87b21d984cBob Halley dst_key_free(&key);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson return (ret);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson }
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff
d981ca645597116d227a48bf37cc5edc061c854dBob Halley ret = computeid(key);
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews if (ret != ISC_R_SUCCESS) {
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews dst_key_free(&key);
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews return (ret);
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff }
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews *keyp = key;
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews return (ISC_R_SUCCESS);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews}
19d365e4448f1782611280b020987988b7ac3210Mark Andrews
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrewsisc_result_t
f1cae4bcb7ee3060d893f5ab3ba55c1820bf3e4aBrian Wellingtondst_key_getnum(const dst_key_t *key, int type, isc_uint32_t *valuep)
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews{
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews REQUIRE(VALID_KEY(key));
19d365e4448f1782611280b020987988b7ac3210Mark Andrews REQUIRE(valuep != NULL);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews REQUIRE(type <= DST_MAX_NUMERIC);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (!key->numset[type])
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (ISC_R_NOTFOUND);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews *valuep = key->nums[type];
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews return (ISC_R_SUCCESS);
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews}
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graffvoid
7d8cdd869ed2162a5befda7cc1600136110f54d6Mark Andrewsdst_key_setnum(dst_key_t *key, int type, isc_uint32_t value)
7d8cdd869ed2162a5befda7cc1600136110f54d6Mark Andrews{
7d8cdd869ed2162a5befda7cc1600136110f54d6Mark Andrews REQUIRE(VALID_KEY(key));
d981ca645597116d227a48bf37cc5edc061c854dBob Halley REQUIRE(type <= DST_MAX_NUMERIC);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews key->nums[type] = value;
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff key->numset[type] = ISC_TRUE;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews}
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrewsvoid
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrewsdst_key_unsetnum(dst_key_t *key, int type)
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff{
94a3bcd132e515b4baa0884ba9dd0f361d2e17bcMark Andrews REQUIRE(VALID_KEY(key));
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff REQUIRE(type <= DST_MAX_NUMERIC);
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews key->numset[type] = ISC_FALSE;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews}
19d365e4448f1782611280b020987988b7ac3210Mark Andrews
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrewsisc_result_t
19d365e4448f1782611280b020987988b7ac3210Mark Andrewsdst_key_gettime(const dst_key_t *key, int type, isc_stdtime_t *timep) {
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews REQUIRE(VALID_KEY(key));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews REQUIRE(timep != NULL);
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews REQUIRE(type <= DST_MAX_TIMES);
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews if (!key->timeset[type])
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews return (ISC_R_NOTFOUND);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews *timep = key->times[type];
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (ISC_R_SUCCESS);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews}
94a3bcd132e515b4baa0884ba9dd0f361d2e17bcMark Andrews
94a3bcd132e515b4baa0884ba9dd0f361d2e17bcMark Andrewsvoid
94a3bcd132e515b4baa0884ba9dd0f361d2e17bcMark Andrewsdst_key_settime(dst_key_t *key, int type, isc_stdtime_t when) {
94a3bcd132e515b4baa0884ba9dd0f361d2e17bcMark Andrews REQUIRE(VALID_KEY(key));
94a3bcd132e515b4baa0884ba9dd0f361d2e17bcMark Andrews REQUIRE(type <= DST_MAX_TIMES);
94a3bcd132e515b4baa0884ba9dd0f361d2e17bcMark Andrews key->times[type] = when;
94a3bcd132e515b4baa0884ba9dd0f361d2e17bcMark Andrews key->timeset[type] = ISC_TRUE;
94a3bcd132e515b4baa0884ba9dd0f361d2e17bcMark Andrews}
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff
d981ca645597116d227a48bf37cc5edc061c854dBob Halleyvoid
d981ca645597116d227a48bf37cc5edc061c854dBob Halleydst_key_unsettime(dst_key_t *key, int type) {
d981ca645597116d227a48bf37cc5edc061c854dBob Halley REQUIRE(VALID_KEY(key));
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff REQUIRE(type <= DST_MAX_TIMES);
d981ca645597116d227a48bf37cc5edc061c854dBob Halley key->timeset[type] = ISC_FALSE;
d981ca645597116d227a48bf37cc5edc061c854dBob Halley}
d981ca645597116d227a48bf37cc5edc061c854dBob Halley
d981ca645597116d227a48bf37cc5edc061c854dBob Halleyisc_result_t
d981ca645597116d227a48bf37cc5edc061c854dBob Halleydst_key_getprivateformat(const dst_key_t *key, int *majorp, int *minorp) {
d981ca645597116d227a48bf37cc5edc061c854dBob Halley REQUIRE(VALID_KEY(key));
d981ca645597116d227a48bf37cc5edc061c854dBob Halley REQUIRE(majorp != NULL);
d981ca645597116d227a48bf37cc5edc061c854dBob Halley REQUIRE(minorp != NULL);
d981ca645597116d227a48bf37cc5edc061c854dBob Halley *majorp = key->fmt_major;
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews *minorp = key->fmt_minor;
d981ca645597116d227a48bf37cc5edc061c854dBob Halley return (ISC_R_SUCCESS);
d981ca645597116d227a48bf37cc5edc061c854dBob Halley}
d981ca645597116d227a48bf37cc5edc061c854dBob Halley
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrewsvoid
d981ca645597116d227a48bf37cc5edc061c854dBob Halleydst_key_setprivateformat(dst_key_t *key, int major, int minor) {
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews REQUIRE(VALID_KEY(key));
d981ca645597116d227a48bf37cc5edc061c854dBob Halley key->fmt_major = major;
d981ca645597116d227a48bf37cc5edc061c854dBob Halley key->fmt_minor = minor;
d981ca645597116d227a48bf37cc5edc061c854dBob Halley}
d981ca645597116d227a48bf37cc5edc061c854dBob Halley
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graffstatic isc_boolean_t
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halleycomparekeys(const dst_key_t *key1, const dst_key_t *key2,
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff isc_boolean_t match_revoked_key,
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley isc_boolean_t (*compare)(const dst_key_t *key1,
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews const dst_key_t *key2))
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley{
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley REQUIRE(dst_initialized == ISC_TRUE);
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley REQUIRE(VALID_KEY(key1));
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley REQUIRE(VALID_KEY(key2));
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley if (key1 == key2)
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley return (ISC_TRUE);
c03bb27f0675a6e60ceea66b451548e8481bc05cMark Andrews
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley if (key1 == NULL || key2 == NULL)
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley return (ISC_FALSE);
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews if (key1->key_alg != key2->key_alg)
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews return (ISC_FALSE);
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews
9916239908343b3eb17f0578de4c3cd6a313d85fMark Andrews if (key1->key_id != key2->key_id) {
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley if (!match_revoked_key)
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley return (ISC_FALSE);
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley if (key1->key_alg == DST_ALG_RSAMD5)
0513f89e68f82f9ec54e7af9c979a7c43babbe31Bob Halley return (ISC_FALSE);
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff if ((key1->key_flags & DNS_KEYFLAG_REVOKE) ==
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff (key2->key_flags & DNS_KEYFLAG_REVOKE))
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff return (ISC_FALSE);
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff if (key1->key_id != key2->key_rid &&
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff key1->key_rid != key2->key_id)
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff return (ISC_FALSE);
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff }
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff if (compare != NULL)
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence return (compare(key1, key2));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson else
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff return (ISC_FALSE);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson}
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson/*
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson * Compares only the public portion of two keys, by converting them
88ba491496daf4463a2c898be8a6c47775a6d048Mark Andrews * both to wire format and comparing the results.
78838d3e0cd62423c23de5503910e01884d2104bBrian Wellington */
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssonstatic isc_boolean_t
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssonpub_compare(const dst_key_t *key1, const dst_key_t *key2) {
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_result_t result;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson unsigned char buf1[DST_KEY_MAXSIZE], buf2[DST_KEY_MAXSIZE];
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_buffer_t b1, b2;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_region_t r1, r2;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_buffer_init(&b1, buf1, sizeof(buf1));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson result = dst_key_todns(key1, &b1);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson if (result != ISC_R_SUCCESS)
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence return (ISC_FALSE);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson /* Zero out flags. */
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson buf1[0] = buf1[1] = 0;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson if ((key1->key_flags & DNS_KEYFLAG_EXTENDED) != 0)
34b394b43e2207e8f8f3703f0402422121455638David Lawrence isc_buffer_subtract(&b1, 2);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff isc_buffer_init(&b2, buf2, sizeof(buf2));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson result = dst_key_todns(key2, &b2);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence if (result != ISC_R_SUCCESS)
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence return (ISC_FALSE);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence /* Zero out flags. */
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson buf2[0] = buf2[1] = 0;
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence if ((key2->key_flags & DNS_KEYFLAG_EXTENDED) != 0)
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_buffer_subtract(&b2, 2);
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_buffer_usedregion(&b1, &r1);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson /* Remove extended flags. */
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson if ((key1->key_flags & DNS_KEYFLAG_EXTENDED) != 0) {
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson memmove(&buf1[4], &buf1[6], r1.length - 6);
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff r1.length -= 2;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson }
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_buffer_usedregion(&b2, &r2);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson /* Remove extended flags. */
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson if ((key2->key_flags & DNS_KEYFLAG_EXTENDED) != 0) {
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff memmove(&buf2[4], &buf2[6], r2.length - 6);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson r2.length -= 2;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson }
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (ISC_TF(isc_region_compare(&r1, &r2) == 0));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson}
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssonisc_boolean_t
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssondst_key_compare(const dst_key_t *key1, const dst_key_t *key2) {
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (comparekeys(key1, key2, ISC_FALSE, key1->func->compare));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson}
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssonisc_boolean_t
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssondst_key_pubcompare(const dst_key_t *key1, const dst_key_t *key2,
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_boolean_t match_revoked_key)
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson{
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (comparekeys(key1, key2, match_revoked_key, pub_compare));
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff}
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graffisc_boolean_t
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graffdst_key_paramcompare(const dst_key_t *key1, const dst_key_t *key2) {
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff REQUIRE(dst_initialized == ISC_TRUE);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence REQUIRE(VALID_KEY(key1));
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington REQUIRE(VALID_KEY(key2));
600cfa2ba4c50017581b6c14e3a688a82ecebbe0David Lawrence
600cfa2ba4c50017581b6c14e3a688a82ecebbe0David Lawrence if (key1 == key2)
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington return (ISC_TRUE);
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff if (key1 == NULL || key2 == NULL)
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff return (ISC_FALSE);
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff if (key1->key_alg == key2->key_alg &&
fc024be774c7cdee938da018aa3994be746e36deDavid Lawrence key1->func->paramcompare != NULL &&
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff key1->func->paramcompare(key1, key2) == ISC_TRUE)
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington return (ISC_TRUE);
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff else
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff return (ISC_FALSE);
6b0ce7d29fac9df84ed34aa2d4634e754aec750dAndreas Gustafsson}
6b0ce7d29fac9df84ed34aa2d4634e754aec750dAndreas Gustafsson
6b0ce7d29fac9df84ed34aa2d4634e754aec750dAndreas Gustafssonvoid
6b0ce7d29fac9df84ed34aa2d4634e754aec750dAndreas Gustafssondst_key_attach(dst_key_t *source, dst_key_t **target) {
6b0ce7d29fac9df84ed34aa2d4634e754aec750dAndreas Gustafsson
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington REQUIRE(dst_initialized == ISC_TRUE);
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington REQUIRE(target != NULL && *target == NULL);
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington REQUIRE(VALID_KEY(source));
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington isc_refcount_increment(&source->refs, NULL);
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington *target = source;
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington}
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellingtonvoid
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellingtondst_key_free(dst_key_t **keyp) {
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington isc_mem_t *mctx;
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington dst_key_t *key;
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff unsigned int refs;
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington REQUIRE(dst_initialized == ISC_TRUE);
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff REQUIRE(keyp != NULL && VALID_KEY(*keyp));
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington key = *keyp;
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff mctx = key->mctx;
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington isc_refcount_decrement(&key->refs, &refs);
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff if (refs != 0)
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff return;
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff isc_refcount_destroy(&key->refs);
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews if (key->keydata.generic != NULL) {
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff INSIST(key->func->destroy != NULL);
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff key->func->destroy(key);
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff }
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews if (key->engine != NULL)
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews isc_mem_free(mctx, key->engine);
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews if (key->label != NULL)
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff isc_mem_free(mctx, key->label);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence dns_name_free(key->key_name, mctx);
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington isc_mem_put(mctx, key->key_name, sizeof(dns_name_t));
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff if (key->key_tkeytoken) {
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff isc_buffer_free(&key->key_tkeytoken);
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff }
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff memset(key, 0, sizeof(dst_key_t));
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff isc_mem_put(mctx, key, sizeof(dst_key_t));
6b0ce7d29fac9df84ed34aa2d4634e754aec750dAndreas Gustafsson *keyp = NULL;
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff}
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graffisc_boolean_t
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graffdst_key_isprivate(const dst_key_t *key) {
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff REQUIRE(VALID_KEY(key));
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff INSIST(key->func->isprivate != NULL);
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff return (key->func->isprivate(key));
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff}
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellingtonisc_result_t
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graffdst_key_buildfilename(const dst_key_t *key, int type,
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff const char *directory, isc_buffer_t *out) {
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews REQUIRE(VALID_KEY(key));
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson REQUIRE(type == DST_TYPE_PRIVATE || type == DST_TYPE_PUBLIC ||
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson type == 0);
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson return (buildfilename(key->key_name, key->key_id, key->key_alg,
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson type, directory, out));
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson}
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafssonisc_result_t
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafssondst_key_sigsize(const dst_key_t *key, unsigned int *n) {
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson REQUIRE(dst_initialized == ISC_TRUE);
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson REQUIRE(VALID_KEY(key));
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson REQUIRE(n != NULL);
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson /* XXXVIX this switch statement is too sparse to gen a jump table. */
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson switch (key->key_alg) {
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson case DST_ALG_RSAMD5:
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson case DST_ALG_RSASHA1:
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson case DST_ALG_NSEC3RSASHA1:
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson case DST_ALG_RSASHA256:
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson case DST_ALG_RSASHA512:
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson *n = (key->key_size + 7) / 8;
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson break;
fa460c223a69449eaac67ddb6abafe74f5e1ff02Michael Graff case DST_ALG_DSA:
79eec6934923f97a61edb8dbe2641ce56dc30085Bob Halley case DST_ALG_NSEC3DSA:
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff *n = DNS_SIG_DSASIGSIZE;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence break;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff case DST_ALG_ECCGOST:
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews *n = DNS_SIG_GOSTSIGSIZE;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff break;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff case DST_ALG_ECDSA256:
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff *n = DNS_SIG_ECDSA256SIZE;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff break;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff case DST_ALG_ECDSA384:
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff *n = DNS_SIG_ECDSA384SIZE;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff break;
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence case DST_ALG_HMACMD5:
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence *n = 16;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff break;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff case DST_ALG_HMACSHA1:
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff *n = ISC_SHA1_DIGESTLENGTH;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff break;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff case DST_ALG_HMACSHA224:
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff *n = ISC_SHA224_DIGESTLENGTH;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff break;
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff case DST_ALG_HMACSHA256:
94a537e6ab3069f8d34e12e5ea722250be2b89c8Michael Graff *n = ISC_SHA256_DIGESTLENGTH;
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews break;
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington case DST_ALG_HMACSHA384:
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington *n = ISC_SHA384_DIGESTLENGTH;
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington break;
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington case DST_ALG_HMACSHA512:
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington *n = ISC_SHA512_DIGESTLENGTH;
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington break;
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington case DST_ALG_GSSAPI:
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington *n = 128; /*%< XXX */
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington break;
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews case DST_ALG_DH:
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews default:
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews return (DST_R_UNSUPPORTEDALG);
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff }
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence return (ISC_R_SUCCESS);
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington}
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff
6324997211a5e2d82528dcde98e8981190a35faeMichael Graffisc_result_t
5cca7753fde4cbfe15d0c0c2cf1fd519f61f2e7fBrian Wellingtondst_key_secretsize(const dst_key_t *key, unsigned int *n) {
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff REQUIRE(dst_initialized == ISC_TRUE);
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff REQUIRE(VALID_KEY(key));
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff REQUIRE(n != NULL);
6324997211a5e2d82528dcde98e8981190a35faeMichael Graff
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews if (key->key_alg == DST_ALG_DH)
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews *n = (key->key_size + 7) / 8;
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson else
8c962eba3d6faebc008806ebb6bb9d08089118e9Andreas Gustafsson return (DST_R_UNSUPPORTEDALG);
8c962eba3d6faebc008806ebb6bb9d08089118e9Andreas Gustafsson return (ISC_R_SUCCESS);
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson}
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson/*%
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson * Set the flags on a key, then recompute the key ID
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson */
8c962eba3d6faebc008806ebb6bb9d08089118e9Andreas Gustafssonisc_result_t
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafssondst_key_setflags(dst_key_t *key, isc_uint32_t flags) {
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson REQUIRE(VALID_KEY(key));
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson key->key_flags = flags;
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson return (computeid(key));
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson}
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafssonvoid
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafssondst_key_format(const dst_key_t *key, char *cp, unsigned int size) {
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson char namestr[DNS_NAME_FORMATSIZE];
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson char algstr[DNS_NAME_FORMATSIZE];
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson dns_name_format(dst_key_name(key), namestr, sizeof(namestr));
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson dns_secalg_format((dns_secalg_t) dst_key_alg(key), algstr,
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson sizeof(algstr));
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson snprintf(cp, size, "%s/%s/%d", namestr, algstr, dst_key_id(key));
d3a86da2e8f09e2c3f55721aae537b9cacc7e537Andreas Gustafsson}
79eec6934923f97a61edb8dbe2641ce56dc30085Bob Halley
79eec6934923f97a61edb8dbe2641ce56dc30085Bob Halleyisc_result_t
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graffdst_key_dump(dst_key_t *key, isc_mem_t *mctx, char **buffer, int *length) {
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington REQUIRE(buffer != NULL && *buffer == NULL);
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington REQUIRE(length != NULL && *length == 0);
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington REQUIRE(VALID_KEY(key));
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews if (key->func->isprivate == NULL)
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews return (ISC_R_NOTIMPLEMENTED);
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff return (key->func->dump(key, mctx, buffer, length));
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrews}
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrewsisc_result_t
8d3e74b1683f714a484bbcf73249e8ee470e36d7Mark Andrewsdst_key_restore(dns_name_t *name, unsigned int alg, unsigned int flags,
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington unsigned int protocol, dns_rdataclass_t rdclass,
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington isc_mem_t *mctx, const char *keystr, dst_key_t **keyp)
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington{
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington isc_result_t result;
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington dst_key_t *key;
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington REQUIRE(dst_initialized == ISC_TRUE);
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington REQUIRE(keyp != NULL && *keyp == NULL);
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington if (alg >= DST_MAX_ALGS || dst_t_func[alg] == NULL)
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence return (DST_R_UNSUPPORTEDALG);
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington
5d83b561ad7eb84885a8ec63dee4c51b335f067aBrian Wellington if (dst_t_func[alg]->restore == NULL)
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff return (ISC_R_NOTIMPLEMENTED);
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson key = get_key_struct(name, alg, flags, protocol, 0, rdclass, 0, mctx);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson if (key == NULL)
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (ISC_R_NOMEMORY);
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence result = (dst_t_func[alg]->restore)(key, keystr);
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews if (result == ISC_R_SUCCESS)
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff *keyp = key;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson else
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence dst_key_free(&key);
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews return (result);
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff}
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson/***
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson *** Static methods
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson ***/
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson/*%
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews * Allocates a key structure and fills in some of the fields.
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff */
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssonstatic dst_key_t *
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssonget_key_struct(dns_name_t *name, unsigned int alg,
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews unsigned int flags, unsigned int protocol,
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews unsigned int bits, dns_rdataclass_t rdclass,
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff dns_ttl_t ttl, isc_mem_t *mctx)
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson{
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dst_key_t *key;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_result_t result;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson int i;
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson key = (dst_key_t *) isc_mem_get(mctx, sizeof(dst_key_t));
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews if (key == NULL)
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff return (NULL);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson memset(key, 0, sizeof(dst_key_t));
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews key->magic = KEY_MAGIC;
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff result = isc_refcount_init(&key->refs, 1);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson if (result != ISC_R_SUCCESS) {
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_mem_put(mctx, key, sizeof(dst_key_t));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (NULL);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson }
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
88ba491496daf4463a2c898be8a6c47775a6d048Mark Andrews key->key_name = isc_mem_get(mctx, sizeof(dns_name_t));
88ba491496daf4463a2c898be8a6c47775a6d048Mark Andrews if (key->key_name == NULL) {
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_refcount_destroy(&key->refs);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_mem_put(mctx, key, sizeof(dst_key_t));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (NULL);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson }
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dns_name_init(key->key_name, NULL);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson result = dns_name_dup(name, mctx, key->key_name);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson if (result != ISC_R_SUCCESS) {
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_refcount_destroy(&key->refs);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_mem_put(mctx, key->key_name, sizeof(dns_name_t));
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_mem_put(mctx, key, sizeof(dst_key_t));
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence return (NULL);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson }
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson key->key_alg = alg;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson key->key_flags = flags;
34b394b43e2207e8f8f3703f0402422121455638David Lawrence key->key_proto = protocol;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson key->mctx = mctx;
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff key->keydata.generic = NULL;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson key->key_size = bits;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson key->key_class = rdclass;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson key->key_ttl = ttl;
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews key->func = dst_t_func[alg];
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence key->fmt_major = 0;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson key->fmt_minor = 0;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson for (i = 0; i < (DST_MAX_TIMES + 1); i++) {
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence key->times[i] = 0;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson key->timeset[i] = ISC_FALSE;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson }
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson return (key);
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson}
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson/*%
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson * Reads a public key from disk
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson */
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssonisc_result_t
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafssondst_key_read_public(const char *filename, int type,
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_mem_t *mctx, dst_key_t **keyp)
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews{
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson u_char rdatabuf[DST_KEY_MAXSIZE];
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_buffer_t b;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dns_fixedname_t name;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_lex_t *lex = NULL;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_token_t token;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_result_t ret;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dns_rdata_t rdata = DNS_RDATA_INIT;
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence unsigned int opt = ISC_LEXOPT_DNSMULTILINE;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dns_rdataclass_t rdclass = dns_rdataclass_in;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_lexspecials_t specials;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson isc_uint32_t ttl = 0;
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews isc_result_t result;
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson dns_rdatatype_t keytype;
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews /*
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews * Open the file and read its formatted contents
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence * File format:
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence * domain.name [ttl] [class] [KEY|DNSKEY] <flags> <protocol> <algorithm> <key>
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence */
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews /* 1500 should be large enough for any key */
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews ret = isc_lex_create(mctx, 1500, &lex);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (ret != ISC_R_SUCCESS)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews goto cleanup;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff memset(specials, 0, sizeof(specials));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews specials['('] = 1;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews specials[')'] = 1;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews specials['"'] = 1;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_lex_setspecials(lex, specials);
fe47f41b13620bfafc4f8cf65d5df24f1e568764Bob Halley isc_lex_setcomments(lex, ISC_LEXCOMMENT_DNSMASTERFILE);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews ret = isc_lex_openfile(lex, filename);
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence if (ret != ISC_R_SUCCESS)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews goto cleanup;
fe47f41b13620bfafc4f8cf65d5df24f1e568764Bob Halley
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#define NEXTTOKEN(lex, opt, token) { \
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews ret = isc_lex_gettoken(lex, opt, token); \
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (ret != ISC_R_SUCCESS) \
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews goto cleanup; \
0e8cf9a887c70f96ac448b06c069d90b830215ccMark Andrews }
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#define BADTOKEN() { \
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff ret = ISC_R_UNEXPECTEDTOKEN; \
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews goto cleanup; \
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews }
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
ca2912424b1d7c348186a325dd2078a37bb8d818Andreas Gustafsson /* Read the domain name */
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews NEXTTOKEN(lex, opt, &token);
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff if (token.type != isc_tokentype_string)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews BADTOKEN();
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews /*
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews * We don't support "@" in .key files.
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews */
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (!strcmp(DST_AS_STR(token), "@"))
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews BADTOKEN();
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews dns_fixedname_init(&name);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_buffer_init(&b, DST_AS_STR(token), strlen(DST_AS_STR(token)));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_buffer_add(&b, strlen(DST_AS_STR(token)));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews ret = dns_name_fromtext(dns_fixedname_name(&name), &b, dns_rootname,
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff 0, NULL);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (ret != ISC_R_SUCCESS)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews goto cleanup;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews /* Read the next word: either TTL, class, or 'KEY' */
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff NEXTTOKEN(lex, opt, &token);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (token.type != isc_tokentype_string)
fe47f41b13620bfafc4f8cf65d5df24f1e568764Bob Halley BADTOKEN();
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff /* If it's a TTL, read the next one */
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews result = dns_ttl_fromtext(&token.value.as_textregion, &ttl);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (result == ISC_R_SUCCESS)
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff NEXTTOKEN(lex, opt, &token);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (token.type != isc_tokentype_string)
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews BADTOKEN();
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews ret = dns_rdataclass_fromtext(&rdclass, &token.value.as_textregion);
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews if (ret == ISC_R_SUCCESS)
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews NEXTTOKEN(lex, opt, &token);
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (token.type != isc_tokentype_string)
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence BADTOKEN();
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews if (strcasecmp(DST_AS_STR(token), "DNSKEY") == 0)
f0ff273b530afa730025e1c5ad311950f7ff4328Mark Andrews keytype = dns_rdatatype_dnskey;
f0ff273b530afa730025e1c5ad311950f7ff4328Mark Andrews else if (strcasecmp(DST_AS_STR(token), "KEY") == 0)
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews keytype = dns_rdatatype_key; /*%< SIG(0), TKEY */
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews else
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff BADTOKEN();
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence if (((type & DST_TYPE_KEY) != 0 && keytype != dns_rdatatype_key) ||
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence ((type & DST_TYPE_KEY) == 0 && keytype != dns_rdatatype_dnskey)) {
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews ret = DST_R_BADKEYTYPE;
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews goto cleanup;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence }
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence isc_buffer_init(&b, rdatabuf, sizeof(rdatabuf));
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews ret = dns_rdata_fromtext(&rdata, rdclass, keytype, lex, NULL,
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews ISC_FALSE, mctx, &b, NULL);
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews if (ret != ISC_R_SUCCESS)
ad493ef9ddb5a3e78e9d99f57abe75552f36a8f4Andreas Gustafsson goto cleanup;
7c0378745269fe49a05904935afc42b85528f53aDavid Lawrence
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews ret = dst_key_fromdns(dns_fixedname_name(&name), rdclass, &b, mctx,
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews keyp);
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews if (ret != ISC_R_SUCCESS)
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews goto cleanup;
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews dst_key_setttl(*keyp, ttl);
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews cleanup:
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews if (lex != NULL)
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews isc_lex_destroy(&lex);
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews return (ret);
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews}
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrewsstatic isc_boolean_t
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrewsissymmetric(const dst_key_t *key) {
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews REQUIRE(dst_initialized == ISC_TRUE);
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews REQUIRE(VALID_KEY(key));
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews /* XXXVIX this switch statement is too sparse to gen a jump table. */
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews switch (key->key_alg) {
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews case DST_ALG_RSAMD5:
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews case DST_ALG_RSASHA1:
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence case DST_ALG_NSEC3RSASHA1:
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff case DST_ALG_RSASHA256:
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews case DST_ALG_RSASHA512:
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews case DST_ALG_DSA:
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews case DST_ALG_NSEC3DSA:
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews case DST_ALG_DH:
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews case DST_ALG_ECCGOST:
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews case DST_ALG_ECDSA256:
7d62ddffbb4d1cc97b8d80b7ee4944554a57523eMark Andrews case DST_ALG_ECDSA384:
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff return (ISC_FALSE);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews case DST_ALG_HMACMD5:
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews case DST_ALG_GSSAPI:
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff return (ISC_TRUE);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews default:
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (ISC_FALSE);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews }
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews}
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence/*%
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews * Write key timing metadata to a file pointer, preceded by 'tag'
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff */
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrewsstatic void
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrewsprinttime(const dst_key_t *key, int type, const char *tag, FILE *stream) {
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff isc_result_t result;
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence#ifdef ISC_PLATFORM_USETHREADS
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence char output[26]; /* Minimum buffer as per ctime_r() specification. */
bfb2a81b65579882a80855c279cedc45aebd62e8Mark Andrews#else
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff const char *output;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#endif
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_stdtime_t when;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews time_t t;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews char utc[sizeof("YYYYMMDDHHSSMM")];
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff isc_buffer_t b;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_region_t r;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews result = dst_key_gettime(key, type, &when);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (result == ISC_R_NOTFOUND)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews /* time_t and isc_stdtime_t might be different sizes */
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews t = when;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#ifdef ISC_PLATFORM_USETHREADS
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#ifdef WIN32
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (ctime_s(output, sizeof(output), &t) != 0)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews goto error;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#else
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (ctime_r(&t, output) == NULL)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews goto error;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#endif
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#else
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence output = ctime(&t);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#endif
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_buffer_init(&b, utc, sizeof(utc));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews result = dns_time32_totext(when, &b);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (result != ISC_R_SUCCESS)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews goto error;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_buffer_usedregion(&b, &r);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews fprintf(stream, "%s: %.*s (%.*s)\n", tag, (int)r.length, r.base,
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews (int)strlen(output) - 1, output);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return;
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence error:
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews fprintf(stream, "%s: (set, unable to display)\n", tag);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews}
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence/*%
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews * Writes a public key to disk in DNS format.
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews */
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrewsstatic isc_result_t
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graffwrite_public_key(const dst_key_t *key, int type, const char *directory) {
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews FILE *fp;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_buffer_t keyb, textb, fileb, classb;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_region_t r;
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff char filename[ISC_DIR_NAMEMAX];
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews unsigned char key_array[DST_KEY_MAXSIZE];
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews char text_array[DST_KEY_MAXTEXTSIZE];
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington char class_array[10];
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington isc_result_t ret;
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington dns_rdata_t rdata = DNS_RDATA_INIT;
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington isc_fsaccess_t access;
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington REQUIRE(VALID_KEY(key));
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington isc_buffer_init(&keyb, key_array, sizeof(key_array));
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington isc_buffer_init(&textb, text_array, sizeof(text_array));
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington isc_buffer_init(&classb, class_array, sizeof(class_array));
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington ret = dst_key_todns(key, &keyb);
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington if (ret != ISC_R_SUCCESS)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (ret);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
26b0f58b6c4d65bc8b131debf40b8c376c2978bfBob Halley isc_buffer_usedregion(&keyb, &r);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews dns_rdata_fromregion(&rdata, key->key_class, dns_rdatatype_dnskey, &r);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews ret = dns_rdata_totext(&rdata, (dns_name_t *) NULL, &textb);
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence if (ret != ISC_R_SUCCESS)
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence return (DST_R_INVALIDPUBLICKEY);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
3d5cad69ec20157912e95cf3b79316dfb0a314f3Mark Andrews ret = dns_rdataclass_totext(key->key_class, &classb);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (ret != ISC_R_SUCCESS)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (DST_R_INVALIDPUBLICKEY);
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff
15330e4fa27c82ac04cc2ce234ec930e4b6b42d3Mark Andrews /*
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews * Make the filename.
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews */
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence isc_buffer_init(&fileb, filename, sizeof(filename));
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews ret = dst_key_buildfilename(key, DST_TYPE_PUBLIC, directory, &fileb);
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff if (ret != ISC_R_SUCCESS)
e4653123ecc6cdbfc0b9eda6e98e44af3b1f9a08Mark Andrews return (ret);
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews /*
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews * Create public key file.
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff */
15330e4fa27c82ac04cc2ce234ec930e4b6b42d3Mark Andrews if ((fp = fopen(filename, "w")) == NULL)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (DST_R_WRITEERROR);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
1c3191528684f3dd93ebb122298c2f8ebfc6d397Mark Andrews if (issymmetric(key)) {
34b394b43e2207e8f8f3703f0402422121455638David Lawrence access = 0;
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence isc_fsaccess_add(ISC_FSACCESS_OWNER,
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews ISC_FSACCESS_READ | ISC_FSACCESS_WRITE,
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff &access);
7c0378745269fe49a05904935afc42b85528f53aDavid Lawrence (void)isc_fsaccess_set(filename, access);
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff }
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews /* Write key information in comments */
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff if ((type & DST_TYPE_KEY) == 0) {
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson fprintf(fp, "; This is a %s%s-signing key, keyid %d, for ",
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson (key->key_flags & DNS_KEYFLAG_REVOKE) != 0 ?
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson "revoked " :
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson "",
34b394b43e2207e8f8f3703f0402422121455638David Lawrence (key->key_flags & DNS_KEYFLAG_KSK) != 0 ?
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence "key" :
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson "zone",
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff key->key_id);
7c0378745269fe49a05904935afc42b85528f53aDavid Lawrence ret = dns_name_print(key->key_name, fp);
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff if (ret != ISC_R_SUCCESS) {
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson fclose(fp);
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson return (ret);
5466ce3f279d9fa83ce826bcdc9482bc591152aeAndreas Gustafsson }
5466ce3f279d9fa83ce826bcdc9482bc591152aeAndreas Gustafsson fputc('\n', fp);
5466ce3f279d9fa83ce826bcdc9482bc591152aeAndreas Gustafsson
5466ce3f279d9fa83ce826bcdc9482bc591152aeAndreas Gustafsson printtime(key, DST_TIME_CREATED, "; Created", fp);
5466ce3f279d9fa83ce826bcdc9482bc591152aeAndreas Gustafsson printtime(key, DST_TIME_PUBLISH, "; Publish", fp);
5466ce3f279d9fa83ce826bcdc9482bc591152aeAndreas Gustafsson printtime(key, DST_TIME_ACTIVATE, "; Activate", fp);
5466ce3f279d9fa83ce826bcdc9482bc591152aeAndreas Gustafsson printtime(key, DST_TIME_REVOKE, "; Revoke", fp);
15330e4fa27c82ac04cc2ce234ec930e4b6b42d3Mark Andrews printtime(key, DST_TIME_INACTIVE, "; Inactive", fp);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews printtime(key, DST_TIME_DELETE, "; Delete", fp);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews }
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence
035504dbd8ca5949e8380b860873b3385a4e61e5Mark Andrews /* Now print the actual key */
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews ret = dns_name_print(key->key_name, fp);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews fprintf(fp, " ");
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews if (key->key_ttl != 0)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews fprintf(fp, "%d ", key->key_ttl);
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews isc_buffer_usedregion(&classb, &r);
15330e4fa27c82ac04cc2ce234ec930e4b6b42d3Mark Andrews if ((unsigned) fwrite(r.base, 1, r.length, fp) != r.length)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews ret = DST_R_WRITEERROR;
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence
035504dbd8ca5949e8380b860873b3385a4e61e5Mark Andrews if ((type & DST_TYPE_KEY) != 0)
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews fprintf(fp, " KEY ");
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews else
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews fprintf(fp, " DNSKEY ");
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson isc_buffer_usedregion(&textb, &r);
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson if ((unsigned) fwrite(r.base, 1, r.length, fp) != r.length)
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence ret = DST_R_WRITEERROR;
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson fputc('\n', fp);
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson fflush(fp);
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson if (ferror(fp))
5a219d878f0bd786e86da2c9b92999260dda3f8dAndreas Gustafsson ret = DST_R_WRITEERROR;
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff fclose(fp);
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews return (ret);
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews}
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence
78838d3e0cd62423c23de5503910e01884d2104bBrian Wellingtonstatic isc_result_t
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graffbuildfilename(dns_name_t *name, dns_keytag_t id,
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews unsigned int alg, unsigned int type,
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews const char *directory, isc_buffer_t *out)
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff{
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews const char *suffix = "";
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews unsigned int len;
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews isc_result_t result;
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews REQUIRE(out != NULL);
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews if ((type & DST_TYPE_PRIVATE) != 0)
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews suffix = ".private";
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews else if (type == DST_TYPE_PUBLIC)
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews suffix = ".key";
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews if (directory != NULL) {
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews if (isc_buffer_availablelength(out) < strlen(directory))
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews return (ISC_R_NOSPACE);
904294c0c952227f7778fd0ba2ccea08c097b872Mark Andrews isc_buffer_putstr(out, directory);
904294c0c952227f7778fd0ba2ccea08c097b872Mark Andrews if (strlen(directory) > 0U &&
44a966dff66061ac3f266c6b451a70733eb78e82Mark Andrews directory[strlen(directory) - 1] != '/')
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews isc_buffer_putstr(out, "/");
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews }
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews if (isc_buffer_availablelength(out) < 1)
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews return (ISC_R_NOSPACE);
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence isc_buffer_putstr(out, "K");
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence result = dns_name_tofilenametext(name, ISC_FALSE, out);
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence if (result != ISC_R_SUCCESS)
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence return (result);
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence len = 1 + 3 + 1 + 5 + strlen(suffix) + 1;
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews if (isc_buffer_availablelength(out) < len)
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence return (ISC_R_NOSPACE);
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence sprintf((char *) isc_buffer_used(out), "+%03d+%05d%s", alg, id,
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews suffix);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews isc_buffer_add(out, len);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews return (ISC_R_SUCCESS);
ffe74cc719aa0f10c38fbc1f2f3ea7db0960cb8fMark Andrews}
8a17d1e7cdba9fdcf71fb2f821a954a251204105Mark Andrews
8a17d1e7cdba9fdcf71fb2f821a954a251204105Mark Andrewsstatic isc_result_t
8a17d1e7cdba9fdcf71fb2f821a954a251204105Mark Andrewscomputeid(dst_key_t *key) {
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence isc_buffer_t dnsbuf;
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence unsigned char dns_array[DST_KEY_MAXSIZE];
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence isc_region_t r;
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence isc_result_t ret;
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence isc_buffer_init(&dnsbuf, dns_array, sizeof(dns_array));
8a17d1e7cdba9fdcf71fb2f821a954a251204105Mark Andrews ret = dst_key_todns(key, &dnsbuf);
8a17d1e7cdba9fdcf71fb2f821a954a251204105Mark Andrews if (ret != ISC_R_SUCCESS)
8a17d1e7cdba9fdcf71fb2f821a954a251204105Mark Andrews return (ret);
8a17d1e7cdba9fdcf71fb2f821a954a251204105Mark Andrews
8a17d1e7cdba9fdcf71fb2f821a954a251204105Mark Andrews isc_buffer_usedregion(&dnsbuf, &r);
8a17d1e7cdba9fdcf71fb2f821a954a251204105Mark Andrews key->key_id = dst_region_computeid(&r, key->key_alg);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews key->key_rid = dst_region_computerid(&r, key->key_alg);
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence return (ISC_R_SUCCESS);
47b26abe77184f9bedc68e36bdad03332cf67570David Lawrence}
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrewsstatic isc_result_t
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrewsfrombuffer(dns_name_t *name, unsigned int alg, unsigned int flags,
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews unsigned int protocol, dns_rdataclass_t rdclass,
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews isc_buffer_t *source, isc_mem_t *mctx, dst_key_t **keyp)
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews{
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews dst_key_t *key;
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews isc_result_t ret;
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews REQUIRE(dns_name_isabsolute(name));
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews REQUIRE(source != NULL);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews REQUIRE(mctx != NULL);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews REQUIRE(keyp != NULL && *keyp == NULL);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews key = get_key_struct(name, alg, flags, protocol, 0, rdclass, 0, mctx);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews if (key == NULL)
15330e4fa27c82ac04cc2ce234ec930e4b6b42d3Mark Andrews return (ISC_R_NOMEMORY);
15330e4fa27c82ac04cc2ce234ec930e4b6b42d3Mark Andrews
15330e4fa27c82ac04cc2ce234ec930e4b6b42d3Mark Andrews if (isc_buffer_remaininglength(source) > 0) {
15330e4fa27c82ac04cc2ce234ec930e4b6b42d3Mark Andrews ret = algorithm_status(alg);
15330e4fa27c82ac04cc2ce234ec930e4b6b42d3Mark Andrews if (ret != ISC_R_SUCCESS) {
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews dst_key_free(&key);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (ret);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews }
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews if (key->func->fromdns == NULL) {
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews dst_key_free(&key);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (DST_R_UNSUPPORTEDALG);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews }
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews ret = key->func->fromdns(key, source);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews if (ret != ISC_R_SUCCESS) {
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff dst_key_free(&key);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (ret);
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff }
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff }
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence *keyp = key;
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence return (ISC_R_SUCCESS);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence}
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graffstatic isc_result_t
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrewsalgorithm_status(unsigned int alg) {
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews REQUIRE(dst_initialized == ISC_TRUE);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews if (dst_algorithm_supported(alg))
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (ISC_R_SUCCESS);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews#ifndef OPENSSL
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews if (alg == DST_ALG_RSAMD5 || alg == DST_ALG_RSASHA1 ||
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews alg == DST_ALG_DSA || alg == DST_ALG_DH ||
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews alg == DST_ALG_HMACMD5 || alg == DST_ALG_NSEC3DSA ||
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews alg == DST_ALG_NSEC3RSASHA1 ||
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews alg == DST_ALG_RSASHA256 || alg == DST_ALG_RSASHA512 ||
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews alg == DST_ALG_ECCGOST ||
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews alg == DST_ALG_ECDSA256 || alg == DST_ALG_ECDSA384)
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (DST_R_NOCRYPTO);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews#endif
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (DST_R_UNSUPPORTEDALG);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews}
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrewsstatic isc_result_t
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrewsaddsuffix(char *filename, int len, const char *odirname,
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews const char *ofilename, const char *suffix)
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews{
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews int olen = strlen(ofilename);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews int n;
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews if (olen > 1 && ofilename[olen - 1] == '.')
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews olen -= 1;
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews else if (olen > 8 && strcmp(ofilename + olen - 8, ".private") == 0)
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews olen -= 8;
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews else if (olen > 4 && strcmp(ofilename + olen - 4, ".key") == 0)
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews olen -= 4;
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews if (odirname == NULL)
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews n = snprintf(filename, len, "%.*s%s", olen, ofilename, suffix);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence else
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence n = snprintf(filename, len, "%s/%.*s%s",
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence odirname, olen, ofilename, suffix);
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff if (n < 0)
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (ISC_R_FAILURE);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews if (n >= len)
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (ISC_R_NOSPACE);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (ISC_R_SUCCESS);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews}
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrewsisc_result_t
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrewsdst__entropy_getdata(void *buf, unsigned int len, isc_boolean_t pseudo) {
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews#ifdef BIND9
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews unsigned int flags = dst_entropy_flags;
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews if (len == 0)
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (ISC_R_SUCCESS);
6e49e91bd08778d7eae45a2229dcf41ed97cc636David Lawrence if (pseudo)
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews flags &= ~ISC_ENTROPY_GOODONLY;
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff else
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews flags |= ISC_ENTROPY_BLOCKING;
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (isc_entropy_getdata(dst_entropy_pool, buf, len, NULL, flags));
419590499823ce15b5d2ad4fe71eaf04bd5a86c0Michael Graff#else
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews UNUSED(buf);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews UNUSED(len);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence UNUSED(pseudo);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence return (ISC_R_NOTIMPLEMENTED);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence#endif
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence}
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrenceunsigned int
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencedst__entropy_status(void) {
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence#ifdef BIND9
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence#ifdef GSSAPI
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence unsigned int flags = dst_entropy_flags;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence isc_result_t ret;
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews unsigned char buf[32];
3ddd814a97de1d152ba0913c592d6e6dc83d38a6Michael Graff static isc_boolean_t first = ISC_TRUE;
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
df8c9ee4819c97089664ccc035eb2aa7569034fdDavid Lawrence if (first) {
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews /* Someone believes RAND_status() initializes the PRNG */
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews flags &= ~ISC_ENTROPY_GOODONLY;
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews ret = isc_entropy_getdata(dst_entropy_pool, buf,
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews sizeof(buf), NULL, flags);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews INSIST(ret == ISC_R_SUCCESS);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews isc_entropy_putdata(dst_entropy_pool, buf,
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews sizeof(buf), 2 * sizeof(buf));
add4043305ca411202ed9cf1929a4179016515ceBrian Wellington first = ISC_FALSE;
add4043305ca411202ed9cf1929a4179016515ceBrian Wellington }
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews#endif
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (isc_entropy_status(dst_entropy_pool));
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews#else
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews return (0);
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews#endif
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews}
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrews
3a4ec3da9fa14511cbc3660f75817cfacb3f4d1eMark Andrewsisc_buffer_t *
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrencedst_key_tkeytoken(const dst_key_t *key) {
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence REQUIRE(VALID_KEY(key));
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence return (key->key_tkeytoken);
add4043305ca411202ed9cf1929a4179016515ceBrian Wellington}
add4043305ca411202ed9cf1929a4179016515ceBrian Wellington