1/*
2 *
3 * keys.h
4 *
5 * priv key definitions
6 *
7 * a Net::DNS like library for C
8 *
9 * (c) NLnet Labs, 2005-2006
10 *
11 * See the file LICENSE for the license
12 */
13
14/**
15 * \file
16 *
17 * Addendum to \ref dnssec.h, this module contains key and algorithm definitions and functions.
18 */
19
20
21#ifndef LDNS_KEYS_H
22#define LDNS_KEYS_H
23
24#include <ldns/common.h>
25#if LDNS_BUILD_CONFIG_HAVE_SSL
26#include <openssl/ssl.h>
27#endif /* LDNS_BUILD_CONFIG_HAVE_SSL */
28#include <ldns/util.h>
29#include <errno.h>
30
31#ifdef __cplusplus
32extern "C" {
33#endif
34
35extern ldns_lookup_table ldns_signing_algorithms[];
36
37#define LDNS_KEY_ZONE_KEY 0x0100   /* rfc 4034 */
38#define LDNS_KEY_SEP_KEY 0x0001    /* rfc 4034 */
39#define LDNS_KEY_REVOKE_KEY 0x0080 /* rfc 5011 */
40
41/**
42 * Algorithms used in dns
43 */
44enum ldns_enum_algorithm
45{
46        LDNS_RSAMD5             = 1,   /* RFC 4034,4035 */
47        LDNS_DH                 = 2,
48        LDNS_DSA                = 3,
49        LDNS_ECC                = 4,
50        LDNS_RSASHA1            = 5,
51        LDNS_DSA_NSEC3          = 6,
52        LDNS_RSASHA1_NSEC3      = 7,
53        LDNS_RSASHA256          = 8,   /* RFC 5702 */
54        LDNS_RSASHA512          = 10,  /* RFC 5702 */
55        LDNS_ECC_GOST           = 12,  /* RFC 5933 */
56        LDNS_ECDSAP256SHA256    = 13,  /* RFC 6605 */
57        LDNS_ECDSAP384SHA384    = 14,  /* RFC 6605 */
58#ifdef USE_ED25519
59	/* this ifdef is internal to ldns, because we do not want to export
60	 * the symbol.  Users can define it if they want access,
61	 * the feature is not fully implemented at this time and openssl
62	 * does not support it fully either (also for ED448). */
63	LDNS_ED25519		= 15,  /* draft-ietf-curdle-dnskey-ed25519 */
64#endif
65#ifdef USE_ED448
66	LDNS_ED448		= 16,  /* draft-ietf-curdle-dnskey-ed448 */
67#endif
68        LDNS_INDIRECT           = 252,
69        LDNS_PRIVATEDNS         = 253,
70        LDNS_PRIVATEOID         = 254
71};
72typedef enum ldns_enum_algorithm ldns_algorithm;
73
74/**
75 * Hashing algorithms used in the DS record
76 */
77enum ldns_enum_hash
78{
79        LDNS_SHA1               = 1,  /* RFC 4034 */
80        LDNS_SHA256             = 2,  /* RFC 4509 */
81        LDNS_HASH_GOST          = 3,  /* RFC 5933 */
82        LDNS_SHA384             = 4   /* RFC 6605 */
83};
84typedef enum ldns_enum_hash ldns_hash;
85
86/**
87 * Algorithms used in dns for signing
88 */
89enum ldns_enum_signing_algorithm
90{
91	LDNS_SIGN_RSAMD5	 = LDNS_RSAMD5,
92	LDNS_SIGN_RSASHA1	 = LDNS_RSASHA1,
93	LDNS_SIGN_DSA		 = LDNS_DSA,
94	LDNS_SIGN_RSASHA1_NSEC3  = LDNS_RSASHA1_NSEC3,
95	LDNS_SIGN_RSASHA256	 = LDNS_RSASHA256,
96	LDNS_SIGN_RSASHA512	 = LDNS_RSASHA512,
97	LDNS_SIGN_DSA_NSEC3	 = LDNS_DSA_NSEC3,
98	LDNS_SIGN_ECC_GOST       = LDNS_ECC_GOST,
99        LDNS_SIGN_ECDSAP256SHA256 = LDNS_ECDSAP256SHA256,
100        LDNS_SIGN_ECDSAP384SHA384 = LDNS_ECDSAP384SHA384,
101#ifdef USE_ED25519
102	LDNS_SIGN_ED25519	 = LDNS_ED25519,
103#endif
104#ifdef USE_ED448
105	LDNS_SIGN_ED448		 = LDNS_ED448,
106#endif
107	LDNS_SIGN_HMACMD5	 = 157,	/* not official! This type is for TSIG, not DNSSEC */
108	LDNS_SIGN_HMACSHA1	 = 158,	/* not official! This type is for TSIG, not DNSSEC */
109	LDNS_SIGN_HMACSHA256 = 159,  /* ditto */
110	LDNS_SIGN_HMACSHA224 = 162,  /* ditto */
111	LDNS_SIGN_HMACSHA384 = 164,  /* ditto */
112	LDNS_SIGN_HMACSHA512 = 165  /* ditto */
113};
114typedef enum ldns_enum_signing_algorithm ldns_signing_algorithm;
115
116/**
117 * General key structure, can contain all types of keys that
118 * are used in DNSSEC. Mostly used to store private keys, since
119 * public keys can also be stored in a \ref ldns_rr with type
120 * \ref LDNS_RR_TYPE_DNSKEY.
121 *
122 * This structure can also store some variables that influence the
123 * signatures generated by signing with this key, for instance the
124 * inception date.
125 */
126struct ldns_struct_key {
127	ldns_signing_algorithm _alg;
128	/** Whether to use this key when signing */
129	bool _use;
130	/** Storage pointers for the types of keys supported */
131	/* TODO remove unions? */
132	struct {
133#if LDNS_BUILD_CONFIG_HAVE_SSL
134#ifndef S_SPLINT_S
135		/* The key can be an OpenSSL EVP Key
136		 */
137		EVP_PKEY *key;
138#endif
139#endif /* LDNS_BUILD_CONFIG_HAVE_SSL */
140		/**
141		 * The key can be an HMAC key
142		 */
143		struct {
144			unsigned char *key;
145			size_t size;
146		} hmac;
147		/** the key structure can also just point to some external
148		 *  key data
149		 */
150		void *external_key;
151	} _key;
152	/** Depending on the key we can have extra data */
153	union {
154                /** Some values that influence generated signatures */
155		struct {
156			/** The TTL of the rrset that is currently signed */
157			uint32_t orig_ttl;
158			/** The inception date of signatures made with this key. */
159			uint32_t inception;
160			/** The expiration date of signatures made with this key. */
161			uint32_t expiration;
162			/** The keytag of this key. */
163			uint16_t keytag;
164			/** The dnssec key flags as specified in RFC4035, like ZSK and KSK */
165			uint16_t flags;
166		}  dnssec;
167	} _extra;
168	/** Owner name of the key */
169	ldns_rdf *_pubkey_owner;
170};
171typedef struct ldns_struct_key ldns_key;
172
173/**
174 * Same as rr_list, but now for keys
175 */
176struct ldns_struct_key_list
177{
178	size_t _key_count;
179	ldns_key **_keys;
180};
181typedef struct ldns_struct_key_list ldns_key_list;
182
183
184/**
185 * Creates a new empty key list
186 * \return a new ldns_key_list structure pointer
187 */
188ldns_key_list *ldns_key_list_new(void);
189
190/**
191 * Creates a new empty key structure
192 * \return a new ldns_key * structure
193 */
194ldns_key *ldns_key_new(void);
195
196/**
197 * Creates a new key based on the algorithm
198 *
199 * \param[in] a The algorithm to use
200 * \param[in] size the number of bytes for the keysize
201 * \return a new ldns_key structure with the key
202 */
203ldns_key *ldns_key_new_frm_algorithm(ldns_signing_algorithm a, uint16_t size);
204
205/**
206 * Creates a new priv key based on the
207 * contents of the file pointed by fp.
208 *
209 * The file should be in Private-key-format v1.x.
210 *
211 * \param[out] k the new ldns_key structure
212 * \param[in] fp the file pointer to use
213 * \return an error or LDNS_STATUS_OK
214 */
215ldns_status ldns_key_new_frm_fp(ldns_key **k, FILE *fp);
216
217/**
218 * Creates a new private key based on the
219 * contents of the file pointed by fp
220 *
221 * The file should be in Private-key-format v1.x.
222 *
223 * \param[out] k the new ldns_key structure
224 * \param[in] fp the file pointer to use
225 * \param[in] line_nr pointer to an integer containing the current line number (for debugging purposes)
226 * \return an error or LDNS_STATUS_OK
227 */
228ldns_status ldns_key_new_frm_fp_l(ldns_key **k, FILE *fp, int *line_nr);
229
230#if LDNS_BUILD_CONFIG_HAVE_SSL
231/**
232 * Read the key with the given id from the given engine and store it
233 * in the given ldns_key structure. The algorithm type is set
234 */
235ldns_status ldns_key_new_frm_engine(ldns_key **key, ENGINE *e, char *key_id, ldns_algorithm);
236
237
238/**
239 * frm_fp helper function. This function parses the
240 * remainder of the (RSA) priv. key file generated from bind9
241 * \param[in] fp the file to parse
242 * \return NULL on failure otherwise a RSA structure
243 */
244RSA *ldns_key_new_frm_fp_rsa(FILE *fp);
245#endif /* LDNS_BUILD_CONFIG_HAVE_SSL */
246
247#if LDNS_BUILD_CONFIG_HAVE_SSL
248/**
249 * frm_fp helper function. This function parses the
250 * remainder of the (RSA) priv. key file generated from bind9
251 * \param[in] fp the file to parse
252 * \param[in] line_nr pointer to an integer containing the current line number (for debugging purposes)
253 * \return NULL on failure otherwise a RSA structure
254 */
255RSA *ldns_key_new_frm_fp_rsa_l(FILE *fp, int *line_nr);
256#endif /* LDNS_BUILD_CONFIG_HAVE_SSL */
257
258#if LDNS_BUILD_CONFIG_HAVE_SSL
259/**
260 * frm_fp helper function. This function parses the
261 * remainder of the (DSA) priv. key file
262 * \param[in] fp the file to parse
263 * \return NULL on failure otherwise a RSA structure
264 */
265DSA *ldns_key_new_frm_fp_dsa(FILE *fp);
266#endif /* LDNS_BUILD_CONFIG_HAVE_SSL */
267
268#if LDNS_BUILD_CONFIG_HAVE_SSL
269/**
270 * frm_fp helper function. This function parses the
271 * remainder of the (DSA) priv. key file
272 * \param[in] fp the file to parse
273 * \param[in] line_nr pointer to an integer containing the current line number (for debugging purposes)
274 * \return NULL on failure otherwise a RSA structure
275 */
276DSA *ldns_key_new_frm_fp_dsa_l(FILE *fp, int *line_nr);
277#endif /* LDNS_BUILD_CONFIG_HAVE_SSL */
278
279#if LDNS_BUILD_CONFIG_HAVE_SSL
280/**
281 * frm_fp helper function. This function parses the
282 * remainder of the (HMAC-MD5) key file
283 * This function allocated a buffer that needs to be freed
284 * \param[in] fp the file to parse
285 * \param[out] hmac_size the number of bits in the resulting buffer
286 * \return NULL on failure otherwise a newly allocated char buffer
287 */
288unsigned char *ldns_key_new_frm_fp_hmac(FILE *fp, size_t *hmac_size);
289#endif
290
291#if LDNS_BUILD_CONFIG_HAVE_SSL
292/**
293 * frm_fp helper function. This function parses the
294 * remainder of the (HMAC-MD5) key file
295 * This function allocated a buffer that needs to be freed
296 * \param[in] fp the file to parse
297 * \param[in] line_nr pointer to an integer containing the current line number (for error reporting purposes)
298 * \param[out] hmac_size the number of bits in the resulting buffer
299 * \return NULL on failure otherwise a newly allocated char buffer
300 */
301unsigned char *ldns_key_new_frm_fp_hmac_l(FILE *fp, int *line_nr, size_t *hmac_size);
302#endif /* LDNS_BUILD_CONFIG_HAVE_SSL */
303
304/* acces write functions */
305/**
306 * Set the key's algorithm
307 * \param[in] k the key
308 * \param[in] l the algorithm
309 */
310void ldns_key_set_algorithm(ldns_key *k, ldns_signing_algorithm l);
311#if LDNS_BUILD_CONFIG_HAVE_SSL
312/**
313 * Set the key's evp key
314 * \param[in] k the key
315 * \param[in] e the evp key
316 */
317void ldns_key_set_evp_key(ldns_key *k, EVP_PKEY *e);
318
319/**
320 * Set the key's rsa data.
321 * The rsa data should be freed by the user.
322 * \param[in] k the key
323 * \param[in] r the rsa data
324 */
325void ldns_key_set_rsa_key(ldns_key *k, RSA *r);
326
327/**
328 * Set the key's dsa data
329 * The dsa data should be freed by the user.
330 * \param[in] k the key
331 * \param[in] d the dsa data
332 */
333void ldns_key_set_dsa_key(ldns_key *k, DSA *d);
334
335/**
336 * Assign the key's rsa data
337 * The rsa data will be freed automatically when the key is freed.
338 * \param[in] k the key
339 * \param[in] r the rsa data
340 */
341void ldns_key_assign_rsa_key(ldns_key *k, RSA *r);
342
343/**
344 * Assign the key's dsa data
345 * The dsa data will be freed automatically when the key is freed.
346 * \param[in] k the key
347 * \param[in] d the dsa data
348 */
349void ldns_key_assign_dsa_key(ldns_key *k, DSA *d);
350
351/**
352 * Get the PKEY id for GOST, loads GOST into openssl as a side effect.
353 * Only available if GOST is compiled into the library and openssl.
354 * \return the gost id for EVP_CTX creation.
355 */
356int ldns_key_EVP_load_gost_id(void);
357
358/** Release the engine reference held for the GOST engine. */
359void ldns_key_EVP_unload_gost(void);
360#endif /* LDNS_BUILD_CONFIG_HAVE_SSL */
361
362/**
363 * Set the key's hmac data
364 * \param[in] k the key
365 * \param[in] hmac the raw key data
366 */
367void ldns_key_set_hmac_key(ldns_key *k, unsigned char *hmac);
368
369/**
370 * Set the key id data. This is used if the key points to
371 * some externally stored key data
372 *
373 * Only the pointer is set, the data there is not copied,
374 * and must be freed manually; ldns_key_deep_free() does
375 * *not* free this data
376 * \param[in] key the key
377 * \param[in] external_key key id data
378 */
379void ldns_key_set_external_key(ldns_key *key, void *external_key);
380
381/**
382 * Set the key's hmac size
383 * \param[in] k the key
384 * \param[in] hmac_size the size of the hmac data
385 */
386void ldns_key_set_hmac_size(ldns_key *k, size_t hmac_size);
387/**
388 * Set the key's original ttl
389 * \param[in] k the key
390 * \param[in] t the ttl
391 */
392void ldns_key_set_origttl(ldns_key *k, uint32_t t);
393/**
394 * Set the key's inception date (seconds after epoch)
395 * \param[in] k the key
396 * \param[in] i the inception
397 */
398void ldns_key_set_inception(ldns_key *k, uint32_t i);
399/**
400 * Set the key's expiration date (seconds after epoch)
401 * \param[in] k the key
402 * \param[in] e the expiration
403 */
404void ldns_key_set_expiration(ldns_key *k, uint32_t e);
405/**
406 * Set the key's pubkey owner
407 * \param[in] k the key
408 * \param[in] r the owner
409 */
410void ldns_key_set_pubkey_owner(ldns_key *k, ldns_rdf *r);
411/**
412 * Set the key's key tag
413 * \param[in] k the key
414 * \param[in] tag the keytag
415 */
416void ldns_key_set_keytag(ldns_key *k, uint16_t tag);
417/**
418 * Set the key's flags
419 * \param[in] k the key
420 * \param[in] flags the flags
421 */
422void ldns_key_set_flags(ldns_key *k, uint16_t flags);
423/**
424 * Set the keylist's key count to count
425 * \param[in] key the key
426 * \param[in] count the cuont
427 */
428void ldns_key_list_set_key_count(ldns_key_list *key, size_t count);
429
430/**
431 * pushes a key to a keylist
432 * \param[in] key_list the key_list to push to
433 * \param[in] key the key to push
434 * \return false on error, otherwise true
435 */
436bool ldns_key_list_push_key(ldns_key_list *key_list, ldns_key *key);
437
438/**
439 * returns the number of keys in the key list
440 * \param[in] key_list the key_list
441 * \return the numbers of keys in the list
442 */
443size_t ldns_key_list_key_count(const ldns_key_list *key_list);
444
445/**
446 * returns a pointer to the key in the list at the given position
447 * \param[in] key the key
448 * \param[in] nr the position in the list
449 * \return the key
450 */
451ldns_key *ldns_key_list_key(const ldns_key_list *key, size_t nr);
452
453#if LDNS_BUILD_CONFIG_HAVE_SSL
454/**
455 * returns the (openssl) RSA struct contained in the key
456 * \param[in] k the key to look in
457 * \return the RSA * structure in the key
458 */
459RSA *ldns_key_rsa_key(const ldns_key *k);
460/**
461 * returns the (openssl) EVP struct contained in the key
462 * \param[in] k the key to look in
463 * \return the RSA * structure in the key
464 */
465EVP_PKEY *ldns_key_evp_key(const ldns_key *k);
466#endif /* LDNS_BUILD_CONFIG_HAVE_SSL */
467
468/**
469 * returns the (openssl) DSA struct contained in the key
470 */
471#if LDNS_BUILD_CONFIG_HAVE_SSL
472DSA *ldns_key_dsa_key(const ldns_key *k);
473#endif /* LDNS_BUILD_CONFIG_HAVE_SSL */
474
475/**
476 * return the signing alg of the key
477 * \param[in] k the key
478 * \return the algorithm
479 */
480ldns_signing_algorithm ldns_key_algorithm(const ldns_key *k);
481/**
482 * set the use flag
483 * \param[in] k the key
484 * \param[in] v the boolean value to set the _use field to
485 */
486void ldns_key_set_use(ldns_key *k, bool v);
487/**
488 * return the use flag
489 * \param[in] k the key
490 * \return the boolean value of the _use field
491 */
492bool ldns_key_use(const ldns_key *k);
493/**
494 * return the hmac key data
495 * \param[in] k the key
496 * \return the hmac key data
497 */
498unsigned char *ldns_key_hmac_key(const ldns_key *k);
499/**
500 * return the key id key data
501 * \param[in] k the key
502 * \return the key id data
503 */
504void *ldns_key_external_key(const ldns_key *k);
505/**
506 * return the hmac key size
507 * \param[in] k the key
508 * \return the hmac key size
509 */
510size_t ldns_key_hmac_size(const ldns_key *k);
511/**
512 * return the original ttl of the key
513 * \param[in] k the key
514 * \return the original ttl
515 */
516uint32_t ldns_key_origttl(const ldns_key *k);
517/**
518 * return the key's inception date
519 * \param[in] k the key
520 * \return the inception date
521 */
522uint32_t ldns_key_inception(const ldns_key *k);
523/**
524 * return the key's expiration date
525 * \param[in] k the key
526 * \return the experiration date
527 */
528uint32_t ldns_key_expiration(const ldns_key *k);
529/**
530 * return the keytag
531 * \param[in] k the key
532 * \return the keytag
533 */
534uint16_t ldns_key_keytag(const ldns_key *k);
535/**
536 * return the public key's owner
537 * \param[in] k the key
538 * \return the owner
539 */
540ldns_rdf *ldns_key_pubkey_owner(const ldns_key *k);
541/**
542 * Set the 'use' flag for all keys in the list
543 * \param[in] keys The key_list
544 * \param[in] v The value to set the use flags to
545 */
546void
547ldns_key_list_set_use(ldns_key_list *keys, bool v);
548
549/**
550 * return the flag of the key
551 * \param[in] k the key
552 * \return the flag
553 */
554uint16_t ldns_key_flags(const ldns_key *k);
555
556/**
557 * pops the last rr from a keylist
558 * \param[in] key_list the rr_list to pop from
559 * \return NULL if nothing to pop. Otherwise the popped RR
560 */
561ldns_key *ldns_key_list_pop_key(ldns_key_list *key_list);
562
563/**
564 * converts a ldns_key to a public key rr
565 * If the key data exists at an external point, the corresponding
566 * rdata field must still be added with ldns_rr_rdf_push() to the
567 * result rr of this function
568 *
569 * \param[in] k the ldns_key to convert
570 * \return ldns_rr representation of the key
571 */
572ldns_rr *ldns_key2rr(const ldns_key *k);
573
574/**
575 * print a private key to the file output
576 *
577 * \param[in] output the FILE descriptor where to print to
578 * \param[in] k the ldns_key to print
579 */
580void ldns_key_print(FILE *output, const ldns_key *k);
581
582/**
583 * frees a key structure, but not its internal data structures
584 *
585 * \param[in] key the key object to free
586 */
587void ldns_key_free(ldns_key *key);
588
589/**
590 * frees a key structure and all its internal data structures, except
591 * the data set by ldns_key_set_external_key()
592 *
593 * \param[in] key the key object to free
594 */
595void ldns_key_deep_free(ldns_key *key);
596
597/**
598 * Frees a key list structure
599 * \param[in] key_list the key list object to free
600 */
601void ldns_key_list_free(ldns_key_list *key_list);
602
603/**
604 * Instantiates a DNSKEY or DS RR from file.
605 * \param[in] filename the file to read the record from
606 * \return the corresponding RR, or NULL if the parsing failed
607 */
608ldns_rr * ldns_read_anchor_file(const char *filename);
609
610/**
611 * Returns the 'default base name' for key files;
612 * IE. K\<zone\>+\<alg\>+\<keytag\>
613 * (without the .key or .private)
614 * The memory for this is allocated by this function,
615 * and should be freed by the caller
616 *
617 * \param[in] key the key to get the file name from
618 * \returns A string containing the file base name
619 */
620char *ldns_key_get_file_base_name(const ldns_key *key);
621
622/**
623 * See if a key algorithm is supported
624 * \param[in] algo the signing algorithm number.
625 * \returns true if supported.
626 */
627int ldns_key_algo_supported(int algo);
628
629/**
630 * Get signing algorithm by name.  Comparison is case insensitive.
631 * \param[in] name string with the name.
632 * \returns 0 on parse failure or the algorithm number.
633 */
634ldns_signing_algorithm ldns_get_signing_algorithm_by_name(const char* name);
635
636#ifdef __cplusplus
637}
638#endif
639
640#endif /* LDNS_KEYS_H */
641