xref: /netbsd-src/crypto/external/bsd/netpgp/dist/src/lib/misc.c (revision 88fcb00c0357f2d7c1774f86a352637bfda96184)
1 /*-
2  * Copyright (c) 2009,2010 The NetBSD Foundation, Inc.
3  * All rights reserved.
4  *
5  * This code is derived from software contributed to The NetBSD Foundation
6  * by Alistair Crooks (agc@NetBSD.org)
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  *
17  * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
18  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
19  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
20  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
21  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
25  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27  * POSSIBILITY OF SUCH DAMAGE.
28  */
29 /*
30  * Copyright (c) 2005-2008 Nominet UK (www.nic.uk)
31  * All rights reserved.
32  * Contributors: Ben Laurie, Rachel Willmer. The Contributors have asserted
33  * their moral rights under the UK Copyright Design and Patents Act 1988 to
34  * be recorded as the authors of this copyright work.
35  *
36  * Licensed under the Apache License, Version 2.0 (the "License"); you may not
37  * use this file except in compliance with the License.
38  *
39  * You may obtain a copy of the License at
40  *     http://www.apache.org/licenses/LICENSE-2.0
41  *
42  * Unless required by applicable law or agreed to in writing, software
43  * distributed under the License is distributed on an "AS IS" BASIS,
44  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
45  *
46  * See the License for the specific language governing permissions and
47  * limitations under the License.
48  */
49 
50 /** \file
51  */
52 #include "config.h"
53 
54 #ifdef HAVE_SYS_CDEFS_H
55 #include <sys/cdefs.h>
56 #endif
57 
58 #if defined(__NetBSD__)
59 __COPYRIGHT("@(#) Copyright (c) 2009 The NetBSD Foundation, Inc. All rights reserved.");
60 __RCSID("$NetBSD: misc.c,v 1.40 2010/11/29 06:21:40 agc Exp $");
61 #endif
62 
63 #include <sys/types.h>
64 #include <sys/stat.h>
65 #include <sys/mman.h>
66 
67 #include <ctype.h>
68 #include <stdarg.h>
69 #include <stdio.h>
70 #include <stdlib.h>
71 #include <string.h>
72 
73 #ifdef HAVE_UNISTD_H
74 #include <unistd.h>
75 #endif
76 
77 #ifdef HAVE_OPENSSL_RAND_H
78 #include <openssl/rand.h>
79 #endif
80 
81 #include "errors.h"
82 #include "packet.h"
83 #include "crypto.h"
84 #include "create.h"
85 #include "packet-parse.h"
86 #include "packet-show.h"
87 #include "signature.h"
88 #include "netpgpsdk.h"
89 #include "netpgpdefs.h"
90 #include "memory.h"
91 #include "readerwriter.h"
92 #include "version.h"
93 #include "netpgpdigest.h"
94 
95 #ifdef WIN32
96 #define vsnprintf _vsnprintf
97 #endif
98 
99 
100 typedef struct {
101 	pgp_keyring_t		*keyring;
102 } accumulate_t;
103 
104 /**
105  * \ingroup Core_Callbacks
106  */
107 static pgp_cb_ret_t
108 accumulate_cb(const pgp_packet_t *pkt, pgp_cbdata_t *cbinfo)
109 {
110 	const pgp_contents_t	*content = &pkt->u;
111 	pgp_keyring_t		*keyring;
112 	accumulate_t		*accumulate;
113 
114 	if (pgp_get_debug_level(__FILE__)) {
115 		(void) fprintf(stderr, "accumulate callback: packet tag %u\n", pkt->tag);
116 	}
117 	accumulate = pgp_callback_arg(cbinfo);
118 	keyring = accumulate->keyring;
119 	switch (pkt->tag) {
120 	case PGP_PTAG_CT_PUBLIC_KEY:
121 	case PGP_PTAG_CT_PUBLIC_SUBKEY:
122 		pgp_add_to_pubring(keyring, &content->pubkey, pkt->tag);
123 		return PGP_KEEP_MEMORY;
124 	case PGP_PTAG_CT_SECRET_KEY:
125 	case PGP_PTAG_CT_ENCRYPTED_SECRET_KEY:
126 		pgp_add_to_secring(keyring, &content->seckey);
127 		return PGP_KEEP_MEMORY;
128 	case PGP_PTAG_CT_USER_ID:
129 		if (pgp_get_debug_level(__FILE__)) {
130 			(void) fprintf(stderr, "User ID: %s for key %d\n",
131 					content->userid,
132 					keyring->keyc - 1);
133 		}
134 		if (keyring->keyc == 0) {
135 			PGP_ERROR(cbinfo->errors, PGP_E_P_NO_USERID, "No userid found");
136 		} else {
137 			pgp_add_userid(&keyring->keys[keyring->keyc - 1], content->userid);
138 		}
139 		return PGP_KEEP_MEMORY;
140 	case PGP_PARSER_PACKET_END:
141 		if (keyring->keyc > 0) {
142 			pgp_add_subpacket(&keyring->keys[keyring->keyc - 1],
143 						&content->packet);
144 			return PGP_KEEP_MEMORY;
145 		}
146 		return PGP_RELEASE_MEMORY;
147 	case PGP_PARSER_ERROR:
148 		(void) fprintf(stderr, "Error: %s\n", content->error);
149 		return PGP_FINISHED;
150 	case PGP_PARSER_ERRCODE:
151 		(void) fprintf(stderr, "parse error: %s\n",
152 				pgp_errcode(content->errcode.errcode));
153 		break;
154 	default:
155 		break;
156 	}
157 	/* XXX: we now exclude so many things, we should either drop this or */
158 	/* do something to pass on copies of the stuff we keep */
159 	return pgp_stacked_callback(pkt, cbinfo);
160 }
161 
162 /**
163  * \ingroup Core_Parse
164  *
165  * Parse packets from an input stream until EOF or error.
166  *
167  * Key data found in the parsed data is added to #keyring.
168  *
169  * \param keyring Pointer to an existing keyring
170  * \param parse Options to use when parsing
171 */
172 int
173 pgp_parse_and_accumulate(pgp_keyring_t *keyring, pgp_stream_t *parse)
174 {
175 	accumulate_t	accumulate;
176 	const int	printerrors = 1;
177 	int             ret;
178 
179 	if (parse->readinfo.accumulate) {
180 		(void) fprintf(stderr,
181 			"pgp_parse_and_accumulate: already init\n");
182 		return 0;
183 	}
184 
185 	(void) memset(&accumulate, 0x0, sizeof(accumulate));
186 
187 	accumulate.keyring = keyring;
188 
189 	pgp_callback_push(parse, accumulate_cb, &accumulate);
190 	parse->readinfo.accumulate = 1;
191 	ret = pgp_parse(parse, !printerrors);
192 
193 	return ret;
194 }
195 
196 
197 /** \file
198  * \brief Error Handling
199  */
200 #define ERRNAME(code)	{ code, #code }
201 
202 static pgp_errcode_name_map_t errcode_name_map[] = {
203 	ERRNAME(PGP_E_OK),
204 	ERRNAME(PGP_E_FAIL),
205 	ERRNAME(PGP_E_SYSTEM_ERROR),
206 	ERRNAME(PGP_E_UNIMPLEMENTED),
207 
208 	ERRNAME(PGP_E_R),
209 	ERRNAME(PGP_E_R_READ_FAILED),
210 	ERRNAME(PGP_E_R_EARLY_EOF),
211 	ERRNAME(PGP_E_R_BAD_FORMAT),
212 	ERRNAME(PGP_E_R_UNCONSUMED_DATA),
213 
214 	ERRNAME(PGP_E_W),
215 	ERRNAME(PGP_E_W_WRITE_FAILED),
216 	ERRNAME(PGP_E_W_WRITE_TOO_SHORT),
217 
218 	ERRNAME(PGP_E_P),
219 	ERRNAME(PGP_E_P_NOT_ENOUGH_DATA),
220 	ERRNAME(PGP_E_P_UNKNOWN_TAG),
221 	ERRNAME(PGP_E_P_PACKET_CONSUMED),
222 	ERRNAME(PGP_E_P_MPI_FORMAT_ERROR),
223 
224 	ERRNAME(PGP_E_C),
225 
226 	ERRNAME(PGP_E_V),
227 	ERRNAME(PGP_E_V_BAD_SIGNATURE),
228 	ERRNAME(PGP_E_V_NO_SIGNATURE),
229 	ERRNAME(PGP_E_V_UNKNOWN_SIGNER),
230 
231 	ERRNAME(PGP_E_ALG),
232 	ERRNAME(PGP_E_ALG_UNSUPPORTED_SYMMETRIC_ALG),
233 	ERRNAME(PGP_E_ALG_UNSUPPORTED_PUBLIC_KEY_ALG),
234 	ERRNAME(PGP_E_ALG_UNSUPPORTED_SIGNATURE_ALG),
235 	ERRNAME(PGP_E_ALG_UNSUPPORTED_HASH_ALG),
236 
237 	ERRNAME(PGP_E_PROTO),
238 	ERRNAME(PGP_E_PROTO_BAD_SYMMETRIC_DECRYPT),
239 	ERRNAME(PGP_E_PROTO_UNKNOWN_SS),
240 	ERRNAME(PGP_E_PROTO_CRITICAL_SS_IGNORED),
241 	ERRNAME(PGP_E_PROTO_BAD_PUBLIC_KEY_VRSN),
242 	ERRNAME(PGP_E_PROTO_BAD_SIGNATURE_VRSN),
243 	ERRNAME(PGP_E_PROTO_BAD_ONE_PASS_SIG_VRSN),
244 	ERRNAME(PGP_E_PROTO_BAD_PKSK_VRSN),
245 	ERRNAME(PGP_E_PROTO_DECRYPTED_MSG_WRONG_LEN),
246 	ERRNAME(PGP_E_PROTO_BAD_SK_CHECKSUM),
247 
248 	{0x00, NULL},		/* this is the end-of-array marker */
249 };
250 
251 /**
252  * \ingroup Core_Errors
253  * \brief returns error code name
254  * \param errcode
255  * \return error code name or "Unknown"
256  */
257 const char     *
258 pgp_errcode(const pgp_errcode_t errcode)
259 {
260 	return (pgp_str_from_map((int) errcode,
261 			(pgp_map_t *) errcode_name_map));
262 }
263 
264 /* generic grab new storage function */
265 void *
266 pgp_new(size_t size)
267 {
268 	void	*vp;
269 
270 	if ((vp = calloc(1, size)) == NULL) {
271 		(void) fprintf(stderr,
272 			"allocation failure for %" PRIsize "u bytes", size);
273 	}
274 	return vp;
275 }
276 
277 /**
278  * \ingroup Core_Errors
279  * \brief Pushes the given error on the given errorstack
280  * \param errstack Error stack to use
281  * \param errcode Code of error to push
282  * \param sys_errno System errno (used if errcode=PGP_E_SYSTEM_ERROR)
283  * \param file Source filename where error occurred
284  * \param line Line in source file where error occurred
285  * \param fmt Comment
286  *
287  */
288 
289 void
290 pgp_push_error(pgp_error_t **errstack, pgp_errcode_t errcode,
291 		int sys_errno, const char *file, int line, const char *fmt,...)
292 {
293 	/* first get the varargs and generate the comment */
294 	pgp_error_t  *err;
295 	unsigned	maxbuf = 128;
296 	va_list		args;
297 	char           *comment;
298 
299 	if ((comment = calloc(1, maxbuf + 1)) == NULL) {
300 		(void) fprintf(stderr, "calloc comment failure\n");
301 		return;
302 	}
303 
304 	va_start(args, fmt);
305 	vsnprintf(comment, maxbuf + 1, fmt, args);
306 	va_end(args);
307 
308 	/* alloc a new error and add it to the top of the stack */
309 
310 	if ((err = calloc(1, sizeof(*err))) == NULL) {
311 		(void) fprintf(stderr, "calloc comment failure\n");
312 		return;
313 	}
314 
315 	err->next = *errstack;
316 	*errstack = err;
317 
318 	/* fill in the details */
319 	err->errcode = errcode;
320 	err->sys_errno = sys_errno;
321 	err->file = file;
322 	err->line = line;
323 
324 	err->comment = comment;
325 }
326 
327 /**
328 \ingroup Core_Errors
329 \brief print this error
330 \param err Error to print
331 */
332 void
333 pgp_print_error(pgp_error_t *err)
334 {
335 	printf("%s:%d: ", err->file, err->line);
336 	if (err->errcode == PGP_E_SYSTEM_ERROR) {
337 		printf("system error %d returned from %s()\n", err->sys_errno,
338 		       err->comment);
339 	} else {
340 		printf("%s, %s\n", pgp_errcode(err->errcode), err->comment);
341 	}
342 }
343 
344 /**
345 \ingroup Core_Errors
346 \brief Print all errors on stack
347 \param errstack Error stack to print
348 */
349 void
350 pgp_print_errors(pgp_error_t *errstack)
351 {
352 	pgp_error_t    *err;
353 
354 	for (err = errstack; err != NULL; err = err->next) {
355 		pgp_print_error(err);
356 	}
357 }
358 
359 /**
360 \ingroup Core_Errors
361 \brief Return 1 if given error is present anywhere on stack
362 \param errstack Error stack to check
363 \param errcode Error code to look for
364 \return 1 if found; else 0
365 */
366 int
367 pgp_has_error(pgp_error_t *errstack, pgp_errcode_t errcode)
368 {
369 	pgp_error_t    *err;
370 
371 	for (err = errstack; err != NULL; err = err->next) {
372 		if (err->errcode == errcode) {
373 			return 1;
374 		}
375 	}
376 	return 0;
377 }
378 
379 /**
380 \ingroup Core_Errors
381 \brief Frees all errors on stack
382 \param errstack Error stack to free
383 */
384 void
385 pgp_free_errors(pgp_error_t *errstack)
386 {
387 	pgp_error_t    *next;
388 
389 	while (errstack != NULL) {
390 		next = errstack->next;
391 		free(errstack->comment);
392 		free(errstack);
393 		errstack = next;
394 	}
395 }
396 
397 /* hash a 32-bit integer */
398 static int
399 hash_uint32(pgp_hash_t *hash, uint32_t n)
400 {
401 	uint8_t	ibuf[4];
402 
403 	ibuf[0] = (uint8_t)(n >> 24) & 0xff;
404 	ibuf[1] = (uint8_t)(n >> 16) & 0xff;
405 	ibuf[2] = (uint8_t)(n >> 8) & 0xff;
406 	ibuf[3] = (uint8_t)n & 0xff;
407 	(*hash->add)(hash, (const uint8_t *)(void *)ibuf, (unsigned)sizeof(ibuf));
408 	return sizeof(ibuf);
409 }
410 
411 /* hash a string - first length, then string itself */
412 static int
413 hash_string(pgp_hash_t *hash, const uint8_t *buf, uint32_t len)
414 {
415 	if (pgp_get_debug_level(__FILE__)) {
416 		hexdump(stderr, "hash_string", buf, len);
417 	}
418 	hash_uint32(hash, len);
419 	(*hash->add)(hash, buf, len);
420 	return (int)(sizeof(len) + len);
421 }
422 
423 /* hash a bignum, possibly padded - first length, then string itself */
424 static int
425 hash_bignum(pgp_hash_t *hash, BIGNUM *bignum)
426 {
427 	uint8_t	*bn;
428 	size_t	 len;
429 	int	 padbyte;
430 
431 	if (BN_is_zero(bignum)) {
432 		hash_uint32(hash, 0);
433 		return sizeof(len);
434 	}
435 	if ((len = (size_t) BN_num_bytes(bignum)) < 1) {
436 		(void) fprintf(stderr, "hash_bignum: bad size\n");
437 		return 0;
438 	}
439 	if ((bn = calloc(1, len)) == NULL) {
440 		(void) fprintf(stderr, "hash_bignum: bad bn alloc\n");
441 		return 0;
442 	}
443 	BN_bn2bin(bignum, bn + 1);
444 	bn[0] = 0x0;
445 	padbyte = (bn[1] & 0x80) ? 1 : 0;
446 	hash_string(hash, bn + 1 - padbyte, (unsigned)(len + padbyte));
447 	free(bn);
448 	return (int)(sizeof(len) + len + padbyte);
449 }
450 
451 /** \file
452  */
453 
454 /**
455  * \ingroup Core_Keys
456  * \brief Calculate a public key fingerprint.
457  * \param fp Where to put the calculated fingerprint
458  * \param key The key for which the fingerprint is calculated
459  */
460 int
461 pgp_fingerprint(pgp_fingerprint_t *fp, const pgp_pubkey_t *key, pgp_hash_alg_t hashtype)
462 {
463 	pgp_memory_t	*mem;
464 	pgp_hash_t	 hash;
465 	const char	*type;
466 	uint32_t	 len;
467 
468 	mem = pgp_memory_new();
469 	if (key->version == 2 || key->version == 3) {
470 		if (key->alg != PGP_PKA_RSA &&
471 		    key->alg != PGP_PKA_RSA_ENCRYPT_ONLY &&
472 		    key->alg != PGP_PKA_RSA_SIGN_ONLY) {
473 			(void) fprintf(stderr,
474 				"pgp_fingerprint: bad algorithm\n");
475 			return 0;
476 		}
477 		pgp_hash_md5(&hash);
478 		if (!hash.init(&hash)) {
479 			(void) fprintf(stderr,
480 				"pgp_fingerprint: bad md5 alloc\n");
481 			return 0;
482 		}
483 		hash_bignum(&hash, key->key.rsa.n);
484 		hash_bignum(&hash, key->key.rsa.e);
485 		fp->length = hash.finish(&hash, fp->fingerprint);
486 		if (pgp_get_debug_level(__FILE__)) {
487 			hexdump(stderr, "v2/v3 fingerprint", fp->fingerprint, fp->length);
488 		}
489 	} else if (hashtype == PGP_HASH_MD5) {
490 		pgp_hash_md5(&hash);
491 		if (!hash.init(&hash)) {
492 			(void) fprintf(stderr,
493 				"pgp_fingerprint: bad md5 alloc\n");
494 			return 0;
495 		}
496 		type = (key->alg == PGP_PKA_RSA) ? "ssh-rsa" : "ssh-dss";
497 		hash_string(&hash, (const uint8_t *)(const void *)type, (unsigned)strlen(type));
498 		switch(key->alg) {
499 		case PGP_PKA_RSA:
500 			hash_bignum(&hash, key->key.rsa.e);
501 			hash_bignum(&hash, key->key.rsa.n);
502 			break;
503 		case PGP_PKA_DSA:
504 			hash_bignum(&hash, key->key.dsa.p);
505 			hash_bignum(&hash, key->key.dsa.q);
506 			hash_bignum(&hash, key->key.dsa.g);
507 			hash_bignum(&hash, key->key.dsa.y);
508 			break;
509 		default:
510 			break;
511 		}
512 		fp->length = hash.finish(&hash, fp->fingerprint);
513 		if (pgp_get_debug_level(__FILE__)) {
514 			hexdump(stderr, "md5 fingerprint", fp->fingerprint, fp->length);
515 		}
516 	} else {
517 		pgp_build_pubkey(mem, key, 0);
518 		pgp_hash_sha1(&hash);
519 		if (!hash.init(&hash)) {
520 			(void) fprintf(stderr,
521 				"pgp_fingerprint: bad sha1 alloc\n");
522 			return 0;
523 		}
524 		len = (unsigned)pgp_mem_len(mem);
525 		pgp_hash_add_int(&hash, 0x99, 1);
526 		pgp_hash_add_int(&hash, len, 2);
527 		hash.add(&hash, pgp_mem_data(mem), len);
528 		fp->length = hash.finish(&hash, fp->fingerprint);
529 		pgp_memory_free(mem);
530 		if (pgp_get_debug_level(__FILE__)) {
531 			hexdump(stderr, "sha1 fingerprint", fp->fingerprint, fp->length);
532 		}
533 	}
534 	return 1;
535 }
536 
537 /**
538  * \ingroup Core_Keys
539  * \brief Calculate the Key ID from the public key.
540  * \param keyid Space for the calculated ID to be stored
541  * \param key The key for which the ID is calculated
542  */
543 
544 int
545 pgp_keyid(uint8_t *keyid, const size_t idlen, const pgp_pubkey_t *key, pgp_hash_alg_t hashtype)
546 {
547 	pgp_fingerprint_t finger;
548 
549 	if (key->version == 2 || key->version == 3) {
550 		unsigned	n;
551 		uint8_t		bn[NETPGP_BUFSIZ];
552 
553 		n = (unsigned) BN_num_bytes(key->key.rsa.n);
554 		if (n > sizeof(bn)) {
555 			(void) fprintf(stderr, "pgp_keyid: bad num bytes\n");
556 			return 0;
557 		}
558 		if (key->alg != PGP_PKA_RSA &&
559 		    key->alg != PGP_PKA_RSA_ENCRYPT_ONLY &&
560 		    key->alg != PGP_PKA_RSA_SIGN_ONLY) {
561 			(void) fprintf(stderr, "pgp_keyid: bad algorithm\n");
562 			return 0;
563 		}
564 		BN_bn2bin(key->key.rsa.n, bn);
565 		(void) memcpy(keyid, bn + n - idlen, idlen);
566 	} else {
567 		pgp_fingerprint(&finger, key, hashtype);
568 		(void) memcpy(keyid,
569 				finger.fingerprint + finger.length - idlen,
570 				idlen);
571 	}
572 	return 1;
573 }
574 
575 /**
576 \ingroup Core_Hashes
577 \brief Add to the hash
578 \param hash Hash to add to
579 \param n Int to add
580 \param length Length of int in bytes
581 */
582 void
583 pgp_hash_add_int(pgp_hash_t *hash, unsigned n, unsigned length)
584 {
585 	uint8_t   c;
586 
587 	while (length--) {
588 		c = n >> (length * 8);
589 		hash->add(hash, &c, 1);
590 	}
591 }
592 
593 /**
594 \ingroup Core_Hashes
595 \brief Setup hash for given hash algorithm
596 \param hash Hash to set up
597 \param alg Hash algorithm to use
598 */
599 void
600 pgp_hash_any(pgp_hash_t *hash, pgp_hash_alg_t alg)
601 {
602 	switch (alg) {
603 	case PGP_HASH_MD5:
604 		pgp_hash_md5(hash);
605 		break;
606 
607 	case PGP_HASH_SHA1:
608 		pgp_hash_sha1(hash);
609 		break;
610 
611 	case PGP_HASH_SHA256:
612 		pgp_hash_sha256(hash);
613 		break;
614 
615 	case PGP_HASH_SHA384:
616 		pgp_hash_sha384(hash);
617 		break;
618 
619 	case PGP_HASH_SHA512:
620 		pgp_hash_sha512(hash);
621 		break;
622 
623 	case PGP_HASH_SHA224:
624 		pgp_hash_sha224(hash);
625 		break;
626 
627 	default:
628 		(void) fprintf(stderr, "pgp_hash_any: bad algorithm\n");
629 	}
630 }
631 
632 /**
633 \ingroup Core_Hashes
634 \brief Returns size of hash for given hash algorithm
635 \param alg Hash algorithm to use
636 \return Size of hash algorithm in bytes
637 */
638 unsigned
639 pgp_hash_size(pgp_hash_alg_t alg)
640 {
641 	switch (alg) {
642 	case PGP_HASH_MD5:
643 		return 16;
644 
645 	case PGP_HASH_SHA1:
646 		return 20;
647 
648 	case PGP_HASH_SHA256:
649 		return 32;
650 
651 	case PGP_HASH_SHA224:
652 		return 28;
653 
654 	case PGP_HASH_SHA512:
655 		return 64;
656 
657 	case PGP_HASH_SHA384:
658 		return 48;
659 
660 	default:
661 		(void) fprintf(stderr, "pgp_hash_size: bad algorithm\n");
662 	}
663 
664 	return 0;
665 }
666 
667 /**
668 \ingroup Core_Hashes
669 \brief Returns hash enum corresponding to given string
670 \param hash Text name of hash algorithm i.e. "SHA1"
671 \returns Corresponding enum i.e. PGP_HASH_SHA1
672 */
673 pgp_hash_alg_t
674 pgp_str_to_hash_alg(const char *hash)
675 {
676 	if (hash == NULL) {
677 		return PGP_DEFAULT_HASH_ALGORITHM;
678 	}
679 	if (netpgp_strcasecmp(hash, "SHA1") == 0) {
680 		return PGP_HASH_SHA1;
681 	}
682 	if (netpgp_strcasecmp(hash, "MD5") == 0) {
683 		return PGP_HASH_MD5;
684 	}
685 	if (netpgp_strcasecmp(hash, "SHA256") == 0) {
686 		return PGP_HASH_SHA256;
687 	}
688 	/*
689         if (netpgp_strcasecmp(hash,"SHA224") == 0) {
690 		return PGP_HASH_SHA224;
691 	}
692         */
693 	if (netpgp_strcasecmp(hash, "SHA512") == 0) {
694 		return PGP_HASH_SHA512;
695 	}
696 	if (netpgp_strcasecmp(hash, "SHA384") == 0) {
697 		return PGP_HASH_SHA384;
698 	}
699 	return PGP_HASH_UNKNOWN;
700 }
701 
702 /**
703 \ingroup Core_Hashes
704 \brief Hash given data
705 \param out Where to write the hash
706 \param alg Hash algorithm to use
707 \param in Data to hash
708 \param length Length of data
709 \return Size of hash created
710 */
711 unsigned
712 pgp_hash(uint8_t *out, pgp_hash_alg_t alg, const void *in, size_t length)
713 {
714 	pgp_hash_t      hash;
715 
716 	pgp_hash_any(&hash, alg);
717 	if (!hash.init(&hash)) {
718 		(void) fprintf(stderr, "pgp_hash: bad alloc\n");
719 		/* we'll just continue here - don't want to return a 0 hash */
720 		/* XXX - agc - no way to return failure */
721 	}
722 	hash.add(&hash, in, (unsigned)length);
723 	return hash.finish(&hash, out);
724 }
725 
726 /**
727 \ingroup Core_Hashes
728 \brief Calculate hash for MDC packet
729 \param preamble Preamble to hash
730 \param sz_preamble Size of preamble
731 \param plaintext Plaintext to hash
732 \param sz_plaintext Size of plaintext
733 \param hashed Resulting hash
734 */
735 void
736 pgp_calc_mdc_hash(const uint8_t *preamble,
737 			const size_t sz_preamble,
738 			const uint8_t *plaintext,
739 			const unsigned sz_plaintext,
740 			uint8_t *hashed)
741 {
742 	pgp_hash_t	hash;
743 	uint8_t		c;
744 
745 	if (pgp_get_debug_level(__FILE__)) {
746 		hexdump(stderr, "preamble", preamble, sz_preamble);
747 		hexdump(stderr, "plaintext", plaintext, sz_plaintext);
748 	}
749 	/* init */
750 	pgp_hash_any(&hash, PGP_HASH_SHA1);
751 	if (!hash.init(&hash)) {
752 		(void) fprintf(stderr, "pgp_calc_mdc_hash: bad alloc\n");
753 		/* we'll just continue here - it will die anyway */
754 		/* agc - XXX - no way to return failure */
755 	}
756 
757 	/* preamble */
758 	hash.add(&hash, preamble, (unsigned)sz_preamble);
759 	/* plaintext */
760 	hash.add(&hash, plaintext, sz_plaintext);
761 	/* MDC packet tag */
762 	c = MDC_PKT_TAG;
763 	hash.add(&hash, &c, 1);
764 	/* MDC packet len */
765 	c = PGP_SHA1_HASH_SIZE;
766 	hash.add(&hash, &c, 1);
767 
768 	/* finish */
769 	hash.finish(&hash, hashed);
770 
771 	if (pgp_get_debug_level(__FILE__)) {
772 		hexdump(stderr, "hashed", hashed, PGP_SHA1_HASH_SIZE);
773 	}
774 }
775 
776 /**
777 \ingroup HighLevel_Supported
778 \brief Is this Hash Algorithm supported?
779 \param hash_alg Hash Algorithm to check
780 \return 1 if supported; else 0
781 */
782 unsigned
783 pgp_is_hash_alg_supported(const pgp_hash_alg_t *hash_alg)
784 {
785 	switch (*hash_alg) {
786 	case PGP_HASH_MD5:
787 	case PGP_HASH_SHA1:
788 	case PGP_HASH_SHA256:
789 		return 1;
790 
791 	default:
792 		return 0;
793 	}
794 }
795 
796 /* structure to map string to cipher def */
797 typedef struct str2cipher_t {
798 	const char	*s;	/* cipher name */
799 	pgp_symm_alg_t i;	/* cipher def */
800 } str2cipher_t;
801 
802 static str2cipher_t	str2cipher[] = {
803 	{	"cast5",		PGP_SA_CAST5		},
804 	{	"idea",			PGP_SA_IDEA		},
805 	{	"aes128",		PGP_SA_AES_128		},
806 	{	"aes256",		PGP_SA_AES_256		},
807 	{	"camellia128",		PGP_SA_CAMELLIA_128	},
808 	{	"camellia256",		PGP_SA_CAMELLIA_256	},
809 	{	"tripledes",		PGP_SA_TRIPLEDES	},
810 	{	NULL,			0			}
811 };
812 
813 /* convert from a string to a cipher definition */
814 pgp_symm_alg_t
815 pgp_str_to_cipher(const char *cipher)
816 {
817 	str2cipher_t	*sp;
818 
819 	for (sp = str2cipher ; cipher && sp->s ; sp++) {
820 		if (netpgp_strcasecmp(cipher, sp->s) == 0) {
821 			return sp->i;
822 		}
823 	}
824 	return PGP_SA_DEFAULT_CIPHER;
825 }
826 
827 void
828 pgp_random(void *dest, size_t length)
829 {
830 	RAND_bytes(dest, (int)length);
831 }
832 
833 /**
834 \ingroup HighLevel_Memory
835 \brief Memory to initialise
836 \param mem memory to initialise
837 \param needed Size to initialise to
838 */
839 void
840 pgp_memory_init(pgp_memory_t *mem, size_t needed)
841 {
842 	uint8_t	*temp;
843 
844 	mem->length = 0;
845 	if (mem->buf) {
846 		if (mem->allocated < needed) {
847 			if ((temp = realloc(mem->buf, needed)) == NULL) {
848 				(void) fprintf(stderr, "pgp_memory_init: bad alloc\n");
849 			} else {
850 				mem->buf = temp;
851 				mem->allocated = needed;
852 			}
853 		}
854 	} else {
855 		if ((mem->buf = calloc(1, needed)) == NULL) {
856 			(void) fprintf(stderr, "pgp_memory_init: bad alloc\n");
857 		} else {
858 			mem->allocated = needed;
859 		}
860 	}
861 }
862 
863 /**
864 \ingroup HighLevel_Memory
865 \brief Pad memory to required length
866 \param mem Memory to use
867 \param length New size
868 */
869 void
870 pgp_memory_pad(pgp_memory_t *mem, size_t length)
871 {
872 	uint8_t	*temp;
873 
874 	if (mem->allocated < mem->length) {
875 		(void) fprintf(stderr, "pgp_memory_pad: bad alloc in\n");
876 		return;
877 	}
878 	if (mem->allocated < mem->length + length) {
879 		mem->allocated = mem->allocated * 2 + length;
880 		temp = realloc(mem->buf, mem->allocated);
881 		if (temp == NULL) {
882 			(void) fprintf(stderr, "pgp_memory_pad: bad alloc\n");
883 		} else {
884 			mem->buf = temp;
885 		}
886 	}
887 	if (mem->allocated < mem->length + length) {
888 		(void) fprintf(stderr, "pgp_memory_pad: bad alloc out\n");
889 	}
890 }
891 
892 /**
893 \ingroup HighLevel_Memory
894 \brief Add data to memory
895 \param mem Memory to which to add
896 \param src Data to add
897 \param length Length of data to add
898 */
899 void
900 pgp_memory_add(pgp_memory_t *mem, const uint8_t *src, size_t length)
901 {
902 	pgp_memory_pad(mem, length);
903 	(void) memcpy(mem->buf + mem->length, src, length);
904 	mem->length += length;
905 }
906 
907 /* XXX: this could be refactored via the writer, but an awful lot of */
908 /* hoops to jump through for 2 lines of code! */
909 void
910 pgp_memory_place_int(pgp_memory_t *mem, unsigned offset, unsigned n,
911 		     size_t length)
912 {
913 	if (mem->allocated < offset + length) {
914 		(void) fprintf(stderr,
915 			"pgp_memory_place_int: bad alloc\n");
916 	} else {
917 		while (length-- > 0) {
918 			mem->buf[offset++] = n >> (length * 8);
919 		}
920 	}
921 }
922 
923 /**
924  * \ingroup HighLevel_Memory
925  * \brief Retains allocated memory and set length of stored data to zero.
926  * \param mem Memory to clear
927  * \sa pgp_memory_release()
928  * \sa pgp_memory_free()
929  */
930 void
931 pgp_memory_clear(pgp_memory_t *mem)
932 {
933 	mem->length = 0;
934 }
935 
936 /**
937 \ingroup HighLevel_Memory
938 \brief Free memory and associated data
939 \param mem Memory to free
940 \note This does not free mem itself
941 \sa pgp_memory_clear()
942 \sa pgp_memory_free()
943 */
944 void
945 pgp_memory_release(pgp_memory_t *mem)
946 {
947 	if (mem->mmapped) {
948 		(void) munmap(mem->buf, mem->length);
949 	} else {
950 		free(mem->buf);
951 	}
952 	mem->buf = NULL;
953 	mem->length = 0;
954 }
955 
956 void
957 pgp_memory_make_packet(pgp_memory_t *out, pgp_content_enum tag)
958 {
959 	size_t          extra;
960 
961 	extra = (out->length < 192) ? 1 : (out->length < 8192 + 192) ? 2 : 5;
962 	pgp_memory_pad(out, extra + 1);
963 	memmove(out->buf + extra + 1, out->buf, out->length);
964 
965 	out->buf[0] = PGP_PTAG_ALWAYS_SET | PGP_PTAG_NEW_FORMAT | tag;
966 
967 	if (out->length < 192) {
968 		out->buf[1] = (uint8_t)out->length;
969 	} else if (out->length < 8192 + 192) {
970 		out->buf[1] = (uint8_t)((out->length - 192) >> 8) + 192;
971 		out->buf[2] = (uint8_t)(out->length - 192);
972 	} else {
973 		out->buf[1] = 0xff;
974 		out->buf[2] = (uint8_t)(out->length >> 24);
975 		out->buf[3] = (uint8_t)(out->length >> 16);
976 		out->buf[4] = (uint8_t)(out->length >> 8);
977 		out->buf[5] = (uint8_t)(out->length);
978 	}
979 
980 	out->length += extra + 1;
981 }
982 
983 /**
984    \ingroup HighLevel_Memory
985    \brief Create a new zeroed pgp_memory_t
986    \return Pointer to new pgp_memory_t
987    \note Free using pgp_memory_free() after use.
988    \sa pgp_memory_free()
989 */
990 
991 pgp_memory_t   *
992 pgp_memory_new(void)
993 {
994 	return calloc(1, sizeof(pgp_memory_t));
995 }
996 
997 /**
998    \ingroup HighLevel_Memory
999    \brief Free memory ptr and associated memory
1000    \param mem Memory to be freed
1001    \sa pgp_memory_release()
1002    \sa pgp_memory_clear()
1003 */
1004 
1005 void
1006 pgp_memory_free(pgp_memory_t *mem)
1007 {
1008 	pgp_memory_release(mem);
1009 	free(mem);
1010 }
1011 
1012 /**
1013    \ingroup HighLevel_Memory
1014    \brief Get length of data stored in pgp_memory_t struct
1015    \return Number of bytes in data
1016 */
1017 size_t
1018 pgp_mem_len(const pgp_memory_t *mem)
1019 {
1020 	return mem->length;
1021 }
1022 
1023 /**
1024    \ingroup HighLevel_Memory
1025    \brief Get data stored in pgp_memory_t struct
1026    \return Pointer to data
1027 */
1028 void *
1029 pgp_mem_data(pgp_memory_t *mem)
1030 {
1031 	return mem->buf;
1032 }
1033 
1034 /* read a gile into an pgp_memory_t */
1035 int
1036 pgp_mem_readfile(pgp_memory_t *mem, const char *f)
1037 {
1038 	struct stat	 st;
1039 	FILE		*fp;
1040 	int		 cc;
1041 
1042 	if ((fp = fopen(f, "rb")) == NULL) {
1043 		(void) fprintf(stderr,
1044 				"pgp_mem_readfile: can't open \"%s\"\n", f);
1045 		return 0;
1046 	}
1047 	(void) fstat(fileno(fp), &st);
1048 	mem->allocated = (size_t)st.st_size;
1049 	mem->buf = mmap(NULL, mem->allocated, PROT_READ,
1050 				MAP_PRIVATE | MAP_FILE, fileno(fp), 0);
1051 	if (mem->buf == MAP_FAILED) {
1052 		/* mmap failed for some reason - try to allocate memory */
1053 		if ((mem->buf = calloc(1, mem->allocated)) == NULL) {
1054 			(void) fprintf(stderr, "pgp_mem_readfile: calloc\n");
1055 			(void) fclose(fp);
1056 			return 0;
1057 		}
1058 		/* read into contents of mem */
1059 		for (mem->length = 0 ;
1060 		     (cc = (int)read(fileno(fp), &mem->buf[mem->length],
1061 					(size_t)(mem->allocated - mem->length))) > 0 ;
1062 		     mem->length += (size_t)cc) {
1063 		}
1064 	} else {
1065 		mem->length = mem->allocated;
1066 		mem->mmapped = 1;
1067 	}
1068 	(void) fclose(fp);
1069 	return (mem->allocated == mem->length);
1070 }
1071 
1072 typedef struct {
1073 	uint16_t  sum;
1074 } sum16_t;
1075 
1076 
1077 /**
1078  * Searches the given map for the given type.
1079  * Returns a human-readable descriptive string if found,
1080  * returns NULL if not found
1081  *
1082  * It is the responsibility of the calling function to handle the
1083  * error case sensibly (i.e. don't just print out the return string.
1084  *
1085  */
1086 static const char *
1087 str_from_map_or_null(int type, pgp_map_t *map)
1088 {
1089 	pgp_map_t      *row;
1090 
1091 	for (row = map; row->string != NULL; row++) {
1092 		if (row->type == type) {
1093 			return row->string;
1094 		}
1095 	}
1096 	return NULL;
1097 }
1098 
1099 /**
1100  * \ingroup Core_Print
1101  *
1102  * Searches the given map for the given type.
1103  * Returns a readable string if found, "Unknown" if not.
1104  */
1105 
1106 const char     *
1107 pgp_str_from_map(int type, pgp_map_t *map)
1108 {
1109 	const char     *str;
1110 
1111 	str = str_from_map_or_null(type, map);
1112 	return (str) ? str : "Unknown";
1113 }
1114 
1115 #define LINELEN	16
1116 
1117 /* show hexadecimal/ascii dump */
1118 void
1119 hexdump(FILE *fp, const char *header, const uint8_t *src, size_t length)
1120 {
1121 	size_t	i;
1122 	char	line[LINELEN + 1];
1123 
1124 	(void) fprintf(fp, "%s%s", (header) ? header : "", (header) ? "\n" : "");
1125 	(void) fprintf(fp, "[%" PRIsize "u char%s]\n", length, (length == 1) ? "" : "s");
1126 	for (i = 0 ; i < length ; i++) {
1127 		if (i % LINELEN == 0) {
1128 			(void) fprintf(fp, "%.5" PRIsize "u | ", i);
1129 		}
1130 		(void) fprintf(fp, "%.02x ", (uint8_t)src[i]);
1131 		line[i % LINELEN] = (isprint(src[i])) ? src[i] : '.';
1132 		if (i % LINELEN == LINELEN - 1) {
1133 			line[LINELEN] = 0x0;
1134 			(void) fprintf(fp, " | %s\n", line);
1135 		}
1136 	}
1137 	if (i % LINELEN != 0) {
1138 		for ( ; i % LINELEN != 0 ; i++) {
1139 			(void) fprintf(fp, "   ");
1140 			line[i % LINELEN] = ' ';
1141 		}
1142 		line[LINELEN] = 0x0;
1143 		(void) fprintf(fp, " | %s\n", line);
1144 	}
1145 }
1146 
1147 /**
1148  * \ingroup HighLevel_Functions
1149  * \brief Closes down OpenPGP::SDK.
1150  *
1151  * Close down OpenPGP:SDK, release any resources under the control of
1152  * the library.
1153  */
1154 
1155 void
1156 pgp_finish(void)
1157 {
1158 	pgp_crypto_finish();
1159 }
1160 
1161 static int
1162 sum16_reader(pgp_stream_t *stream, void *dest_, size_t length, pgp_error_t **errors,
1163 	     pgp_reader_t *readinfo, pgp_cbdata_t *cbinfo)
1164 {
1165 	const uint8_t	*dest = dest_;
1166 	sum16_t		*arg = pgp_reader_get_arg(readinfo);
1167 	int		 r;
1168 	int		 n;
1169 
1170 	r = pgp_stacked_read(stream, dest_, length, errors, readinfo, cbinfo);
1171 	if (r < 0) {
1172 		return r;
1173 	}
1174 	for (n = 0; n < r; ++n) {
1175 		arg->sum = (arg->sum + dest[n]) & 0xffff;
1176 	}
1177 	return r;
1178 }
1179 
1180 static void
1181 sum16_destroyer(pgp_reader_t *readinfo)
1182 {
1183 	free(pgp_reader_get_arg(readinfo));
1184 }
1185 
1186 /**
1187    \ingroup Internal_Readers_Sum16
1188    \param stream Parse settings
1189 */
1190 
1191 void
1192 pgp_reader_push_sum16(pgp_stream_t *stream)
1193 {
1194 	sum16_t    *arg;
1195 
1196 	if ((arg = calloc(1, sizeof(*arg))) == NULL) {
1197 		(void) fprintf(stderr, "pgp_reader_push_sum16: bad alloc\n");
1198 	} else {
1199 		pgp_reader_push(stream, sum16_reader, sum16_destroyer, arg);
1200 	}
1201 }
1202 
1203 /**
1204    \ingroup Internal_Readers_Sum16
1205    \param stream Parse settings
1206    \return sum
1207 */
1208 uint16_t
1209 pgp_reader_pop_sum16(pgp_stream_t *stream)
1210 {
1211 	uint16_t	 sum;
1212 	sum16_t		*arg;
1213 
1214 	arg = pgp_reader_get_arg(pgp_readinfo(stream));
1215 	sum = arg->sum;
1216 	pgp_reader_pop(stream);
1217 	free(arg);
1218 	return sum;
1219 }
1220 
1221 /* small useful functions for setting the file-level debugging levels */
1222 /* if the debugv list contains the filename in question, we're debugging it */
1223 
1224 enum {
1225 	MAX_DEBUG_NAMES = 32
1226 };
1227 
1228 static int      debugc;
1229 static char    *debugv[MAX_DEBUG_NAMES];
1230 
1231 /* set the debugging level per filename */
1232 int
1233 pgp_set_debug_level(const char *f)
1234 {
1235 	const char     *name;
1236 	int             i;
1237 
1238 	if (f == NULL) {
1239 		f = "all";
1240 	}
1241 	if ((name = strrchr(f, '/')) == NULL) {
1242 		name = f;
1243 	} else {
1244 		name += 1;
1245 	}
1246 	for (i = 0; i < debugc && i < MAX_DEBUG_NAMES; i++) {
1247 		if (strcmp(debugv[i], name) == 0) {
1248 			return 1;
1249 		}
1250 	}
1251 	if (i == MAX_DEBUG_NAMES) {
1252 		return 0;
1253 	}
1254 	debugv[debugc++] = netpgp_strdup(name);
1255 	return 1;
1256 }
1257 
1258 /* get the debugging level per filename */
1259 int
1260 pgp_get_debug_level(const char *f)
1261 {
1262 	const char     *name;
1263 	int             i;
1264 
1265 	if ((name = strrchr(f, '/')) == NULL) {
1266 		name = f;
1267 	} else {
1268 		name += 1;
1269 	}
1270 	for (i = 0; i < debugc; i++) {
1271 		if (strcmp(debugv[i], "all") == 0 ||
1272 		    strcmp(debugv[i], name) == 0) {
1273 			return 1;
1274 		}
1275 	}
1276 	return 0;
1277 }
1278 
1279 /* return the version for the library */
1280 const char *
1281 pgp_get_info(const char *type)
1282 {
1283 	if (strcmp(type, "version") == 0) {
1284 		return NETPGP_VERSION_STRING;
1285 	}
1286 	if (strcmp(type, "maintainer") == 0) {
1287 		return NETPGP_MAINTAINER;
1288 	}
1289 	return "[unknown]";
1290 }
1291 
1292 /* local version of asprintf so we don't have to play autoconf games */
1293 int
1294 pgp_asprintf(char **ret, const char *fmt, ...)
1295 {
1296 	va_list args;
1297 	char    buf[120 * 1024];	/* XXX - "huge" buffer on stack */
1298 	int     cc;
1299 
1300 	va_start(args, fmt);
1301 	cc = vsnprintf(buf, sizeof(buf), fmt, args);
1302 	va_end(args);
1303 	if ((*ret = calloc(1, (size_t)(cc + 1))) == NULL) {
1304 		*ret = NULL;
1305 		return -1;
1306 	}
1307 	(void) memcpy(*ret, buf, (size_t)cc);
1308 	(*ret)[cc] = 0x0;
1309 	return cc;
1310 }
1311 
1312 void
1313 netpgp_log(const char *fmt, ...)
1314 {
1315 	va_list	 vp;
1316 	time_t	 t;
1317 	char	 buf[BUFSIZ * 2];
1318 	int	 cc;
1319 
1320 	(void) time(&t);
1321 	cc = snprintf(buf, sizeof(buf), "%.24s: netpgp: ", ctime(&t));
1322 	va_start(vp, fmt);
1323 	(void) vsnprintf(&buf[cc], sizeof(buf) - (size_t)cc, fmt, vp);
1324 	va_end(vp);
1325 	/* do something with message */
1326 	/* put into log buffer? */
1327 }
1328 
1329 /* portable replacement for strdup(3) */
1330 char *
1331 netpgp_strdup(const char *s)
1332 {
1333 	size_t	 len;
1334 	char	*cp;
1335 
1336 	len = strlen(s);
1337 	if ((cp = calloc(1, len + 1)) != NULL) {
1338 		(void) memcpy(cp, s, len);
1339 		cp[len] = 0x0;
1340 	}
1341 	return cp;
1342 }
1343 
1344 /* portable replacement for strcasecmp(3) */
1345 int
1346 netpgp_strcasecmp(const char *s1, const char *s2)
1347 {
1348 	int	n;
1349 
1350 	for (n = 0 ; *s1 && *s2 && (n = tolower((uint8_t)*s1) - tolower((uint8_t)*s2)) == 0 ; s1++, s2++) {
1351 	}
1352 	return n;
1353 }
1354