dst.h 29.9 KB
Newer Older
David Lawrence's avatar
David Lawrence committed
1
/*
2
 * Copyright (C) Internet Systems Consortium, Inc. ("ISC")
3
 *
4 5
 * This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
6
 * file, you can obtain one at https://mozilla.org/MPL/2.0/.
7 8 9
 *
 * See the COPYRIGHT file distributed with this work for additional
 * information regarding copyright ownership.
David Lawrence's avatar
David Lawrence committed
10 11
 */

12 13 14
#ifndef DST_DST_H
#define DST_DST_H 1

15
/*! \file dst/dst.h */
16

17
#include <inttypes.h>
18
#include <stdbool.h>
19

20
#include <isc/lang.h>
21
#include <isc/stdtime.h>
22

23 24
#include <dns/ds.h>
#include <dns/dsdigest.h>
25
#include <dns/log.h>
26 27
#include <dns/name.h>
#include <dns/secalg.h>
28
#include <dns/types.h>
29

30 31
#include <dst/gssapi.h>

32 33 34 35 36 37
ISC_LANG_BEGINDECLS

/***
 *** Types
 ***/

38
/*%
39 40 41 42 43
 * The dst_key structure is opaque.  Applications should use the accessor
 * functions provided to retrieve key attributes.  If an application needs
 * to set attributes, new accessor functions will be written.
 */

44 45
typedef struct dst_key	   dst_key_t;
typedef struct dst_context dst_context_t;
46

47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78
/*%
 * Key states for the DNSSEC records related to a key: DNSKEY, RRSIG (ksk),
 * RRSIG (zsk), and DS.
 *
 * DST_KEY_STATE_HIDDEN:      Records of this type are not published in zone.
 *                            This may be because the key parts were never
 *                            introduced in the zone, or because the key has
 *                            retired and has no records of this type left in
 *                            the zone.
 * DST_KEY_STATE_RUMOURED:    Records of this type are published in zone, but
 *                            not long enough to ensure all resolvers know
 *                            about it.
 * DST_KEY_STATE_OMNIPRESENT: Records of this type are published in zone long
 *                            enough so that all resolvers that know about
 *                            these records, no longer have outdated data.
 * DST_KEY_STATE_UNRETENTIVE: Records of this type have been removed from the
 *                            zone, but there may be resolvers that still have
 *                            have predecessor records cached.  Note that RRSIG
 *                            records in this state may actually still be in the
 *                            zone because they are reused, but retired RRSIG
 *                            records will never be refreshed: A successor key
 *                            is used to create signatures.
 * DST_KEY_STATE_NA:          The state is not applicable for this record type.
 */
typedef enum dst_key_state {
	DST_KEY_STATE_HIDDEN = 0,
	DST_KEY_STATE_RUMOURED = 1,
	DST_KEY_STATE_OMNIPRESENT = 2,
	DST_KEY_STATE_UNRETENTIVE = 3,
	DST_KEY_STATE_NA = 4
} dst_key_state_t;

79
/* DST algorithm codes */
Evan Hunt's avatar
Evan Hunt committed
80 81 82 83 84 85 86 87
#define DST_ALG_UNKNOWN	     0
#define DST_ALG_RSA	     1 /* Used for parsing RSASHA1, RSASHA256 and RSASHA512 */
#define DST_ALG_RSAMD5	     1
#define DST_ALG_DH	     2
#define DST_ALG_DSA	     3
#define DST_ALG_ECC	     4
#define DST_ALG_RSASHA1	     5
#define DST_ALG_NSEC3DSA     6
88
#define DST_ALG_NSEC3RSASHA1 7
Evan Hunt's avatar
Evan Hunt committed
89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105
#define DST_ALG_RSASHA256    8
#define DST_ALG_RSASHA512    10
#define DST_ALG_ECCGOST	     12
#define DST_ALG_ECDSA256     13
#define DST_ALG_ECDSA384     14
#define DST_ALG_ED25519	     15
#define DST_ALG_ED448	     16
#define DST_ALG_HMACMD5	     157
#define DST_ALG_GSSAPI	     160
#define DST_ALG_HMACSHA1     161 /* XXXMPA */
#define DST_ALG_HMACSHA224   162 /* XXXMPA */
#define DST_ALG_HMACSHA256   163 /* XXXMPA */
#define DST_ALG_HMACSHA384   164 /* XXXMPA */
#define DST_ALG_HMACSHA512   165 /* XXXMPA */
#define DST_ALG_INDIRECT     252
#define DST_ALG_PRIVATE	     254
#define DST_MAX_ALGS	     256
106

107
/*% A buffer of this size is large enough to hold any key */
108
#define DST_KEY_MAXSIZE 1280
109

110
/*%
111 112 113
 * A buffer of this size is large enough to hold the textual representation
 * of any key
 */
114
#define DST_KEY_MAXTEXTSIZE 2048
115

116
/*% 'Type' for dst_read_key() */
Evan Hunt's avatar
Evan Hunt committed
117
#define DST_TYPE_KEY	 0x1000000 /* KEY key */
118
#define DST_TYPE_PRIVATE 0x2000000
Evan Hunt's avatar
Evan Hunt committed
119 120
#define DST_TYPE_PUBLIC	 0x4000000
#define DST_TYPE_STATE	 0x8000000
121

122
/* Key timing metadata definitions */
Evan Hunt's avatar
Evan Hunt committed
123 124 125 126 127 128 129
#define DST_TIME_CREATED     0
#define DST_TIME_PUBLISH     1
#define DST_TIME_ACTIVATE    2
#define DST_TIME_REVOKE	     3
#define DST_TIME_INACTIVE    4
#define DST_TIME_DELETE	     5
#define DST_TIME_DSPUBLISH   6
130
#define DST_TIME_SYNCPUBLISH 7
Evan Hunt's avatar
Evan Hunt committed
131 132 133 134 135
#define DST_TIME_SYNCDELETE  8
#define DST_TIME_DNSKEY	     9
#define DST_TIME_ZRRSIG	     10
#define DST_TIME_KRRSIG	     11
#define DST_TIME_DS	     12
136 137
#define DST_TIME_DSDELETE    13
#define DST_MAX_TIMES	     13
138 139

/* Numeric metadata definitions */
140
#define DST_NUM_PREDECESSOR 0
Evan Hunt's avatar
Evan Hunt committed
141 142 143 144 145
#define DST_NUM_SUCCESSOR   1
#define DST_NUM_MAXTTL	    2
#define DST_NUM_ROLLPERIOD  3
#define DST_NUM_LIFETIME    4
#define DST_MAX_NUMERIC	    4
146 147

/* Boolean metadata definitions */
Evan Hunt's avatar
Evan Hunt committed
148 149
#define DST_BOOL_KSK	0
#define DST_BOOL_ZSK	1
150
#define DST_MAX_BOOLEAN 1
151

152
/* Key state metadata definitions */
Evan Hunt's avatar
Evan Hunt committed
153 154 155 156 157
#define DST_KEY_DNSKEY	  0
#define DST_KEY_ZRRSIG	  1
#define DST_KEY_KRRSIG	  2
#define DST_KEY_DS	  3
#define DST_KEY_GOAL	  4
158
#define DST_MAX_KEYSTATES 4
159

160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178
/*
 * Current format version number of the private key parser.
 *
 * When parsing a key file with the same major number but a higher minor
 * number, the key parser will ignore any fields it does not recognize.
 * Thus, DST_MINOR_VERSION should be incremented whenever new
 * fields are added to the private key file (such as new metadata).
 *
 * When rewriting these keys, those fields will be dropped, and the
 * format version set back to the current one..
 *
 * When a key is seen with a higher major number, the key parser will
 * reject it as invalid.  Thus, DST_MAJOR_VERSION should be incremented
 * and DST_MINOR_VERSION set to zero whenever there is a format change
 * which is not backward compatible to previous versions of the dst_key
 * parser, such as change in the syntax of an existing field, the removal
 * of a currently mandatory field, or a new field added which would
 * alter the functioning of the key if it were absent.
 */
179 180
#define DST_MAJOR_VERSION 1
#define DST_MINOR_VERSION 3
181

182 183 184
/***
 *** Functions
 ***/
Francis Dupont's avatar
Francis Dupont committed
185
isc_result_t
186
dst_lib_init(isc_mem_t *mctx, const char *engine);
187
/*%<
Brian Wellington's avatar
Brian Wellington committed
188
 * Initializes the DST subsystem.
Brian Wellington's avatar
Brian Wellington committed
189 190
 *
 * Requires:
191
 * \li 	"mctx" is a valid memory context
Brian Wellington's avatar
Brian Wellington committed
192 193
 *
 * Returns:
194 195
 * \li	ISC_R_SUCCESS
 * \li	ISC_R_NOMEMORY
Francis Dupont's avatar
Francis Dupont committed
196
 * \li	DST_R_NOENGINE
Brian Wellington's avatar
Brian Wellington committed
197 198
 *
 * Ensures:
199
 * \li	DST is properly initialized.
Brian Wellington's avatar
Brian Wellington committed
200 201 202 203
 */

void
dst_lib_destroy(void);
204
/*%<
Brian Wellington's avatar
Brian Wellington committed
205 206 207
 * Releases all resources allocated by DST.
 */

208
bool
Brian Wellington's avatar
Brian Wellington committed
209
dst_algorithm_supported(unsigned int alg);
210
/*%<
211 212 213
 * Checks that a given algorithm is supported by DST.
 *
 * Returns:
214 215
 * \li	true
 * \li	false
216 217
 */

218
bool
219 220 221 222 223
dst_ds_digest_supported(unsigned int digest_type);
/*%<
 * Checks that a given digest algorithm is supported by DST.
 *
 * Returns:
224 225
 * \li	true
 * \li	false
226 227
 */

228
isc_result_t
229 230
dst_context_create(dst_key_t *key, isc_mem_t *mctx, isc_logcategory_t *category,
		   bool useforsigning, int maxbits, dst_context_t **dctxp);
231
/*%<
232
 * Creates a context to be used for a sign or verify operation.
233 234
 *
 * Requires:
235 236 237
 * \li	"key" is a valid key.
 * \li	"mctx" is a valid memory context.
 * \li	dctxp != NULL && *dctxp == NULL
238 239
 *
 * Returns:
240 241
 * \li	ISC_R_SUCCESS
 * \li	ISC_R_NOMEMORY
242 243
 *
 * Ensures:
244
 * \li	*dctxp will contain a usable context.
245 246 247 248
 */

void
dst_context_destroy(dst_context_t **dctxp);
249
/*%<
250 251 252
 * Destroys all memory associated with a context.
 *
 * Requires:
253
 * \li	*dctxp != NULL && *dctxp == NULL
254 255
 *
 * Ensures:
256
 * \li	*dctxp == NULL
257 258 259 260
 */

isc_result_t
dst_context_adddata(dst_context_t *dctx, const isc_region_t *data);
261
/*%<
262 263
 * Incrementally adds data to the context to be used in a sign or verify
 * operation.
264 265
 *
 * Requires:
266 267
 * \li	"dctx" is a valid context
 * \li	"data" is a valid region
268 269
 *
 * Returns:
270 271 272
 * \li	ISC_R_SUCCESS
 * \li	DST_R_SIGNFAILURE
 * \li	all other errors indicate failure
273 274 275 276
 */

isc_result_t
dst_context_sign(dst_context_t *dctx, isc_buffer_t *sig);
277
/*%<
278 279 280
 * Computes a signature using the data and key stored in the context.
 *
 * Requires:
281 282
 * \li	"dctx" is a valid context.
 * \li	"sig" is a valid buffer.
283
 *
284
 * Returns:
285 286 287
 * \li	ISC_R_SUCCESS
 * \li	DST_R_VERIFYFAILURE
 * \li	all other errors indicate failure
288
 *
289
 * Ensures:
290
 * \li	"sig" will contain the signature
291 292
 */

293
isc_result_t
294
dst_context_verify(dst_context_t *dctx, isc_region_t *sig);
295 296 297 298

isc_result_t
dst_context_verify2(dst_context_t *dctx, unsigned int maxbits,
		    isc_region_t *sig);
299
/*%<
300
 * Verifies the signature using the data and key stored in the context.
301
 *
302 303 304
 * 'maxbits' specifies the maximum number of bits permitted in the RSA
 * exponent.
 *
305
 * Requires:
306 307
 * \li	"dctx" is a valid context.
 * \li	"sig" is a valid region.
308
 *
309
 * Returns:
310 311
 * \li	ISC_R_SUCCESS
 * \li	all other errors indicate failure
312
 *
313
 * Ensures:
314
 * \li	"sig" will contain the signature
315 316
 */

317
isc_result_t
Brian Wellington's avatar
Brian Wellington committed
318 319
dst_key_computesecret(const dst_key_t *pub, const dst_key_t *priv,
		      isc_buffer_t *secret);
320
/*%<
321
 * Computes a shared secret from two (Diffie-Hellman) keys.
322 323
 *
 * Requires:
324 325 326
 * \li	"pub" is a valid key that can be used to derive a shared secret
 * \li	"priv" is a valid private key that can be used to derive a shared secret
 * \li	"secret" is a valid buffer
327
 *
328
 * Returns:
329 330
 * \li	ISC_R_SUCCESS
 * \li	any other result indicates failure
331
 *
332
 * Ensures:
333
 * \li	If successful, secret will contain the derived shared secret.
334 335
 */

336 337
isc_result_t
dst_key_getfilename(dns_name_t *name, dns_keytag_t id, unsigned int alg,
338 339
		    int type, const char *directory, isc_mem_t *mctx,
		    isc_buffer_t *buf);
340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358
/*%<
 * Generates a key filename for the name, algorithm, and
 * id, and places it in the buffer 'buf'. If directory is NULL, the
 * current directory is assumed.
 *
 * Requires:
 * \li	"name" is a valid absolute dns name.
 * \li	"id" is a valid key tag identifier.
 * \li	"alg" is a supported key algorithm.
 * \li	"type" is DST_TYPE_PUBLIC, DST_TYPE_PRIVATE, or the bitwise union.
 *		  DST_TYPE_KEY look for a KEY record otherwise DNSKEY
 * \li	"mctx" is a valid memory context.
 * \li	"buf" is not NULL.
 *
 * Returns:
 * \li	ISC_R_SUCCESS
 * \li	any other result indicates failure
 */

359
isc_result_t
Brian Wellington's avatar
Brian Wellington committed
360
dst_key_fromfile(dns_name_t *name, dns_keytag_t id, unsigned int alg, int type,
Brian Wellington's avatar
Brian Wellington committed
361
		 const char *directory, isc_mem_t *mctx, dst_key_t **keyp);
362
/*%<
363
 * Reads a key from permanent storage.  The key can either be a public or
364 365 366
 * private key, or a key state. It specified by name, algorithm, and id.  If
 * a private key or key state is specified, the public key must also be
 * present.  If directory is NULL, the current directory is assumed.
Brian Wellington's avatar
Brian Wellington committed
367
 *
368
 * Requires:
369 370 371
 * \li	"name" is a valid absolute dns name.
 * \li	"id" is a valid key tag identifier.
 * \li	"alg" is a supported key algorithm.
372 373 374
 * \li	"type" is DST_TYPE_PUBLIC, DST_TYPE_PRIVATE or the bitwise union.
 *		  DST_TYPE_KEY look for a KEY record otherwise DNSKEY.
 *		  DST_TYPE_STATE to also read the key state.
375 376
 * \li	"mctx" is a valid memory context.
 * \li	"keyp" is not NULL and "*keyp" is NULL.
377
 *
378
 * Returns:
379 380
 * \li	ISC_R_SUCCESS
 * \li	any other result indicates failure
381
 *
382
 * Ensures:
383
 * \li	If successful, *keyp will contain a valid key.
384 385
 */

386
isc_result_t
387 388
dst_key_fromnamedfile(const char *filename, const char *dirname, int type,
		      isc_mem_t *mctx, dst_key_t **keyp);
389
/*%<
Brian Wellington's avatar
Brian Wellington committed
390
 * Reads a key from permanent storage.  The key can either be a public or
391
 * private key, or a key state. It is specified by filename.  If a private key
392
 * or key state is specified, the public key must also be present.
Brian Wellington's avatar
Brian Wellington committed
393
 *
394 395 396 397
 * If 'dirname' is not NULL, and 'filename' is a relative path,
 * then the file is looked up relative to the given directory.
 * If 'filename' is an absolute path, 'dirname' is ignored.
 *
Brian Wellington's avatar
Brian Wellington committed
398
 * Requires:
399
 * \li	"filename" is not NULL
400 401 402
 * \li	"type" is DST_TYPE_PUBLIC, DST_TYPE_PRIVATE, or the bitwise union.
 *		  DST_TYPE_KEY look for a KEY record otherwise DNSKEY.
 *		  DST_TYPE_STATE to also read the key state.
403 404
 * \li	"mctx" is a valid memory context
 * \li	"keyp" is not NULL and "*keyp" is NULL.
Brian Wellington's avatar
Brian Wellington committed
405 406
 *
 * Returns:
407 408
 * \li	ISC_R_SUCCESS
 * \li	any other result indicates failure
Brian Wellington's avatar
Brian Wellington committed
409 410
 *
 * Ensures:
411
 * \li	If successful, *keyp will contain a valid key.
Brian Wellington's avatar
Brian Wellington committed
412 413
 */

414
isc_result_t
415 416
dst_key_read_public(const char *filename, int type, isc_mem_t *mctx,
		    dst_key_t **keyp);
417
/*%<
418 419 420
 * Reads a public key from permanent storage.  The key must be a public key.
 *
 * Requires:
421 422 423
 * \li	"filename" is not NULL.
 * \li	"type" is DST_TYPE_KEY look for a KEY record otherwise DNSKEY.
 * \li	"mctx" is a valid memory context.
424
 * \li	"keyp" is not NULL and "*keyp" is NULL.
425 426
 *
 * Returns:
427 428 429 430
 * \li	ISC_R_SUCCESS
 * \li	DST_R_BADKEYTYPE if the key type is not the expected one
 * \li	ISC_R_UNEXPECTEDTOKEN if the file can not be parsed as a public key
 * \li	any other result indicates failure
431 432
 *
 * Ensures:
433
 * \li	If successful, *keyp will contain a valid key.
434 435
 */

436
isc_result_t
437
dst_key_read_state(const char *filename, isc_mem_t *mctx, dst_key_t **keyp);
438 439 440 441 442 443 444 445 446 447 448 449 450 451
/*%<
 * Reads a key state from permanent storage.
 *
 * Requires:
 * \li	"filename" is not NULL.
 * \li	"mctx" is a valid memory context.
 * \li	"keyp" is not NULL and "*keyp" is NULL.
 *
 * Returns:
 * \li	ISC_R_SUCCESS
 * \li	ISC_R_UNEXPECTEDTOKEN if the file can not be parsed as a public key
 * \li	any other result indicates failure
 */

Brian Wellington's avatar
Brian Wellington committed
452
isc_result_t
Brian Wellington's avatar
Brian Wellington committed
453
dst_key_tofile(const dst_key_t *key, int type, const char *directory);
454
/*%<
455 456
 * Writes a key to permanent storage.  The key can either be a public or
 * private key.  Public keys are written in DNS format and private keys
Brian Wellington's avatar
Brian Wellington committed
457 458
 * are written as a set of base64 encoded values.  If directory is NULL,
 * the current directory is assumed.
459 460
 *
 * Requires:
461 462
 * \li	"key" is a valid key.
 * \li	"type" is DST_TYPE_PUBLIC, DST_TYPE_PRIVATE, or the bitwise union
463 464
 *
 * Returns:
465 466
 * \li	ISC_R_SUCCESS
 * \li	any other result indicates failure
467 468
 */

469
isc_result_t
470
dst_key_fromdns(const dns_name_t *name, dns_rdataclass_t rdclass,
Brian Wellington's avatar
Brian Wellington committed
471
		isc_buffer_t *source, isc_mem_t *mctx, dst_key_t **keyp);
472
/*%<
473
 * Converts a DNS KEY record into a DST key.
474 475
 *
 * Requires:
476 477 478 479
 * \li	"name" is a valid absolute dns name.
 * \li	"source" is a valid buffer.  There must be at least 4 bytes available.
 * \li	"mctx" is a valid memory context.
 * \li	"keyp" is not NULL and "*keyp" is NULL.
480
 *
481
 * Returns:
482 483
 * \li	ISC_R_SUCCESS
 * \li	any other result indicates failure
484
 *
485
 * Ensures:
486
 * \li	If successful, *keyp will contain a valid key, and the consumed
487 488 489
 *	pointer in data will be advanced.
 */

490 491
isc_result_t
dst_key_todns(const dst_key_t *key, isc_buffer_t *target);
492
/*%<
493
 * Converts a DST key into a DNS KEY record.
494 495
 *
 * Requires:
496 497
 * \li	"key" is a valid key.
 * \li	"target" is a valid buffer.  There must be at least 4 bytes unused.
498
 *
499
 * Returns:
500 501
 * \li	ISC_R_SUCCESS
 * \li	any other result indicates failure
502
 *
503
 * Ensures:
504
 * \li	If successful, the used pointer in 'target' is advanced by at least 4.
505 506
 */

507
isc_result_t
508 509
dst_key_frombuffer(const dns_name_t *name, unsigned int alg, unsigned int flags,
		   unsigned int protocol, dns_rdataclass_t rdclass,
510
		   isc_buffer_t *source, isc_mem_t *mctx, dst_key_t **keyp);
511
/*%<
512
 * Converts a buffer containing DNS KEY RDATA into a DST key.
513 514
 *
 * Requires:
515 516 517 518 519
 *\li	"name" is a valid absolute dns name.
 *\li	"alg" is a supported key algorithm.
 *\li	"source" is a valid buffer.
 *\li	"mctx" is a valid memory context.
 *\li	"keyp" is not NULL and "*keyp" is NULL.
520
 *
521
 * Returns:
522 523
 *\li 	ISC_R_SUCCESS
 * \li	any other result indicates failure
524
 *
525
 * Ensures:
526
 *\li	If successful, *keyp will contain a valid key, and the consumed
527 528 529
 *	pointer in source will be advanced.
 */

530 531
isc_result_t
dst_key_tobuffer(const dst_key_t *key, isc_buffer_t *target);
532
/*%<
533
 * Converts a DST key into DNS KEY RDATA format.
534 535
 *
 * Requires:
536 537
 *\li	"key" is a valid key.
 *\li	"target" is a valid buffer.
538
 *
539
 * Returns:
540 541
 *\li 	ISC_R_SUCCESS
 * \li	any other result indicates failure
542
 *
543
 * Ensures:
544
 *\li	If successful, the used pointer in 'target' is advanced.
545 546
 */

547 548
isc_result_t
dst_key_privatefrombuffer(dst_key_t *key, isc_buffer_t *buffer);
549
/*%<
550 551 552 553 554
 * Converts a public key into a private key, reading the private key
 * information from the buffer.  The buffer should contain the same data
 * as the .private key file would.
 *
 * Requires:
555 556
 *\li	"key" is a valid public key.
 *\li	"buffer" is not NULL.
557 558
 *
 * Returns:
559 560
 *\li 	ISC_R_SUCCESS
 * \li	any other result indicates failure
561 562
 *
 * Ensures:
563
 *\li	If successful, key will contain a valid private key.
564 565
 */

566
dns_gss_ctx_id_t
567 568 569 570 571 572 573 574 575 576 577
dst_key_getgssctx(const dst_key_t *key);
/*%<
 * Returns the opaque key data.
 * Be cautions when using this value unless you know what you are doing.
 *
 * Requires:
 *\li	"key" is not NULL.
 *
 * Returns:
 *\li	gssctx key data, possibly NULL.
 */
578

579
isc_result_t
580 581
dst_key_fromgssapi(const dns_name_t *name, dns_gss_ctx_id_t gssctx,
		   isc_mem_t *mctx, dst_key_t **keyp, isc_region_t *intoken);
582
/*%<
583 584 585
 * Converts a GSSAPI opaque context id into a DST key.
 *
 * Requires:
586
 *\li	"name" is a valid absolute dns name.
587
 *\li	"gssctx" is a GSSAPI context id.
588 589
 *\li	"mctx" is a valid memory context.
 *\li	"keyp" is not NULL and "*keyp" is NULL.
590 591
 *
 * Returns:
592 593
 *\li 	ISC_R_SUCCESS
 * \li	any other result indicates failure
594 595
 *
 * Ensures:
596
 *\li	If successful, *keyp will contain a valid key and be responsible for
597 598 599
 *	the context id.
 */

600 601
#ifdef DST_KEY_INTERNAL
isc_result_t
602
dst_key_buildinternal(const dns_name_t *name, unsigned int alg,
603 604 605
		      unsigned int bits, unsigned int flags,
		      unsigned int protocol, dns_rdataclass_t rdclass,
		      void *data, isc_mem_t *mctx, dst_key_t **keyp);
606
#endif /* ifdef DST_KEY_INTERNAL */
607

Francis Dupont's avatar
Francis Dupont committed
608
isc_result_t
609
dst_key_fromlabel(const dns_name_t *name, int alg, unsigned int flags,
Automatic Updater's avatar
Automatic Updater committed
610 611 612
		  unsigned int protocol, dns_rdataclass_t rdclass,
		  const char *engine, const char *label, const char *pin,
		  isc_mem_t *mctx, dst_key_t **keyp);
Francis Dupont's avatar
Francis Dupont committed
613

614
isc_result_t
615 616 617
dst_key_generate(const dns_name_t *name, unsigned int alg, unsigned int bits,
		 unsigned int param, unsigned int flags, unsigned int protocol,
		 dns_rdataclass_t rdclass, isc_mem_t *mctx, dst_key_t **keyp,
618
		 void (*callback)(int));
619

620
/*%<
621 622
 * Generate a DST key (or keypair) with the supplied parameters.  The
 * interpretation of the "param" field depends on the algorithm:
623
 * \code
624 625 626 627 628 629 630 631
 * 	RSA:	exponent
 * 		0	use exponent 3
 * 		!0	use Fermat4 (2^16 + 1)
 * 	DH:	generator
 * 		0	default - use well known prime if bits == 768 or 1024,
 * 			otherwise use 2 as the generator.
 * 		!0	use this value as the generator.
 * 	DSA:	unused
632 633 634
 * 	HMACMD5: entropy
 *		0	default - require good entropy
 *		!0	lack of good entropy is ok
635
 *\endcode
636 637
 *
 * Requires:
638 639
 *\li	"name" is a valid absolute dns name.
 *\li	"keyp" is not NULL and "*keyp" is NULL.
640
 *
641
 * Returns:
642 643
 *\li 	ISC_R_SUCCESS
 * \li	any other result indicates failure
644
 *
645
 * Ensures:
646
 *\li	If successful, *keyp will contain a valid key.
647 648
 */

649
bool
650
dst_key_compare(const dst_key_t *key1, const dst_key_t *key2);
651
/*%<
652 653 654 655
 * Compares two DST keys.  Returns true if they match, false otherwise.
 *
 * Keys ARE NOT considered to match if one of them is the revoked version
 * of the other.
656 657
 *
 * Requires:
658 659
 *\li	"key1" is a valid key.
 *\li	"key2" is a valid key.
660 661
 *
 * Returns:
662 663
 *\li 	true
 * \li	false
664 665
 */

666
bool
667
dst_key_pubcompare(const dst_key_t *key1, const dst_key_t *key2,
668
		   bool match_revoked_key);
669 670 671 672 673 674 675 676 677 678 679 680 681 682
/*%<
 * Compares only the public portions of two DST keys.  Returns true
 * if they match, false otherwise.  This allows us, for example, to
 * determine whether a public key found in a zone matches up with a
 * key pair found on disk.
 *
 * If match_revoked_key is TRUE, then keys ARE considered to match if one
 * of them is the revoked version of the other. Otherwise, they are not.
 *
 * Requires:
 *\li	"key1" is a valid key.
 *\li	"key2" is a valid key.
 *
 * Returns:
683 684
 *\li 	true
 * \li	false
685
 */
686

687
bool
688
dst_key_paramcompare(const dst_key_t *key1, const dst_key_t *key2);
689
/*%<
690 691
 * Compares the parameters of two DST keys.  This is used to determine if
 * two (Diffie-Hellman) keys can be used to derive a shared secret.
692 693
 *
 * Requires:
694 695
 *\li	"key1" is a valid key.
 *\li	"key2" is a valid key.
696 697
 *
 * Returns:
698 699
 *\li 	true
 * \li	false
700 701
 */

702 703 704 705 706 707 708 709 710 711
void
dst_key_attach(dst_key_t *source, dst_key_t **target);
/*
 * Attach to a existing key increasing the reference count.
 *
 * Requires:
 *\li 'source' to be a valid key.
 *\li 'target' to be non-NULL and '*target' to be NULL.
 */

712
void
713
dst_key_free(dst_key_t **keyp);
714
/*%<
715 716
 * Decrement the key's reference counter and, when it reaches zero,
 * release all memory associated with the key.
717 718
 *
 * Requires:
719
 *\li	"keyp" is not NULL and "*keyp" is a valid key.
720
 *\li	reference counter greater than zero.
721 722
 *
 * Ensures:
723 724
 *\li	All memory associated with "*keyp" will be freed.
 *\li	*keyp == NULL
725 726
 */

727
/*%<
728
 * Accessor functions to obtain key fields.
729 730
 *
 * Require:
731
 *\li	"key" is a valid key.
732
 */
733
dns_name_t *
734 735
dst_key_name(const dst_key_t *key);

736
unsigned int
737 738
dst_key_size(const dst_key_t *key);

739
unsigned int
740 741
dst_key_proto(const dst_key_t *key);

742
unsigned int
743 744
dst_key_alg(const dst_key_t *key);

745
uint32_t
746 747
dst_key_flags(const dst_key_t *key);

748
dns_keytag_t
749 750
dst_key_id(const dst_key_t *key);

751 752 753
dns_keytag_t
dst_key_rid(const dst_key_t *key);

Brian Wellington's avatar
Brian Wellington committed
754 755 756
dns_rdataclass_t
dst_key_class(const dst_key_t *key);

757
bool
758 759
dst_key_isprivate(const dst_key_t *key);

760
bool
761 762
dst_key_iszonekey(const dst_key_t *key);

763
bool
Brian Wellington's avatar
Brian Wellington committed
764 765
dst_key_isnullkey(const dst_key_t *key);

766
isc_result_t
767 768
dst_key_buildfilename(const dst_key_t *key, int type, const char *directory,
		      isc_buffer_t *out);
769
/*%<
770
 * Generates the filename used by dst to store the specified key.
Brian Wellington's avatar
Brian Wellington committed
771
 * If directory is NULL, the current directory is assumed.
772 773
 *
 * Requires:
774 775 776
 *\li	"key" is a valid key
 *\li	"type" is either DST_TYPE_PUBLIC, DST_TYPE_PRIVATE, or 0 for no suffix.
 *\li	"out" is a valid buffer
777 778
 *
 * Ensures:
779
 *\li	the file name will be written to "out", and the used pointer will
780 781 782
 *		be advanced.
 */

783
isc_result_t
Brian Wellington's avatar
Brian Wellington committed
784
dst_key_sigsize(const dst_key_t *key, unsigned int *n);
785
/*%<
786
 * Computes the size of a signature generated by the given key.
787 788
 *
 * Requires:
789 790
 *\li	"key" is a valid key.
 *\li	"n" is not NULL
791 792
 *
 * Returns:
793 794
 *\li	#ISC_R_SUCCESS
 *\li	DST_R_UNSUPPORTEDALG
795 796
 *
 * Ensures:
797
 *\li	"n" stores the size of a generated signature
798 799
 */

800
isc_result_t
Brian Wellington's avatar
Brian Wellington committed
801
dst_key_secretsize(const dst_key_t *key, unsigned int *n);
802
/*%<
803
 * Computes the size of a shared secret generated by the given key.
804 805
 *
 * Requires:
806 807
 *\li	"key" is a valid key.
 *\li	"n" is not NULL
808 809
 *
 * Returns:
810 811
 *\li	#ISC_R_SUCCESS
 *\li	DST_R_UNSUPPORTEDALG
812 813
 *
 * Ensures:
814
 *\li	"n" stores the size of a generated shared secret
815 816
 */

817
uint16_t
Ondřej Surý's avatar
Ondřej Surý committed
818
dst_region_computeid(const isc_region_t *source);
819
uint16_t
Ondřej Surý's avatar
Ondřej Surý committed
820
dst_region_computerid(const isc_region_t *source);
821
/*%<
822
 * Computes the (revoked) key id of the key stored in the provided
Ondřej Surý's avatar
Ondřej Surý committed
823
 * region.
824 825
 *
 * Requires:
826
 *\li	"source" contains a valid, non-NULL region.
827 828
 *
 * Returns:
829
 *\li 	the key id
830 831
 */

832
uint16_t
833
dst_key_getbits(const dst_key_t *key);
834
/*%<
835 836 837 838 839 840 841
 * Get the number of digest bits required (0 == MAX).
 *