~ubuntu-branches/ubuntu/lucid/openssh/lucid

1.13.4 by Colin Watson
Import upstream version 5.2p1
1
/* $OpenBSD: key.c,v 1.80 2008/10/10 05:00:12 stevesk Exp $ */
1 by Noah Meyerhans
Import upstream version 3.8.1p1
2
/*
3
 * read_bignum():
4
 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
5
 *
6
 * As far as I am concerned, the code I have written for this software
7
 * can be used freely for any purpose.  Any derived versions of this
8
 * software must be clearly marked as such, and if the derived work is
9
 * incompatible with the protocol description in the RFC file, it must be
10
 * called by a name other than "ssh" or "Secure Shell".
11
 *
12
 *
13
 * Copyright (c) 2000, 2001 Markus Friedl.  All rights reserved.
1.13.3 by Colin Watson
Import upstream version 5.1p1
14
 * Copyright (c) 2008 Alexander von Gernler.  All rights reserved.
1 by Noah Meyerhans
Import upstream version 3.8.1p1
15
 *
16
 * Redistribution and use in source and binary forms, with or without
17
 * modification, are permitted provided that the following conditions
18
 * are met:
19
 * 1. Redistributions of source code must retain the above copyright
20
 *    notice, this list of conditions and the following disclaimer.
21
 * 2. Redistributions in binary form must reproduce the above copyright
22
 *    notice, this list of conditions and the following disclaimer in the
23
 *    documentation and/or other materials provided with the distribution.
24
 *
25
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
26
 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
27
 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
28
 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
29
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
30
 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
31
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
32
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
33
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
34
 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
35
 */
1.13.1 by Colin Watson
Import upstream version 4.6p1
36
1 by Noah Meyerhans
Import upstream version 3.8.1p1
37
#include "includes.h"
1.13.1 by Colin Watson
Import upstream version 4.6p1
38
1.13.3 by Colin Watson
Import upstream version 5.1p1
39
#include <sys/param.h>
1.13.1 by Colin Watson
Import upstream version 4.6p1
40
#include <sys/types.h>
1 by Noah Meyerhans
Import upstream version 3.8.1p1
41
42
#include <openssl/evp.h>
1.13.3 by Colin Watson
Import upstream version 5.1p1
43
#include <openbsd-compat/openssl-compat.h>
1 by Noah Meyerhans
Import upstream version 3.8.1p1
44
1.13.1 by Colin Watson
Import upstream version 4.6p1
45
#include <stdarg.h>
46
#include <stdio.h>
47
#include <string.h>
48
1 by Noah Meyerhans
Import upstream version 3.8.1p1
49
#include "xmalloc.h"
50
#include "key.h"
51
#include "rsa.h"
52
#include "uuencode.h"
53
#include "buffer.h"
54
#include "log.h"
55
56
Key *
57
key_new(int type)
58
{
59
	Key *k;
60
	RSA *rsa;
61
	DSA *dsa;
1.13.1 by Colin Watson
Import upstream version 4.6p1
62
	k = xcalloc(1, sizeof(*k));
1 by Noah Meyerhans
Import upstream version 3.8.1p1
63
	k->type = type;
64
	k->dsa = NULL;
65
	k->rsa = NULL;
66
	switch (k->type) {
67
	case KEY_RSA1:
68
	case KEY_RSA:
69
		if ((rsa = RSA_new()) == NULL)
70
			fatal("key_new: RSA_new failed");
71
		if ((rsa->n = BN_new()) == NULL)
72
			fatal("key_new: BN_new failed");
73
		if ((rsa->e = BN_new()) == NULL)
74
			fatal("key_new: BN_new failed");
75
		k->rsa = rsa;
76
		break;
77
	case KEY_DSA:
78
		if ((dsa = DSA_new()) == NULL)
79
			fatal("key_new: DSA_new failed");
80
		if ((dsa->p = BN_new()) == NULL)
81
			fatal("key_new: BN_new failed");
82
		if ((dsa->q = BN_new()) == NULL)
83
			fatal("key_new: BN_new failed");
84
		if ((dsa->g = BN_new()) == NULL)
85
			fatal("key_new: BN_new failed");
86
		if ((dsa->pub_key = BN_new()) == NULL)
87
			fatal("key_new: BN_new failed");
88
		k->dsa = dsa;
89
		break;
90
	case KEY_UNSPEC:
91
		break;
92
	default:
93
		fatal("key_new: bad key type %d", k->type);
94
		break;
95
	}
96
	return k;
97
}
98
99
Key *
100
key_new_private(int type)
101
{
102
	Key *k = key_new(type);
103
	switch (k->type) {
104
	case KEY_RSA1:
105
	case KEY_RSA:
106
		if ((k->rsa->d = BN_new()) == NULL)
107
			fatal("key_new_private: BN_new failed");
108
		if ((k->rsa->iqmp = BN_new()) == NULL)
109
			fatal("key_new_private: BN_new failed");
110
		if ((k->rsa->q = BN_new()) == NULL)
111
			fatal("key_new_private: BN_new failed");
112
		if ((k->rsa->p = BN_new()) == NULL)
113
			fatal("key_new_private: BN_new failed");
114
		if ((k->rsa->dmq1 = BN_new()) == NULL)
115
			fatal("key_new_private: BN_new failed");
116
		if ((k->rsa->dmp1 = BN_new()) == NULL)
117
			fatal("key_new_private: BN_new failed");
118
		break;
119
	case KEY_DSA:
120
		if ((k->dsa->priv_key = BN_new()) == NULL)
121
			fatal("key_new_private: BN_new failed");
122
		break;
123
	case KEY_UNSPEC:
124
		break;
125
	default:
126
		break;
127
	}
128
	return k;
129
}
130
131
void
132
key_free(Key *k)
133
{
1.13.1 by Colin Watson
Import upstream version 4.6p1
134
	if (k == NULL)
135
		fatal("key_free: key is NULL");
1 by Noah Meyerhans
Import upstream version 3.8.1p1
136
	switch (k->type) {
137
	case KEY_RSA1:
138
	case KEY_RSA:
139
		if (k->rsa != NULL)
140
			RSA_free(k->rsa);
141
		k->rsa = NULL;
142
		break;
143
	case KEY_DSA:
144
		if (k->dsa != NULL)
145
			DSA_free(k->dsa);
146
		k->dsa = NULL;
147
		break;
148
	case KEY_UNSPEC:
149
		break;
150
	default:
151
		fatal("key_free: bad key type %d", k->type);
152
		break;
153
	}
154
	xfree(k);
155
}
156
157
int
158
key_equal(const Key *a, const Key *b)
159
{
160
	if (a == NULL || b == NULL || a->type != b->type)
161
		return 0;
162
	switch (a->type) {
163
	case KEY_RSA1:
164
	case KEY_RSA:
165
		return a->rsa != NULL && b->rsa != NULL &&
166
		    BN_cmp(a->rsa->e, b->rsa->e) == 0 &&
167
		    BN_cmp(a->rsa->n, b->rsa->n) == 0;
168
	case KEY_DSA:
169
		return a->dsa != NULL && b->dsa != NULL &&
170
		    BN_cmp(a->dsa->p, b->dsa->p) == 0 &&
171
		    BN_cmp(a->dsa->q, b->dsa->q) == 0 &&
172
		    BN_cmp(a->dsa->g, b->dsa->g) == 0 &&
173
		    BN_cmp(a->dsa->pub_key, b->dsa->pub_key) == 0;
174
	default:
175
		fatal("key_equal: bad key type %d", a->type);
176
	}
1.13.3 by Colin Watson
Import upstream version 5.1p1
177
	/* NOTREACHED */
1 by Noah Meyerhans
Import upstream version 3.8.1p1
178
}
179
180
u_char*
181
key_fingerprint_raw(const Key *k, enum fp_type dgst_type,
182
    u_int *dgst_raw_length)
183
{
184
	const EVP_MD *md = NULL;
185
	EVP_MD_CTX ctx;
186
	u_char *blob = NULL;
187
	u_char *retval = NULL;
188
	u_int len = 0;
189
	int nlen, elen;
190
191
	*dgst_raw_length = 0;
192
193
	switch (dgst_type) {
194
	case SSH_FP_MD5:
195
		md = EVP_md5();
196
		break;
197
	case SSH_FP_SHA1:
198
		md = EVP_sha1();
199
		break;
200
	default:
201
		fatal("key_fingerprint_raw: bad digest type %d",
202
		    dgst_type);
203
	}
204
	switch (k->type) {
205
	case KEY_RSA1:
206
		nlen = BN_num_bytes(k->rsa->n);
207
		elen = BN_num_bytes(k->rsa->e);
208
		len = nlen + elen;
209
		blob = xmalloc(len);
210
		BN_bn2bin(k->rsa->n, blob);
211
		BN_bn2bin(k->rsa->e, blob + nlen);
212
		break;
213
	case KEY_DSA:
214
	case KEY_RSA:
215
		key_to_blob(k, &blob, &len);
216
		break;
217
	case KEY_UNSPEC:
218
		return retval;
219
	default:
220
		fatal("key_fingerprint_raw: bad key type %d", k->type);
221
		break;
222
	}
223
	if (blob != NULL) {
224
		retval = xmalloc(EVP_MAX_MD_SIZE);
225
		EVP_DigestInit(&ctx, md);
226
		EVP_DigestUpdate(&ctx, blob, len);
227
		EVP_DigestFinal(&ctx, retval, dgst_raw_length);
228
		memset(blob, 0, len);
229
		xfree(blob);
230
	} else {
231
		fatal("key_fingerprint_raw: blob is null");
232
	}
233
	return retval;
234
}
235
236
static char *
237
key_fingerprint_hex(u_char *dgst_raw, u_int dgst_raw_len)
238
{
239
	char *retval;
1.1.3 by Colin Watson
Import upstream version 4.2p1
240
	u_int i;
1 by Noah Meyerhans
Import upstream version 3.8.1p1
241
1.13.1 by Colin Watson
Import upstream version 4.6p1
242
	retval = xcalloc(1, dgst_raw_len * 3 + 1);
1 by Noah Meyerhans
Import upstream version 3.8.1p1
243
	for (i = 0; i < dgst_raw_len; i++) {
244
		char hex[4];
245
		snprintf(hex, sizeof(hex), "%02x:", dgst_raw[i]);
246
		strlcat(retval, hex, dgst_raw_len * 3 + 1);
247
	}
248
249
	/* Remove the trailing ':' character */
250
	retval[(dgst_raw_len * 3) - 1] = '\0';
251
	return retval;
252
}
253
254
static char *
255
key_fingerprint_bubblebabble(u_char *dgst_raw, u_int dgst_raw_len)
256
{
257
	char vowels[] = { 'a', 'e', 'i', 'o', 'u', 'y' };
258
	char consonants[] = { 'b', 'c', 'd', 'f', 'g', 'h', 'k', 'l', 'm',
259
	    'n', 'p', 'r', 's', 't', 'v', 'z', 'x' };
260
	u_int i, j = 0, rounds, seed = 1;
261
	char *retval;
262
263
	rounds = (dgst_raw_len / 2) + 1;
1.13.1 by Colin Watson
Import upstream version 4.6p1
264
	retval = xcalloc((rounds * 6), sizeof(char));
1 by Noah Meyerhans
Import upstream version 3.8.1p1
265
	retval[j++] = 'x';
266
	for (i = 0; i < rounds; i++) {
267
		u_int idx0, idx1, idx2, idx3, idx4;
268
		if ((i + 1 < rounds) || (dgst_raw_len % 2 != 0)) {
269
			idx0 = (((((u_int)(dgst_raw[2 * i])) >> 6) & 3) +
270
			    seed) % 6;
271
			idx1 = (((u_int)(dgst_raw[2 * i])) >> 2) & 15;
272
			idx2 = ((((u_int)(dgst_raw[2 * i])) & 3) +
273
			    (seed / 6)) % 6;
274
			retval[j++] = vowels[idx0];
275
			retval[j++] = consonants[idx1];
276
			retval[j++] = vowels[idx2];
277
			if ((i + 1) < rounds) {
278
				idx3 = (((u_int)(dgst_raw[(2 * i) + 1])) >> 4) & 15;
279
				idx4 = (((u_int)(dgst_raw[(2 * i) + 1]))) & 15;
280
				retval[j++] = consonants[idx3];
281
				retval[j++] = '-';
282
				retval[j++] = consonants[idx4];
283
				seed = ((seed * 5) +
284
				    ((((u_int)(dgst_raw[2 * i])) * 7) +
285
				    ((u_int)(dgst_raw[(2 * i) + 1])))) % 36;
286
			}
287
		} else {
288
			idx0 = seed % 6;
289
			idx1 = 16;
290
			idx2 = seed / 6;
291
			retval[j++] = vowels[idx0];
292
			retval[j++] = consonants[idx1];
293
			retval[j++] = vowels[idx2];
294
		}
295
	}
296
	retval[j++] = 'x';
297
	retval[j++] = '\0';
298
	return retval;
299
}
300
1.13.3 by Colin Watson
Import upstream version 5.1p1
301
/*
302
 * Draw an ASCII-Art representing the fingerprint so human brain can
303
 * profit from its built-in pattern recognition ability.
304
 * This technique is called "random art" and can be found in some
305
 * scientific publications like this original paper:
306
 *
307
 * "Hash Visualization: a New Technique to improve Real-World Security",
308
 * Perrig A. and Song D., 1999, International Workshop on Cryptographic
309
 * Techniques and E-Commerce (CrypTEC '99)
310
 * sparrow.ece.cmu.edu/~adrian/projects/validation/validation.pdf
311
 *
312
 * The subject came up in a talk by Dan Kaminsky, too.
313
 *
314
 * If you see the picture is different, the key is different.
315
 * If the picture looks the same, you still know nothing.
316
 *
317
 * The algorithm used here is a worm crawling over a discrete plane,
318
 * leaving a trace (augmenting the field) everywhere it goes.
319
 * Movement is taken from dgst_raw 2bit-wise.  Bumping into walls
320
 * makes the respective movement vector be ignored for this turn.
321
 * Graphs are not unambiguous, because circles in graphs can be
322
 * walked in either direction.
323
 */
324
325
/*
326
 * Field sizes for the random art.  Have to be odd, so the starting point
327
 * can be in the exact middle of the picture, and FLDBASE should be >=8 .
328
 * Else pictures would be too dense, and drawing the frame would
329
 * fail, too, because the key type would not fit in anymore.
330
 */
331
#define	FLDBASE		8
332
#define	FLDSIZE_Y	(FLDBASE + 1)
333
#define	FLDSIZE_X	(FLDBASE * 2 + 1)
334
static char *
335
key_fingerprint_randomart(u_char *dgst_raw, u_int dgst_raw_len, const Key *k)
336
{
337
	/*
338
	 * Chars to be used after each other every time the worm
339
	 * intersects with itself.  Matter of taste.
340
	 */
341
	char	*augmentation_string = " .o+=*BOX@%&#/^SE";
342
	char	*retval, *p;
343
	u_char	 field[FLDSIZE_X][FLDSIZE_Y];
344
	u_int	 i, b;
345
	int	 x, y;
346
	size_t	 len = strlen(augmentation_string) - 1;
347
348
	retval = xcalloc(1, (FLDSIZE_X + 3) * (FLDSIZE_Y + 2));
349
350
	/* initialize field */
351
	memset(field, 0, FLDSIZE_X * FLDSIZE_Y * sizeof(char));
352
	x = FLDSIZE_X / 2;
353
	y = FLDSIZE_Y / 2;
354
355
	/* process raw key */
356
	for (i = 0; i < dgst_raw_len; i++) {
357
		int input;
358
		/* each byte conveys four 2-bit move commands */
359
		input = dgst_raw[i];
360
		for (b = 0; b < 4; b++) {
361
			/* evaluate 2 bit, rest is shifted later */
362
			x += (input & 0x1) ? 1 : -1;
363
			y += (input & 0x2) ? 1 : -1;
364
365
			/* assure we are still in bounds */
366
			x = MAX(x, 0);
367
			y = MAX(y, 0);
368
			x = MIN(x, FLDSIZE_X - 1);
369
			y = MIN(y, FLDSIZE_Y - 1);
370
371
			/* augment the field */
1.13.4 by Colin Watson
Import upstream version 5.2p1
372
			if (field[x][y] < len - 2)
373
				field[x][y]++;
1.13.3 by Colin Watson
Import upstream version 5.1p1
374
			input = input >> 2;
375
		}
376
	}
377
378
	/* mark starting point and end point*/
379
	field[FLDSIZE_X / 2][FLDSIZE_Y / 2] = len - 1;
380
	field[x][y] = len;
381
382
	/* fill in retval */
383
	snprintf(retval, FLDSIZE_X, "+--[%4s %4u]", key_type(k), key_size(k));
384
	p = strchr(retval, '\0');
385
386
	/* output upper border */
387
	for (i = p - retval - 1; i < FLDSIZE_X; i++)
388
		*p++ = '-';
389
	*p++ = '+';
390
	*p++ = '\n';
391
392
	/* output content */
393
	for (y = 0; y < FLDSIZE_Y; y++) {
394
		*p++ = '|';
395
		for (x = 0; x < FLDSIZE_X; x++)
396
			*p++ = augmentation_string[MIN(field[x][y], len)];
397
		*p++ = '|';
398
		*p++ = '\n';
399
	}
400
401
	/* output lower border */
402
	*p++ = '+';
403
	for (i = 0; i < FLDSIZE_X; i++)
404
		*p++ = '-';
405
	*p++ = '+';
406
407
	return retval;
408
}
409
1 by Noah Meyerhans
Import upstream version 3.8.1p1
410
char *
411
key_fingerprint(const Key *k, enum fp_type dgst_type, enum fp_rep dgst_rep)
412
{
413
	char *retval = NULL;
414
	u_char *dgst_raw;
415
	u_int dgst_raw_len;
416
417
	dgst_raw = key_fingerprint_raw(k, dgst_type, &dgst_raw_len);
418
	if (!dgst_raw)
419
		fatal("key_fingerprint: null from key_fingerprint_raw()");
420
	switch (dgst_rep) {
421
	case SSH_FP_HEX:
422
		retval = key_fingerprint_hex(dgst_raw, dgst_raw_len);
423
		break;
424
	case SSH_FP_BUBBLEBABBLE:
425
		retval = key_fingerprint_bubblebabble(dgst_raw, dgst_raw_len);
426
		break;
1.13.3 by Colin Watson
Import upstream version 5.1p1
427
	case SSH_FP_RANDOMART:
428
		retval = key_fingerprint_randomart(dgst_raw, dgst_raw_len, k);
429
		break;
1 by Noah Meyerhans
Import upstream version 3.8.1p1
430
	default:
1.13.4 by Colin Watson
Import upstream version 5.2p1
431
		fatal("key_fingerprint: bad digest representation %d",
1 by Noah Meyerhans
Import upstream version 3.8.1p1
432
		    dgst_rep);
433
		break;
434
	}
435
	memset(dgst_raw, 0, dgst_raw_len);
436
	xfree(dgst_raw);
437
	return retval;
438
}
439
440
/*
441
 * Reads a multiple-precision integer in decimal from the buffer, and advances
442
 * the pointer.  The integer must already be initialized.  This function is
443
 * permitted to modify the buffer.  This leaves *cpp to point just beyond the
444
 * last processed (and maybe modified) character.  Note that this may modify
445
 * the buffer containing the number.
446
 */
447
static int
448
read_bignum(char **cpp, BIGNUM * value)
449
{
450
	char *cp = *cpp;
451
	int old;
452
453
	/* Skip any leading whitespace. */
454
	for (; *cp == ' ' || *cp == '\t'; cp++)
455
		;
456
457
	/* Check that it begins with a decimal digit. */
458
	if (*cp < '0' || *cp > '9')
459
		return 0;
460
461
	/* Save starting position. */
462
	*cpp = cp;
463
464
	/* Move forward until all decimal digits skipped. */
465
	for (; *cp >= '0' && *cp <= '9'; cp++)
466
		;
467
468
	/* Save the old terminating character, and replace it by \0. */
469
	old = *cp;
470
	*cp = 0;
471
472
	/* Parse the number. */
473
	if (BN_dec2bn(&value, *cpp) == 0)
474
		return 0;
475
476
	/* Restore old terminating character. */
477
	*cp = old;
478
479
	/* Move beyond the number and return success. */
480
	*cpp = cp;
481
	return 1;
482
}
483
484
static int
485
write_bignum(FILE *f, BIGNUM *num)
486
{
487
	char *buf = BN_bn2dec(num);
488
	if (buf == NULL) {
489
		error("write_bignum: BN_bn2dec() failed");
490
		return 0;
491
	}
492
	fprintf(f, " %s", buf);
493
	OPENSSL_free(buf);
494
	return 1;
495
}
496
497
/* returns 1 ok, -1 error */
498
int
499
key_read(Key *ret, char **cpp)
500
{
501
	Key *k;
502
	int success = -1;
503
	char *cp, *space;
504
	int len, n, type;
505
	u_int bits;
506
	u_char *blob;
507
508
	cp = *cpp;
509
510
	switch (ret->type) {
511
	case KEY_RSA1:
512
		/* Get number of bits. */
513
		if (*cp < '0' || *cp > '9')
514
			return -1;	/* Bad bit count... */
515
		for (bits = 0; *cp >= '0' && *cp <= '9'; cp++)
516
			bits = 10 * bits + *cp - '0';
517
		if (bits == 0)
518
			return -1;
519
		*cpp = cp;
520
		/* Get public exponent, public modulus. */
521
		if (!read_bignum(cpp, ret->rsa->e))
522
			return -1;
523
		if (!read_bignum(cpp, ret->rsa->n))
524
			return -1;
525
		success = 1;
526
		break;
527
	case KEY_UNSPEC:
528
	case KEY_RSA:
529
	case KEY_DSA:
530
		space = strchr(cp, ' ');
531
		if (space == NULL) {
532
			debug3("key_read: missing whitespace");
533
			return -1;
534
		}
535
		*space = '\0';
536
		type = key_type_from_name(cp);
537
		*space = ' ';
538
		if (type == KEY_UNSPEC) {
539
			debug3("key_read: missing keytype");
540
			return -1;
541
		}
542
		cp = space+1;
543
		if (*cp == '\0') {
544
			debug3("key_read: short string");
545
			return -1;
546
		}
547
		if (ret->type == KEY_UNSPEC) {
548
			ret->type = type;
549
		} else if (ret->type != type) {
550
			/* is a key, but different type */
551
			debug3("key_read: type mismatch");
552
			return -1;
553
		}
554
		len = 2*strlen(cp);
555
		blob = xmalloc(len);
556
		n = uudecode(cp, blob, len);
557
		if (n < 0) {
558
			error("key_read: uudecode %s failed", cp);
559
			xfree(blob);
560
			return -1;
561
		}
562
		k = key_from_blob(blob, (u_int)n);
563
		xfree(blob);
564
		if (k == NULL) {
565
			error("key_read: key_from_blob %s failed", cp);
566
			return -1;
567
		}
568
		if (k->type != type) {
569
			error("key_read: type mismatch: encoding error");
570
			key_free(k);
571
			return -1;
572
		}
573
/*XXXX*/
574
		if (ret->type == KEY_RSA) {
575
			if (ret->rsa != NULL)
576
				RSA_free(ret->rsa);
577
			ret->rsa = k->rsa;
578
			k->rsa = NULL;
579
			success = 1;
580
#ifdef DEBUG_PK
581
			RSA_print_fp(stderr, ret->rsa, 8);
582
#endif
583
		} else {
584
			if (ret->dsa != NULL)
585
				DSA_free(ret->dsa);
586
			ret->dsa = k->dsa;
587
			k->dsa = NULL;
588
			success = 1;
589
#ifdef DEBUG_PK
590
			DSA_print_fp(stderr, ret->dsa, 8);
591
#endif
592
		}
593
/*XXXX*/
594
		key_free(k);
595
		if (success != 1)
596
			break;
597
		/* advance cp: skip whitespace and data */
598
		while (*cp == ' ' || *cp == '\t')
599
			cp++;
600
		while (*cp != '\0' && *cp != ' ' && *cp != '\t')
601
			cp++;
602
		*cpp = cp;
603
		break;
604
	default:
605
		fatal("key_read: bad key type: %d", ret->type);
606
		break;
607
	}
608
	return success;
609
}
610
611
int
612
key_write(const Key *key, FILE *f)
613
{
614
	int n, success = 0;
615
	u_int len, bits = 0;
616
	u_char *blob;
617
	char *uu;
618
619
	if (key->type == KEY_RSA1 && key->rsa != NULL) {
620
		/* size of modulus 'n' */
621
		bits = BN_num_bits(key->rsa->n);
622
		fprintf(f, "%u", bits);
623
		if (write_bignum(f, key->rsa->e) &&
624
		    write_bignum(f, key->rsa->n)) {
625
			success = 1;
626
		} else {
627
			error("key_write: failed for RSA key");
628
		}
629
	} else if ((key->type == KEY_DSA && key->dsa != NULL) ||
630
	    (key->type == KEY_RSA && key->rsa != NULL)) {
631
		key_to_blob(key, &blob, &len);
632
		uu = xmalloc(2*len);
633
		n = uuencode(blob, len, uu, 2*len);
634
		if (n > 0) {
635
			fprintf(f, "%s %s", key_ssh_name(key), uu);
636
			success = 1;
637
		}
638
		xfree(blob);
639
		xfree(uu);
640
	}
641
	return success;
642
}
643
644
const char *
645
key_type(const Key *k)
646
{
647
	switch (k->type) {
648
	case KEY_RSA1:
649
		return "RSA1";
650
	case KEY_RSA:
651
		return "RSA";
652
	case KEY_DSA:
653
		return "DSA";
654
	}
655
	return "unknown";
656
}
657
658
const char *
659
key_ssh_name(const Key *k)
660
{
661
	switch (k->type) {
662
	case KEY_RSA:
663
		return "ssh-rsa";
664
	case KEY_DSA:
665
		return "ssh-dss";
666
	}
667
	return "ssh-unknown";
668
}
669
670
u_int
671
key_size(const Key *k)
672
{
673
	switch (k->type) {
674
	case KEY_RSA1:
675
	case KEY_RSA:
676
		return BN_num_bits(k->rsa->n);
677
	case KEY_DSA:
678
		return BN_num_bits(k->dsa->p);
679
	}
680
	return 0;
681
}
682
683
static RSA *
684
rsa_generate_private_key(u_int bits)
685
{
686
	RSA *private;
1.13.1 by Colin Watson
Import upstream version 4.6p1
687
1 by Noah Meyerhans
Import upstream version 3.8.1p1
688
	private = RSA_generate_key(bits, 35, NULL, NULL);
689
	if (private == NULL)
690
		fatal("rsa_generate_private_key: key generation failed.");
691
	return private;
692
}
693
694
static DSA*
695
dsa_generate_private_key(u_int bits)
696
{
697
	DSA *private = DSA_generate_parameters(bits, NULL, 0, NULL, NULL, NULL, NULL);
1.13.1 by Colin Watson
Import upstream version 4.6p1
698
1 by Noah Meyerhans
Import upstream version 3.8.1p1
699
	if (private == NULL)
700
		fatal("dsa_generate_private_key: DSA_generate_parameters failed");
701
	if (!DSA_generate_key(private))
702
		fatal("dsa_generate_private_key: DSA_generate_key failed.");
703
	if (private == NULL)
704
		fatal("dsa_generate_private_key: NULL.");
705
	return private;
706
}
707
708
Key *
709
key_generate(int type, u_int bits)
710
{
711
	Key *k = key_new(KEY_UNSPEC);
712
	switch (type) {
713
	case KEY_DSA:
714
		k->dsa = dsa_generate_private_key(bits);
715
		break;
716
	case KEY_RSA:
717
	case KEY_RSA1:
718
		k->rsa = rsa_generate_private_key(bits);
719
		break;
720
	default:
721
		fatal("key_generate: unknown type %d", type);
722
	}
723
	k->type = type;
724
	return k;
725
}
726
727
Key *
728
key_from_private(const Key *k)
729
{
730
	Key *n = NULL;
731
	switch (k->type) {
732
	case KEY_DSA:
733
		n = key_new(k->type);
1.13.1 by Colin Watson
Import upstream version 4.6p1
734
		if ((BN_copy(n->dsa->p, k->dsa->p) == NULL) ||
735
		    (BN_copy(n->dsa->q, k->dsa->q) == NULL) ||
736
		    (BN_copy(n->dsa->g, k->dsa->g) == NULL) ||
737
		    (BN_copy(n->dsa->pub_key, k->dsa->pub_key) == NULL))
738
			fatal("key_from_private: BN_copy failed");
1 by Noah Meyerhans
Import upstream version 3.8.1p1
739
		break;
740
	case KEY_RSA:
741
	case KEY_RSA1:
742
		n = key_new(k->type);
1.13.1 by Colin Watson
Import upstream version 4.6p1
743
		if ((BN_copy(n->rsa->n, k->rsa->n) == NULL) ||
744
		    (BN_copy(n->rsa->e, k->rsa->e) == NULL))
745
			fatal("key_from_private: BN_copy failed");
1 by Noah Meyerhans
Import upstream version 3.8.1p1
746
		break;
747
	default:
748
		fatal("key_from_private: unknown type %d", k->type);
749
		break;
750
	}
751
	return n;
752
}
753
754
int
755
key_type_from_name(char *name)
756
{
757
	if (strcmp(name, "rsa1") == 0) {
758
		return KEY_RSA1;
759
	} else if (strcmp(name, "rsa") == 0) {
760
		return KEY_RSA;
761
	} else if (strcmp(name, "dsa") == 0) {
762
		return KEY_DSA;
763
	} else if (strcmp(name, "ssh-rsa") == 0) {
764
		return KEY_RSA;
765
	} else if (strcmp(name, "ssh-dss") == 0) {
766
		return KEY_DSA;
5 by Colin Watson
Resynchronise with Debian.
767
	} else if (strcmp(name, "null") == 0) {
768
		return KEY_NULL;
1 by Noah Meyerhans
Import upstream version 3.8.1p1
769
	}
770
	debug2("key_type_from_name: unknown key type '%s'", name);
771
	return KEY_UNSPEC;
772
}
773
774
int
775
key_names_valid2(const char *names)
776
{
777
	char *s, *cp, *p;
778
779
	if (names == NULL || strcmp(names, "") == 0)
780
		return 0;
781
	s = cp = xstrdup(names);
782
	for ((p = strsep(&cp, ",")); p && *p != '\0';
783
	    (p = strsep(&cp, ","))) {
784
		switch (key_type_from_name(p)) {
785
		case KEY_RSA1:
786
		case KEY_UNSPEC:
787
			xfree(s);
788
			return 0;
789
		}
790
	}
791
	debug3("key names ok: [%s]", names);
792
	xfree(s);
793
	return 1;
794
}
795
796
Key *
797
key_from_blob(const u_char *blob, u_int blen)
798
{
799
	Buffer b;
800
	int rlen, type;
1.1.2 by Colin Watson
Import upstream version 4.1p1
801
	char *ktype = NULL;
1 by Noah Meyerhans
Import upstream version 3.8.1p1
802
	Key *key = NULL;
803
804
#ifdef DEBUG_PK
805
	dump_base64(stderr, blob, blen);
806
#endif
807
	buffer_init(&b);
808
	buffer_append(&b, blob, blen);
1.1.2 by Colin Watson
Import upstream version 4.1p1
809
	if ((ktype = buffer_get_string_ret(&b, NULL)) == NULL) {
810
		error("key_from_blob: can't read key type");
811
		goto out;
812
	}
813
1 by Noah Meyerhans
Import upstream version 3.8.1p1
814
	type = key_type_from_name(ktype);
815
816
	switch (type) {
817
	case KEY_RSA:
818
		key = key_new(type);
1.1.2 by Colin Watson
Import upstream version 4.1p1
819
		if (buffer_get_bignum2_ret(&b, key->rsa->e) == -1 ||
820
		    buffer_get_bignum2_ret(&b, key->rsa->n) == -1) {
821
			error("key_from_blob: can't read rsa key");
822
			key_free(key);
823
			key = NULL;
824
			goto out;
825
		}
1 by Noah Meyerhans
Import upstream version 3.8.1p1
826
#ifdef DEBUG_PK
827
		RSA_print_fp(stderr, key->rsa, 8);
828
#endif
829
		break;
830
	case KEY_DSA:
831
		key = key_new(type);
1.1.2 by Colin Watson
Import upstream version 4.1p1
832
		if (buffer_get_bignum2_ret(&b, key->dsa->p) == -1 ||
833
		    buffer_get_bignum2_ret(&b, key->dsa->q) == -1 ||
834
		    buffer_get_bignum2_ret(&b, key->dsa->g) == -1 ||
835
		    buffer_get_bignum2_ret(&b, key->dsa->pub_key) == -1) {
836
			error("key_from_blob: can't read dsa key");
837
			key_free(key);
838
			key = NULL;
839
			goto out;
840
		}
1 by Noah Meyerhans
Import upstream version 3.8.1p1
841
#ifdef DEBUG_PK
842
		DSA_print_fp(stderr, key->dsa, 8);
843
#endif
844
		break;
845
	case KEY_UNSPEC:
846
		key = key_new(type);
847
		break;
848
	default:
849
		error("key_from_blob: cannot handle type %s", ktype);
1.1.2 by Colin Watson
Import upstream version 4.1p1
850
		goto out;
1 by Noah Meyerhans
Import upstream version 3.8.1p1
851
	}
852
	rlen = buffer_len(&b);
853
	if (key != NULL && rlen != 0)
854
		error("key_from_blob: remaining bytes in key blob %d", rlen);
1.1.2 by Colin Watson
Import upstream version 4.1p1
855
 out:
856
	if (ktype != NULL)
857
		xfree(ktype);
1 by Noah Meyerhans
Import upstream version 3.8.1p1
858
	buffer_free(&b);
859
	return key;
860
}
861
862
int
863
key_to_blob(const Key *key, u_char **blobp, u_int *lenp)
864
{
865
	Buffer b;
866
	int len;
867
868
	if (key == NULL) {
869
		error("key_to_blob: key == NULL");
870
		return 0;
871
	}
872
	buffer_init(&b);
873
	switch (key->type) {
874
	case KEY_DSA:
875
		buffer_put_cstring(&b, key_ssh_name(key));
876
		buffer_put_bignum2(&b, key->dsa->p);
877
		buffer_put_bignum2(&b, key->dsa->q);
878
		buffer_put_bignum2(&b, key->dsa->g);
879
		buffer_put_bignum2(&b, key->dsa->pub_key);
880
		break;
881
	case KEY_RSA:
882
		buffer_put_cstring(&b, key_ssh_name(key));
883
		buffer_put_bignum2(&b, key->rsa->e);
884
		buffer_put_bignum2(&b, key->rsa->n);
885
		break;
886
	default:
887
		error("key_to_blob: unsupported key type %d", key->type);
888
		buffer_free(&b);
889
		return 0;
890
	}
891
	len = buffer_len(&b);
892
	if (lenp != NULL)
893
		*lenp = len;
894
	if (blobp != NULL) {
895
		*blobp = xmalloc(len);
896
		memcpy(*blobp, buffer_ptr(&b), len);
897
	}
898
	memset(buffer_ptr(&b), 0, len);
899
	buffer_free(&b);
900
	return len;
901
}
902
903
int
904
key_sign(
905
    const Key *key,
906
    u_char **sigp, u_int *lenp,
907
    const u_char *data, u_int datalen)
908
{
909
	switch (key->type) {
910
	case KEY_DSA:
911
		return ssh_dss_sign(key, sigp, lenp, data, datalen);
912
	case KEY_RSA:
913
		return ssh_rsa_sign(key, sigp, lenp, data, datalen);
914
	default:
1.1.1 by Colin Watson
Import upstream version 3.9p1
915
		error("key_sign: invalid key type %d", key->type);
1 by Noah Meyerhans
Import upstream version 3.8.1p1
916
		return -1;
917
	}
918
}
919
920
/*
921
 * key_verify returns 1 for a correct signature, 0 for an incorrect signature
922
 * and -1 on error.
923
 */
924
int
925
key_verify(
926
    const Key *key,
927
    const u_char *signature, u_int signaturelen,
928
    const u_char *data, u_int datalen)
929
{
930
	if (signaturelen == 0)
931
		return -1;
932
933
	switch (key->type) {
934
	case KEY_DSA:
935
		return ssh_dss_verify(key, signature, signaturelen, data, datalen);
936
	case KEY_RSA:
937
		return ssh_rsa_verify(key, signature, signaturelen, data, datalen);
938
	default:
1.1.1 by Colin Watson
Import upstream version 3.9p1
939
		error("key_verify: invalid key type %d", key->type);
1 by Noah Meyerhans
Import upstream version 3.8.1p1
940
		return -1;
941
	}
942
}
943
944
/* Converts a private to a public key */
945
Key *
946
key_demote(const Key *k)
947
{
948
	Key *pk;
949
1.13.1 by Colin Watson
Import upstream version 4.6p1
950
	pk = xcalloc(1, sizeof(*pk));
1 by Noah Meyerhans
Import upstream version 3.8.1p1
951
	pk->type = k->type;
952
	pk->flags = k->flags;
953
	pk->dsa = NULL;
954
	pk->rsa = NULL;
955
956
	switch (k->type) {
957
	case KEY_RSA1:
958
	case KEY_RSA:
959
		if ((pk->rsa = RSA_new()) == NULL)
960
			fatal("key_demote: RSA_new failed");
961
		if ((pk->rsa->e = BN_dup(k->rsa->e)) == NULL)
962
			fatal("key_demote: BN_dup failed");
963
		if ((pk->rsa->n = BN_dup(k->rsa->n)) == NULL)
964
			fatal("key_demote: BN_dup failed");
965
		break;
966
	case KEY_DSA:
967
		if ((pk->dsa = DSA_new()) == NULL)
968
			fatal("key_demote: DSA_new failed");
969
		if ((pk->dsa->p = BN_dup(k->dsa->p)) == NULL)
970
			fatal("key_demote: BN_dup failed");
971
		if ((pk->dsa->q = BN_dup(k->dsa->q)) == NULL)
972
			fatal("key_demote: BN_dup failed");
973
		if ((pk->dsa->g = BN_dup(k->dsa->g)) == NULL)
974
			fatal("key_demote: BN_dup failed");
975
		if ((pk->dsa->pub_key = BN_dup(k->dsa->pub_key)) == NULL)
976
			fatal("key_demote: BN_dup failed");
977
		break;
978
	default:
979
		fatal("key_free: bad key type %d", k->type);
980
		break;
981
	}
982
983
	return (pk);
984
}