xref: /openbsd-src/usr.bin/ssh/ssh-keygen.c (revision f6b75673f6c960a9743bfd16c1e52dd100265c68)
1 /* $OpenBSD: ssh-keygen.c,v 1.323 2018/10/19 03:12:42 djm Exp $ */
2 /*
3  * Author: Tatu Ylonen <ylo@cs.hut.fi>
4  * Copyright (c) 1994 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
5  *                    All rights reserved
6  * Identity and host key generation and maintenance.
7  *
8  * As far as I am concerned, the code I have written for this software
9  * can be used freely for any purpose.  Any derived versions of this
10  * software must be clearly marked as such, and if the derived work is
11  * incompatible with the protocol description in the RFC file, it must be
12  * called by a name other than "ssh" or "Secure Shell".
13  */
14 
15 #include <sys/types.h>
16 #include <sys/socket.h>
17 #include <sys/stat.h>
18 
19 #include <openssl/evp.h>
20 #include <openssl/pem.h>
21 
22 #include <errno.h>
23 #include <fcntl.h>
24 #include <netdb.h>
25 #include <pwd.h>
26 #include <stdio.h>
27 #include <stdlib.h>
28 #include <string.h>
29 #include <unistd.h>
30 #include <limits.h>
31 #include <locale.h>
32 
33 #include "xmalloc.h"
34 #include "sshkey.h"
35 #include "authfile.h"
36 #include "uuencode.h"
37 #include "sshbuf.h"
38 #include "pathnames.h"
39 #include "log.h"
40 #include "misc.h"
41 #include "match.h"
42 #include "hostfile.h"
43 #include "dns.h"
44 #include "ssh.h"
45 #include "ssh2.h"
46 #include "ssherr.h"
47 #include "atomicio.h"
48 #include "krl.h"
49 #include "digest.h"
50 #include "utf8.h"
51 #include "authfd.h"
52 
53 #ifdef ENABLE_PKCS11
54 #include "ssh-pkcs11.h"
55 #endif
56 
57 #ifdef WITH_OPENSSL
58 # define DEFAULT_KEY_TYPE_NAME "rsa"
59 #else
60 # define DEFAULT_KEY_TYPE_NAME "ed25519"
61 #endif
62 
63 /* Number of bits in the RSA/DSA key.  This value can be set on the command line. */
64 #define DEFAULT_BITS		2048
65 #define DEFAULT_BITS_DSA	1024
66 #define DEFAULT_BITS_ECDSA	256
67 u_int32_t bits = 0;
68 
69 /*
70  * Flag indicating that we just want to change the passphrase.  This can be
71  * set on the command line.
72  */
73 int change_passphrase = 0;
74 
75 /*
76  * Flag indicating that we just want to change the comment.  This can be set
77  * on the command line.
78  */
79 int change_comment = 0;
80 
81 int quiet = 0;
82 
83 int log_level = SYSLOG_LEVEL_INFO;
84 
85 /* Flag indicating that we want to hash a known_hosts file */
86 int hash_hosts = 0;
87 /* Flag indicating that we want lookup a host in known_hosts file */
88 int find_host = 0;
89 /* Flag indicating that we want to delete a host from a known_hosts file */
90 int delete_host = 0;
91 
92 /* Flag indicating that we want to show the contents of a certificate */
93 int show_cert = 0;
94 
95 /* Flag indicating that we just want to see the key fingerprint */
96 int print_fingerprint = 0;
97 int print_bubblebabble = 0;
98 
99 /* Hash algorithm to use for fingerprints. */
100 int fingerprint_hash = SSH_FP_HASH_DEFAULT;
101 
102 /* The identity file name, given on the command line or entered by the user. */
103 char identity_file[1024];
104 int have_identity = 0;
105 
106 /* This is set to the passphrase if given on the command line. */
107 char *identity_passphrase = NULL;
108 
109 /* This is set to the new passphrase if given on the command line. */
110 char *identity_new_passphrase = NULL;
111 
112 /* This is set to the new comment if given on the command line. */
113 char *identity_comment = NULL;
114 
115 /* Path to CA key when certifying keys. */
116 char *ca_key_path = NULL;
117 
118 /* Prefer to use agent keys for CA signing */
119 int prefer_agent = 0;
120 
121 /* Certificate serial number */
122 unsigned long long cert_serial = 0;
123 
124 /* Key type when certifying */
125 u_int cert_key_type = SSH2_CERT_TYPE_USER;
126 
127 /* "key ID" of signed key */
128 char *cert_key_id = NULL;
129 
130 /* Comma-separated list of principal names for certifying keys */
131 char *cert_principals = NULL;
132 
133 /* Validity period for certificates */
134 u_int64_t cert_valid_from = 0;
135 u_int64_t cert_valid_to = ~0ULL;
136 
137 /* Certificate options */
138 #define CERTOPT_X_FWD	(1)
139 #define CERTOPT_AGENT_FWD	(1<<1)
140 #define CERTOPT_PORT_FWD	(1<<2)
141 #define CERTOPT_PTY		(1<<3)
142 #define CERTOPT_USER_RC	(1<<4)
143 #define CERTOPT_DEFAULT	(CERTOPT_X_FWD|CERTOPT_AGENT_FWD| \
144 			 CERTOPT_PORT_FWD|CERTOPT_PTY|CERTOPT_USER_RC)
145 u_int32_t certflags_flags = CERTOPT_DEFAULT;
146 char *certflags_command = NULL;
147 char *certflags_src_addr = NULL;
148 
149 /* Arbitrary extensions specified by user */
150 struct cert_userext {
151 	char *key;
152 	char *val;
153 	int crit;
154 };
155 struct cert_userext *cert_userext;
156 size_t ncert_userext;
157 
158 /* Conversion to/from various formats */
159 int convert_to = 0;
160 int convert_from = 0;
161 enum {
162 	FMT_RFC4716,
163 	FMT_PKCS8,
164 	FMT_PEM
165 } convert_format = FMT_RFC4716;
166 int print_public = 0;
167 int print_generic = 0;
168 
169 char *key_type_name = NULL;
170 
171 /* Load key from this PKCS#11 provider */
172 char *pkcs11provider = NULL;
173 
174 /* Use new OpenSSH private key format when writing SSH2 keys instead of PEM */
175 int use_new_format = 1;
176 
177 /* Cipher for new-format private keys */
178 char *new_format_cipher = NULL;
179 
180 /*
181  * Number of KDF rounds to derive new format keys /
182  * number of primality trials when screening moduli.
183  */
184 int rounds = 0;
185 
186 /* argv0 */
187 extern char *__progname;
188 
189 char hostname[NI_MAXHOST];
190 
191 #ifdef WITH_OPENSSL
192 /* moduli.c */
193 int gen_candidates(FILE *, u_int32_t, u_int32_t, BIGNUM *);
194 int prime_test(FILE *, FILE *, u_int32_t, u_int32_t, char *, unsigned long,
195     unsigned long);
196 #endif
197 
198 static void
199 type_bits_valid(int type, const char *name, u_int32_t *bitsp)
200 {
201 #ifdef WITH_OPENSSL
202 	u_int maxbits, nid;
203 #endif
204 
205 	if (type == KEY_UNSPEC)
206 		fatal("unknown key type %s", key_type_name);
207 	if (*bitsp == 0) {
208 #ifdef WITH_OPENSSL
209 		if (type == KEY_DSA)
210 			*bitsp = DEFAULT_BITS_DSA;
211 		else if (type == KEY_ECDSA) {
212 			if (name != NULL &&
213 			    (nid = sshkey_ecdsa_nid_from_name(name)) > 0)
214 				*bitsp = sshkey_curve_nid_to_bits(nid);
215 			if (*bitsp == 0)
216 				*bitsp = DEFAULT_BITS_ECDSA;
217 		} else
218 #endif
219 			*bitsp = DEFAULT_BITS;
220 	}
221 #ifdef WITH_OPENSSL
222 	maxbits = (type == KEY_DSA) ?
223 	    OPENSSL_DSA_MAX_MODULUS_BITS : OPENSSL_RSA_MAX_MODULUS_BITS;
224 	if (*bitsp > maxbits)
225 		fatal("key bits exceeds maximum %d", maxbits);
226 	switch (type) {
227 	case KEY_DSA:
228 		if (*bitsp != 1024)
229 			fatal("Invalid DSA key length: must be 1024 bits");
230 		break;
231 	case KEY_RSA:
232 		if (*bitsp < SSH_RSA_MINIMUM_MODULUS_SIZE)
233 			fatal("Invalid RSA key length: minimum is %d bits",
234 			    SSH_RSA_MINIMUM_MODULUS_SIZE);
235 		break;
236 	case KEY_ECDSA:
237 		if (sshkey_ecdsa_bits_to_nid(*bitsp) == -1)
238 			fatal("Invalid ECDSA key length: valid lengths are "
239 			    "256, 384 or 521 bits");
240 	}
241 #endif
242 }
243 
244 static void
245 ask_filename(struct passwd *pw, const char *prompt)
246 {
247 	char buf[1024];
248 	char *name = NULL;
249 
250 	if (key_type_name == NULL)
251 		name = _PATH_SSH_CLIENT_ID_RSA;
252 	else {
253 		switch (sshkey_type_from_name(key_type_name)) {
254 		case KEY_DSA_CERT:
255 		case KEY_DSA:
256 			name = _PATH_SSH_CLIENT_ID_DSA;
257 			break;
258 		case KEY_ECDSA_CERT:
259 		case KEY_ECDSA:
260 			name = _PATH_SSH_CLIENT_ID_ECDSA;
261 			break;
262 		case KEY_RSA_CERT:
263 		case KEY_RSA:
264 			name = _PATH_SSH_CLIENT_ID_RSA;
265 			break;
266 		case KEY_ED25519:
267 		case KEY_ED25519_CERT:
268 			name = _PATH_SSH_CLIENT_ID_ED25519;
269 			break;
270 		case KEY_XMSS:
271 		case KEY_XMSS_CERT:
272 			name = _PATH_SSH_CLIENT_ID_XMSS;
273 			break;
274 		default:
275 			fatal("bad key type");
276 		}
277 	}
278 	snprintf(identity_file, sizeof(identity_file),
279 	    "%s/%s", pw->pw_dir, name);
280 	printf("%s (%s): ", prompt, identity_file);
281 	fflush(stdout);
282 	if (fgets(buf, sizeof(buf), stdin) == NULL)
283 		exit(1);
284 	buf[strcspn(buf, "\n")] = '\0';
285 	if (strcmp(buf, "") != 0)
286 		strlcpy(identity_file, buf, sizeof(identity_file));
287 	have_identity = 1;
288 }
289 
290 static struct sshkey *
291 load_identity(char *filename)
292 {
293 	char *pass;
294 	struct sshkey *prv;
295 	int r;
296 
297 	if ((r = sshkey_load_private(filename, "", &prv, NULL)) == 0)
298 		return prv;
299 	if (r != SSH_ERR_KEY_WRONG_PASSPHRASE)
300 		fatal("Load key \"%s\": %s", filename, ssh_err(r));
301 	if (identity_passphrase)
302 		pass = xstrdup(identity_passphrase);
303 	else
304 		pass = read_passphrase("Enter passphrase: ", RP_ALLOW_STDIN);
305 	r = sshkey_load_private(filename, pass, &prv, NULL);
306 	explicit_bzero(pass, strlen(pass));
307 	free(pass);
308 	if (r != 0)
309 		fatal("Load key \"%s\": %s", filename, ssh_err(r));
310 	return prv;
311 }
312 
313 #define SSH_COM_PUBLIC_BEGIN		"---- BEGIN SSH2 PUBLIC KEY ----"
314 #define SSH_COM_PUBLIC_END		"---- END SSH2 PUBLIC KEY ----"
315 #define SSH_COM_PRIVATE_BEGIN		"---- BEGIN SSH2 ENCRYPTED PRIVATE KEY ----"
316 #define	SSH_COM_PRIVATE_KEY_MAGIC	0x3f6ff9eb
317 
318 #ifdef WITH_OPENSSL
319 static void
320 do_convert_to_ssh2(struct passwd *pw, struct sshkey *k)
321 {
322 	size_t len;
323 	u_char *blob;
324 	char comment[61];
325 	int r;
326 
327 	if ((r = sshkey_to_blob(k, &blob, &len)) != 0)
328 		fatal("key_to_blob failed: %s", ssh_err(r));
329 	/* Comment + surrounds must fit into 72 chars (RFC 4716 sec 3.3) */
330 	snprintf(comment, sizeof(comment),
331 	    "%u-bit %s, converted by %s@%s from OpenSSH",
332 	    sshkey_size(k), sshkey_type(k),
333 	    pw->pw_name, hostname);
334 
335 	fprintf(stdout, "%s\n", SSH_COM_PUBLIC_BEGIN);
336 	fprintf(stdout, "Comment: \"%s\"\n", comment);
337 	dump_base64(stdout, blob, len);
338 	fprintf(stdout, "%s\n", SSH_COM_PUBLIC_END);
339 	sshkey_free(k);
340 	free(blob);
341 	exit(0);
342 }
343 
344 static void
345 do_convert_to_pkcs8(struct sshkey *k)
346 {
347 	switch (sshkey_type_plain(k->type)) {
348 	case KEY_RSA:
349 		if (!PEM_write_RSA_PUBKEY(stdout, k->rsa))
350 			fatal("PEM_write_RSA_PUBKEY failed");
351 		break;
352 	case KEY_DSA:
353 		if (!PEM_write_DSA_PUBKEY(stdout, k->dsa))
354 			fatal("PEM_write_DSA_PUBKEY failed");
355 		break;
356 	case KEY_ECDSA:
357 		if (!PEM_write_EC_PUBKEY(stdout, k->ecdsa))
358 			fatal("PEM_write_EC_PUBKEY failed");
359 		break;
360 	default:
361 		fatal("%s: unsupported key type %s", __func__, sshkey_type(k));
362 	}
363 	exit(0);
364 }
365 
366 static void
367 do_convert_to_pem(struct sshkey *k)
368 {
369 	switch (sshkey_type_plain(k->type)) {
370 	case KEY_RSA:
371 		if (!PEM_write_RSAPublicKey(stdout, k->rsa))
372 			fatal("PEM_write_RSAPublicKey failed");
373 		break;
374 	default:
375 		fatal("%s: unsupported key type %s", __func__, sshkey_type(k));
376 	}
377 	exit(0);
378 }
379 
380 static void
381 do_convert_to(struct passwd *pw)
382 {
383 	struct sshkey *k;
384 	struct stat st;
385 	int r;
386 
387 	if (!have_identity)
388 		ask_filename(pw, "Enter file in which the key is");
389 	if (stat(identity_file, &st) < 0)
390 		fatal("%s: %s: %s", __progname, identity_file, strerror(errno));
391 	if ((r = sshkey_load_public(identity_file, &k, NULL)) != 0)
392 		k = load_identity(identity_file);
393 	switch (convert_format) {
394 	case FMT_RFC4716:
395 		do_convert_to_ssh2(pw, k);
396 		break;
397 	case FMT_PKCS8:
398 		do_convert_to_pkcs8(k);
399 		break;
400 	case FMT_PEM:
401 		do_convert_to_pem(k);
402 		break;
403 	default:
404 		fatal("%s: unknown key format %d", __func__, convert_format);
405 	}
406 	exit(0);
407 }
408 
409 /*
410  * This is almost exactly the bignum1 encoding, but with 32 bit for length
411  * instead of 16.
412  */
413 static void
414 buffer_get_bignum_bits(struct sshbuf *b, BIGNUM *value)
415 {
416 	u_int bytes, bignum_bits;
417 	int r;
418 
419 	if ((r = sshbuf_get_u32(b, &bignum_bits)) != 0)
420 		fatal("%s: buffer error: %s", __func__, ssh_err(r));
421 	bytes = (bignum_bits + 7) / 8;
422 	if (sshbuf_len(b) < bytes)
423 		fatal("%s: input buffer too small: need %d have %zu",
424 		    __func__, bytes, sshbuf_len(b));
425 	if (BN_bin2bn(sshbuf_ptr(b), bytes, value) == NULL)
426 		fatal("%s: BN_bin2bn failed", __func__);
427 	if ((r = sshbuf_consume(b, bytes)) != 0)
428 		fatal("%s: buffer error: %s", __func__, ssh_err(r));
429 }
430 
431 static struct sshkey *
432 do_convert_private_ssh2_from_blob(u_char *blob, u_int blen)
433 {
434 	struct sshbuf *b;
435 	struct sshkey *key = NULL;
436 	char *type, *cipher;
437 	u_char e1, e2, e3, *sig = NULL, data[] = "abcde12345";
438 	int r, rlen, ktype;
439 	u_int magic, i1, i2, i3, i4;
440 	size_t slen;
441 	u_long e;
442 	BIGNUM *dsa_p = NULL, *dsa_q = NULL, *dsa_g = NULL;
443 	BIGNUM *dsa_pub_key = NULL, *dsa_priv_key = NULL;
444 	BIGNUM *rsa_n = NULL, *rsa_e = NULL, *rsa_d = NULL;
445 	BIGNUM *rsa_p = NULL, *rsa_q = NULL, *rsa_iqmp = NULL;
446 	if ((b = sshbuf_from(blob, blen)) == NULL)
447 		fatal("%s: sshbuf_from failed", __func__);
448 	if ((r = sshbuf_get_u32(b, &magic)) != 0)
449 		fatal("%s: buffer error: %s", __func__, ssh_err(r));
450 
451 	if (magic != SSH_COM_PRIVATE_KEY_MAGIC) {
452 		error("bad magic 0x%x != 0x%x", magic,
453 		    SSH_COM_PRIVATE_KEY_MAGIC);
454 		sshbuf_free(b);
455 		return NULL;
456 	}
457 	if ((r = sshbuf_get_u32(b, &i1)) != 0 ||
458 	    (r = sshbuf_get_cstring(b, &type, NULL)) != 0 ||
459 	    (r = sshbuf_get_cstring(b, &cipher, NULL)) != 0 ||
460 	    (r = sshbuf_get_u32(b, &i2)) != 0 ||
461 	    (r = sshbuf_get_u32(b, &i3)) != 0 ||
462 	    (r = sshbuf_get_u32(b, &i4)) != 0)
463 		fatal("%s: buffer error: %s", __func__, ssh_err(r));
464 	debug("ignore (%d %d %d %d)", i1, i2, i3, i4);
465 	if (strcmp(cipher, "none") != 0) {
466 		error("unsupported cipher %s", cipher);
467 		free(cipher);
468 		sshbuf_free(b);
469 		free(type);
470 		return NULL;
471 	}
472 	free(cipher);
473 
474 	if (strstr(type, "dsa")) {
475 		ktype = KEY_DSA;
476 	} else if (strstr(type, "rsa")) {
477 		ktype = KEY_RSA;
478 	} else {
479 		sshbuf_free(b);
480 		free(type);
481 		return NULL;
482 	}
483 	if ((key = sshkey_new(ktype)) == NULL)
484 		fatal("sshkey_new failed");
485 	free(type);
486 
487 	switch (key->type) {
488 	case KEY_DSA:
489 		if ((dsa_p = BN_new()) == NULL ||
490 		    (dsa_q = BN_new()) == NULL ||
491 		    (dsa_g = BN_new()) == NULL ||
492 		    (dsa_pub_key = BN_new()) == NULL ||
493 		    (dsa_priv_key = BN_new()) == NULL)
494 			fatal("%s: BN_new", __func__);
495 		buffer_get_bignum_bits(b, dsa_p);
496 		buffer_get_bignum_bits(b, dsa_g);
497 		buffer_get_bignum_bits(b, dsa_q);
498 		buffer_get_bignum_bits(b, dsa_pub_key);
499 		buffer_get_bignum_bits(b, dsa_priv_key);
500 		if (!DSA_set0_pqg(key->dsa, dsa_p, dsa_q, dsa_g))
501 			fatal("%s: DSA_set0_pqg failed", __func__);
502 		dsa_p = dsa_q = dsa_g = NULL; /* transferred */
503 		if (!DSA_set0_key(key->dsa, dsa_pub_key, dsa_priv_key))
504 			fatal("%s: DSA_set0_key failed", __func__);
505 		dsa_pub_key = dsa_priv_key = NULL; /* transferred */
506 		break;
507 	case KEY_RSA:
508 		if ((r = sshbuf_get_u8(b, &e1)) != 0 ||
509 		    (e1 < 30 && (r = sshbuf_get_u8(b, &e2)) != 0) ||
510 		    (e1 < 30 && (r = sshbuf_get_u8(b, &e3)) != 0))
511 			fatal("%s: buffer error: %s", __func__, ssh_err(r));
512 		e = e1;
513 		debug("e %lx", e);
514 		if (e < 30) {
515 			e <<= 8;
516 			e += e2;
517 			debug("e %lx", e);
518 			e <<= 8;
519 			e += e3;
520 			debug("e %lx", e);
521 		}
522 		if ((rsa_e = BN_new()) == NULL)
523 			fatal("%s: BN_new", __func__);
524 		if (!BN_set_word(rsa_e, e)) {
525 			BN_clear_free(rsa_e);
526 			sshbuf_free(b);
527 			sshkey_free(key);
528 			return NULL;
529 		}
530 		if ((rsa_n = BN_new()) == NULL ||
531 		    (rsa_d = BN_new()) == NULL ||
532 		    (rsa_p = BN_new()) == NULL ||
533 		    (rsa_q = BN_new()) == NULL ||
534 		    (rsa_iqmp = BN_new()) == NULL)
535 			fatal("%s: BN_new", __func__);
536 		buffer_get_bignum_bits(b, rsa_d);
537 		buffer_get_bignum_bits(b, rsa_n);
538 		buffer_get_bignum_bits(b, rsa_iqmp);
539 		buffer_get_bignum_bits(b, rsa_q);
540 		buffer_get_bignum_bits(b, rsa_p);
541 		if (!RSA_set0_key(key->rsa, rsa_n, rsa_e, rsa_d))
542 			fatal("%s: RSA_set0_key failed", __func__);
543 		rsa_n = rsa_e = rsa_d = NULL; /* transferred */
544 		if (!RSA_set0_factors(key->rsa, rsa_p, rsa_q))
545 			fatal("%s: RSA_set0_factors failed", __func__);
546 		rsa_p = rsa_q = NULL; /* transferred */
547 		if ((r = ssh_rsa_complete_crt_parameters(key, rsa_iqmp)) != 0)
548 			fatal("generate RSA parameters failed: %s", ssh_err(r));
549 		BN_clear_free(rsa_iqmp);
550 		break;
551 	}
552 	rlen = sshbuf_len(b);
553 	if (rlen != 0)
554 		error("do_convert_private_ssh2_from_blob: "
555 		    "remaining bytes in key blob %d", rlen);
556 	sshbuf_free(b);
557 
558 	/* try the key */
559 	if (sshkey_sign(key, &sig, &slen, data, sizeof(data), NULL, 0) != 0 ||
560 	    sshkey_verify(key, sig, slen, data, sizeof(data), NULL, 0) != 0) {
561 		sshkey_free(key);
562 		free(sig);
563 		return NULL;
564 	}
565 	free(sig);
566 	return key;
567 }
568 
569 static int
570 get_line(FILE *fp, char *line, size_t len)
571 {
572 	int c;
573 	size_t pos = 0;
574 
575 	line[0] = '\0';
576 	while ((c = fgetc(fp)) != EOF) {
577 		if (pos >= len - 1)
578 			fatal("input line too long.");
579 		switch (c) {
580 		case '\r':
581 			c = fgetc(fp);
582 			if (c != EOF && c != '\n' && ungetc(c, fp) == EOF)
583 				fatal("unget: %s", strerror(errno));
584 			return pos;
585 		case '\n':
586 			return pos;
587 		}
588 		line[pos++] = c;
589 		line[pos] = '\0';
590 	}
591 	/* We reached EOF */
592 	return -1;
593 }
594 
595 static void
596 do_convert_from_ssh2(struct passwd *pw, struct sshkey **k, int *private)
597 {
598 	int r, blen, escaped = 0;
599 	u_int len;
600 	char line[1024];
601 	u_char blob[8096];
602 	char encoded[8096];
603 	FILE *fp;
604 
605 	if ((fp = fopen(identity_file, "r")) == NULL)
606 		fatal("%s: %s: %s", __progname, identity_file, strerror(errno));
607 	encoded[0] = '\0';
608 	while ((blen = get_line(fp, line, sizeof(line))) != -1) {
609 		if (blen > 0 && line[blen - 1] == '\\')
610 			escaped++;
611 		if (strncmp(line, "----", 4) == 0 ||
612 		    strstr(line, ": ") != NULL) {
613 			if (strstr(line, SSH_COM_PRIVATE_BEGIN) != NULL)
614 				*private = 1;
615 			if (strstr(line, " END ") != NULL) {
616 				break;
617 			}
618 			/* fprintf(stderr, "ignore: %s", line); */
619 			continue;
620 		}
621 		if (escaped) {
622 			escaped--;
623 			/* fprintf(stderr, "escaped: %s", line); */
624 			continue;
625 		}
626 		strlcat(encoded, line, sizeof(encoded));
627 	}
628 	len = strlen(encoded);
629 	if (((len % 4) == 3) &&
630 	    (encoded[len-1] == '=') &&
631 	    (encoded[len-2] == '=') &&
632 	    (encoded[len-3] == '='))
633 		encoded[len-3] = '\0';
634 	blen = uudecode(encoded, blob, sizeof(blob));
635 	if (blen < 0)
636 		fatal("uudecode failed.");
637 	if (*private)
638 		*k = do_convert_private_ssh2_from_blob(blob, blen);
639 	else if ((r = sshkey_from_blob(blob, blen, k)) != 0)
640 		fatal("decode blob failed: %s", ssh_err(r));
641 	fclose(fp);
642 }
643 
644 static void
645 do_convert_from_pkcs8(struct sshkey **k, int *private)
646 {
647 	EVP_PKEY *pubkey;
648 	FILE *fp;
649 
650 	if ((fp = fopen(identity_file, "r")) == NULL)
651 		fatal("%s: %s: %s", __progname, identity_file, strerror(errno));
652 	if ((pubkey = PEM_read_PUBKEY(fp, NULL, NULL, NULL)) == NULL) {
653 		fatal("%s: %s is not a recognised public key format", __func__,
654 		    identity_file);
655 	}
656 	fclose(fp);
657 	switch (EVP_PKEY_base_id(pubkey)) {
658 	case EVP_PKEY_RSA:
659 		if ((*k = sshkey_new(KEY_UNSPEC)) == NULL)
660 			fatal("sshkey_new failed");
661 		(*k)->type = KEY_RSA;
662 		(*k)->rsa = EVP_PKEY_get1_RSA(pubkey);
663 		break;
664 	case EVP_PKEY_DSA:
665 		if ((*k = sshkey_new(KEY_UNSPEC)) == NULL)
666 			fatal("sshkey_new failed");
667 		(*k)->type = KEY_DSA;
668 		(*k)->dsa = EVP_PKEY_get1_DSA(pubkey);
669 		break;
670 	case EVP_PKEY_EC:
671 		if ((*k = sshkey_new(KEY_UNSPEC)) == NULL)
672 			fatal("sshkey_new failed");
673 		(*k)->type = KEY_ECDSA;
674 		(*k)->ecdsa = EVP_PKEY_get1_EC_KEY(pubkey);
675 		(*k)->ecdsa_nid = sshkey_ecdsa_key_to_nid((*k)->ecdsa);
676 		break;
677 	default:
678 		fatal("%s: unsupported pubkey type %d", __func__,
679 		    EVP_PKEY_base_id(pubkey));
680 	}
681 	EVP_PKEY_free(pubkey);
682 	return;
683 }
684 
685 static void
686 do_convert_from_pem(struct sshkey **k, int *private)
687 {
688 	FILE *fp;
689 	RSA *rsa;
690 
691 	if ((fp = fopen(identity_file, "r")) == NULL)
692 		fatal("%s: %s: %s", __progname, identity_file, strerror(errno));
693 	if ((rsa = PEM_read_RSAPublicKey(fp, NULL, NULL, NULL)) != NULL) {
694 		if ((*k = sshkey_new(KEY_UNSPEC)) == NULL)
695 			fatal("sshkey_new failed");
696 		(*k)->type = KEY_RSA;
697 		(*k)->rsa = rsa;
698 		fclose(fp);
699 		return;
700 	}
701 	fatal("%s: unrecognised raw private key format", __func__);
702 }
703 
704 static void
705 do_convert_from(struct passwd *pw)
706 {
707 	struct sshkey *k = NULL;
708 	int r, private = 0, ok = 0;
709 	struct stat st;
710 
711 	if (!have_identity)
712 		ask_filename(pw, "Enter file in which the key is");
713 	if (stat(identity_file, &st) < 0)
714 		fatal("%s: %s: %s", __progname, identity_file, strerror(errno));
715 
716 	switch (convert_format) {
717 	case FMT_RFC4716:
718 		do_convert_from_ssh2(pw, &k, &private);
719 		break;
720 	case FMT_PKCS8:
721 		do_convert_from_pkcs8(&k, &private);
722 		break;
723 	case FMT_PEM:
724 		do_convert_from_pem(&k, &private);
725 		break;
726 	default:
727 		fatal("%s: unknown key format %d", __func__, convert_format);
728 	}
729 
730 	if (!private) {
731 		if ((r = sshkey_write(k, stdout)) == 0)
732 			ok = 1;
733 		if (ok)
734 			fprintf(stdout, "\n");
735 	} else {
736 		switch (k->type) {
737 		case KEY_DSA:
738 			ok = PEM_write_DSAPrivateKey(stdout, k->dsa, NULL,
739 			    NULL, 0, NULL, NULL);
740 			break;
741 		case KEY_ECDSA:
742 			ok = PEM_write_ECPrivateKey(stdout, k->ecdsa, NULL,
743 			    NULL, 0, NULL, NULL);
744 			break;
745 		case KEY_RSA:
746 			ok = PEM_write_RSAPrivateKey(stdout, k->rsa, NULL,
747 			    NULL, 0, NULL, NULL);
748 			break;
749 		default:
750 			fatal("%s: unsupported key type %s", __func__,
751 			    sshkey_type(k));
752 		}
753 	}
754 
755 	if (!ok)
756 		fatal("key write failed");
757 	sshkey_free(k);
758 	exit(0);
759 }
760 #endif
761 
762 static void
763 do_print_public(struct passwd *pw)
764 {
765 	struct sshkey *prv;
766 	struct stat st;
767 	int r;
768 
769 	if (!have_identity)
770 		ask_filename(pw, "Enter file in which the key is");
771 	if (stat(identity_file, &st) < 0)
772 		fatal("%s: %s", identity_file, strerror(errno));
773 	prv = load_identity(identity_file);
774 	if ((r = sshkey_write(prv, stdout)) != 0)
775 		error("sshkey_write failed: %s", ssh_err(r));
776 	sshkey_free(prv);
777 	fprintf(stdout, "\n");
778 	exit(0);
779 }
780 
781 static void
782 do_download(struct passwd *pw)
783 {
784 #ifdef ENABLE_PKCS11
785 	struct sshkey **keys = NULL;
786 	int i, nkeys;
787 	enum sshkey_fp_rep rep;
788 	int fptype;
789 	char *fp, *ra;
790 
791 	fptype = print_bubblebabble ? SSH_DIGEST_SHA1 : fingerprint_hash;
792 	rep =    print_bubblebabble ? SSH_FP_BUBBLEBABBLE : SSH_FP_DEFAULT;
793 
794 	pkcs11_init(0);
795 	nkeys = pkcs11_add_provider(pkcs11provider, NULL, &keys);
796 	if (nkeys <= 0)
797 		fatal("cannot read public key from pkcs11");
798 	for (i = 0; i < nkeys; i++) {
799 		if (print_fingerprint) {
800 			fp = sshkey_fingerprint(keys[i], fptype, rep);
801 			ra = sshkey_fingerprint(keys[i], fingerprint_hash,
802 			    SSH_FP_RANDOMART);
803 			if (fp == NULL || ra == NULL)
804 				fatal("%s: sshkey_fingerprint fail", __func__);
805 			printf("%u %s %s (PKCS11 key)\n", sshkey_size(keys[i]),
806 			    fp, sshkey_type(keys[i]));
807 			if (log_level >= SYSLOG_LEVEL_VERBOSE)
808 				printf("%s\n", ra);
809 			free(ra);
810 			free(fp);
811 		} else {
812 			(void) sshkey_write(keys[i], stdout); /* XXX check */
813 			fprintf(stdout, "\n");
814 		}
815 		sshkey_free(keys[i]);
816 	}
817 	free(keys);
818 	pkcs11_terminate();
819 	exit(0);
820 #else
821 	fatal("no pkcs11 support");
822 #endif /* ENABLE_PKCS11 */
823 }
824 
825 static struct sshkey *
826 try_read_key(char **cpp)
827 {
828 	struct sshkey *ret;
829 	int r;
830 
831 	if ((ret = sshkey_new(KEY_UNSPEC)) == NULL)
832 		fatal("sshkey_new failed");
833 	if ((r = sshkey_read(ret, cpp)) == 0)
834 		return ret;
835 	/* Not a key */
836 	sshkey_free(ret);
837 	return NULL;
838 }
839 
840 static void
841 fingerprint_one_key(const struct sshkey *public, const char *comment)
842 {
843 	char *fp = NULL, *ra = NULL;
844 	enum sshkey_fp_rep rep;
845 	int fptype;
846 
847 	fptype = print_bubblebabble ? SSH_DIGEST_SHA1 : fingerprint_hash;
848 	rep =    print_bubblebabble ? SSH_FP_BUBBLEBABBLE : SSH_FP_DEFAULT;
849 	fp = sshkey_fingerprint(public, fptype, rep);
850 	ra = sshkey_fingerprint(public, fingerprint_hash, SSH_FP_RANDOMART);
851 	if (fp == NULL || ra == NULL)
852 		fatal("%s: sshkey_fingerprint failed", __func__);
853 	mprintf("%u %s %s (%s)\n", sshkey_size(public), fp,
854 	    comment ? comment : "no comment", sshkey_type(public));
855 	if (log_level >= SYSLOG_LEVEL_VERBOSE)
856 		printf("%s\n", ra);
857 	free(ra);
858 	free(fp);
859 }
860 
861 static void
862 fingerprint_private(const char *path)
863 {
864 	struct stat st;
865 	char *comment = NULL;
866 	struct sshkey *public = NULL;
867 	int r;
868 
869 	if (stat(identity_file, &st) < 0)
870 		fatal("%s: %s", path, strerror(errno));
871 	if ((r = sshkey_load_public(path, &public, &comment)) != 0) {
872 		debug("load public \"%s\": %s", path, ssh_err(r));
873 		if ((r = sshkey_load_private(path, NULL,
874 		    &public, &comment)) != 0) {
875 			debug("load private \"%s\": %s", path, ssh_err(r));
876 			fatal("%s is not a key file.", path);
877 		}
878 	}
879 
880 	fingerprint_one_key(public, comment);
881 	sshkey_free(public);
882 	free(comment);
883 }
884 
885 static void
886 do_fingerprint(struct passwd *pw)
887 {
888 	FILE *f;
889 	struct sshkey *public = NULL;
890 	char *comment = NULL, *cp, *ep, *line = NULL;
891 	size_t linesize = 0;
892 	int i, invalid = 1;
893 	const char *path;
894 	u_long lnum = 0;
895 
896 	if (!have_identity)
897 		ask_filename(pw, "Enter file in which the key is");
898 	path = identity_file;
899 
900 	if (strcmp(identity_file, "-") == 0) {
901 		f = stdin;
902 		path = "(stdin)";
903 	} else if ((f = fopen(path, "r")) == NULL)
904 		fatal("%s: %s: %s", __progname, path, strerror(errno));
905 
906 	while (getline(&line, &linesize, f) != -1) {
907 		lnum++;
908 		cp = line;
909 		cp[strcspn(cp, "\n")] = '\0';
910 		/* Trim leading space and comments */
911 		cp = line + strspn(line, " \t");
912 		if (*cp == '#' || *cp == '\0')
913 			continue;
914 
915 		/*
916 		 * Input may be plain keys, private keys, authorized_keys
917 		 * or known_hosts.
918 		 */
919 
920 		/*
921 		 * Try private keys first. Assume a key is private if
922 		 * "SSH PRIVATE KEY" appears on the first line and we're
923 		 * not reading from stdin (XXX support private keys on stdin).
924 		 */
925 		if (lnum == 1 && strcmp(identity_file, "-") != 0 &&
926 		    strstr(cp, "PRIVATE KEY") != NULL) {
927 			free(line);
928 			fclose(f);
929 			fingerprint_private(path);
930 			exit(0);
931 		}
932 
933 		/*
934 		 * If it's not a private key, then this must be prepared to
935 		 * accept a public key prefixed with a hostname or options.
936 		 * Try a bare key first, otherwise skip the leading stuff.
937 		 */
938 		if ((public = try_read_key(&cp)) == NULL) {
939 			i = strtol(cp, &ep, 10);
940 			if (i == 0 || ep == NULL ||
941 			    (*ep != ' ' && *ep != '\t')) {
942 				int quoted = 0;
943 
944 				comment = cp;
945 				for (; *cp && (quoted || (*cp != ' ' &&
946 				    *cp != '\t')); cp++) {
947 					if (*cp == '\\' && cp[1] == '"')
948 						cp++;	/* Skip both */
949 					else if (*cp == '"')
950 						quoted = !quoted;
951 				}
952 				if (!*cp)
953 					continue;
954 				*cp++ = '\0';
955 			}
956 		}
957 		/* Retry after parsing leading hostname/key options */
958 		if (public == NULL && (public = try_read_key(&cp)) == NULL) {
959 			debug("%s:%lu: not a public key", path, lnum);
960 			continue;
961 		}
962 
963 		/* Find trailing comment, if any */
964 		for (; *cp == ' ' || *cp == '\t'; cp++)
965 			;
966 		if (*cp != '\0' && *cp != '#')
967 			comment = cp;
968 
969 		fingerprint_one_key(public, comment);
970 		sshkey_free(public);
971 		invalid = 0; /* One good key in the file is sufficient */
972 	}
973 	fclose(f);
974 	free(line);
975 
976 	if (invalid)
977 		fatal("%s is not a public key file.", path);
978 	exit(0);
979 }
980 
981 static void
982 do_gen_all_hostkeys(struct passwd *pw)
983 {
984 	struct {
985 		char *key_type;
986 		char *key_type_display;
987 		char *path;
988 	} key_types[] = {
989 #ifdef WITH_OPENSSL
990 		{ "rsa", "RSA" ,_PATH_HOST_RSA_KEY_FILE },
991 		{ "dsa", "DSA", _PATH_HOST_DSA_KEY_FILE },
992 		{ "ecdsa", "ECDSA",_PATH_HOST_ECDSA_KEY_FILE },
993 #endif /* WITH_OPENSSL */
994 		{ "ed25519", "ED25519",_PATH_HOST_ED25519_KEY_FILE },
995 #ifdef WITH_XMSS
996 		{ "xmss", "XMSS",_PATH_HOST_XMSS_KEY_FILE },
997 #endif /* WITH_XMSS */
998 		{ NULL, NULL, NULL }
999 	};
1000 
1001 	int first = 0;
1002 	struct stat st;
1003 	struct sshkey *private, *public;
1004 	char comment[1024], *prv_tmp, *pub_tmp, *prv_file, *pub_file;
1005 	int i, type, fd, r;
1006 	FILE *f;
1007 
1008 	for (i = 0; key_types[i].key_type; i++) {
1009 		public = private = NULL;
1010 		prv_tmp = pub_tmp = prv_file = pub_file = NULL;
1011 
1012 		xasprintf(&prv_file, "%s%s",
1013 		    identity_file, key_types[i].path);
1014 
1015 		/* Check whether private key exists and is not zero-length */
1016 		if (stat(prv_file, &st) == 0) {
1017 			if (st.st_size != 0)
1018 				goto next;
1019 		} else if (errno != ENOENT) {
1020 			error("Could not stat %s: %s", key_types[i].path,
1021 			    strerror(errno));
1022 			goto failnext;
1023 		}
1024 
1025 		/*
1026 		 * Private key doesn't exist or is invalid; proceed with
1027 		 * key generation.
1028 		 */
1029 		xasprintf(&prv_tmp, "%s%s.XXXXXXXXXX",
1030 		    identity_file, key_types[i].path);
1031 		xasprintf(&pub_tmp, "%s%s.pub.XXXXXXXXXX",
1032 		    identity_file, key_types[i].path);
1033 		xasprintf(&pub_file, "%s%s.pub",
1034 		    identity_file, key_types[i].path);
1035 
1036 		if (first == 0) {
1037 			first = 1;
1038 			printf("%s: generating new host keys: ", __progname);
1039 		}
1040 		printf("%s ", key_types[i].key_type_display);
1041 		fflush(stdout);
1042 		type = sshkey_type_from_name(key_types[i].key_type);
1043 		if ((fd = mkstemp(prv_tmp)) == -1) {
1044 			error("Could not save your public key in %s: %s",
1045 			    prv_tmp, strerror(errno));
1046 			goto failnext;
1047 		}
1048 		close(fd); /* just using mkstemp() to generate/reserve a name */
1049 		bits = 0;
1050 		type_bits_valid(type, NULL, &bits);
1051 		if ((r = sshkey_generate(type, bits, &private)) != 0) {
1052 			error("sshkey_generate failed: %s", ssh_err(r));
1053 			goto failnext;
1054 		}
1055 		if ((r = sshkey_from_private(private, &public)) != 0)
1056 			fatal("sshkey_from_private failed: %s", ssh_err(r));
1057 		snprintf(comment, sizeof comment, "%s@%s", pw->pw_name,
1058 		    hostname);
1059 		if ((r = sshkey_save_private(private, prv_tmp, "",
1060 		    comment, use_new_format, new_format_cipher, rounds)) != 0) {
1061 			error("Saving key \"%s\" failed: %s",
1062 			    prv_tmp, ssh_err(r));
1063 			goto failnext;
1064 		}
1065 		if ((fd = mkstemp(pub_tmp)) == -1) {
1066 			error("Could not save your public key in %s: %s",
1067 			    pub_tmp, strerror(errno));
1068 			goto failnext;
1069 		}
1070 		(void)fchmod(fd, 0644);
1071 		f = fdopen(fd, "w");
1072 		if (f == NULL) {
1073 			error("fdopen %s failed: %s", pub_tmp, strerror(errno));
1074 			close(fd);
1075 			goto failnext;
1076 		}
1077 		if ((r = sshkey_write(public, f)) != 0) {
1078 			error("write key failed: %s", ssh_err(r));
1079 			fclose(f);
1080 			goto failnext;
1081 		}
1082 		fprintf(f, " %s\n", comment);
1083 		if (ferror(f) != 0) {
1084 			error("write key failed: %s", strerror(errno));
1085 			fclose(f);
1086 			goto failnext;
1087 		}
1088 		if (fclose(f) != 0) {
1089 			error("key close failed: %s", strerror(errno));
1090 			goto failnext;
1091 		}
1092 
1093 		/* Rename temporary files to their permanent locations. */
1094 		if (rename(pub_tmp, pub_file) != 0) {
1095 			error("Unable to move %s into position: %s",
1096 			    pub_file, strerror(errno));
1097 			goto failnext;
1098 		}
1099 		if (rename(prv_tmp, prv_file) != 0) {
1100 			error("Unable to move %s into position: %s",
1101 			    key_types[i].path, strerror(errno));
1102  failnext:
1103 			first = 0;
1104 			goto next;
1105 		}
1106  next:
1107 		sshkey_free(private);
1108 		sshkey_free(public);
1109 		free(prv_tmp);
1110 		free(pub_tmp);
1111 		free(prv_file);
1112 		free(pub_file);
1113 	}
1114 	if (first != 0)
1115 		printf("\n");
1116 }
1117 
1118 struct known_hosts_ctx {
1119 	const char *host;	/* Hostname searched for in find/delete case */
1120 	FILE *out;		/* Output file, stdout for find_hosts case */
1121 	int has_unhashed;	/* When hashing, original had unhashed hosts */
1122 	int found_key;		/* For find/delete, host was found */
1123 	int invalid;		/* File contained invalid items; don't delete */
1124 };
1125 
1126 static int
1127 known_hosts_hash(struct hostkey_foreach_line *l, void *_ctx)
1128 {
1129 	struct known_hosts_ctx *ctx = (struct known_hosts_ctx *)_ctx;
1130 	char *hashed, *cp, *hosts, *ohosts;
1131 	int has_wild = l->hosts && strcspn(l->hosts, "*?!") != strlen(l->hosts);
1132 	int was_hashed = l->hosts && l->hosts[0] == HASH_DELIM;
1133 
1134 	switch (l->status) {
1135 	case HKF_STATUS_OK:
1136 	case HKF_STATUS_MATCHED:
1137 		/*
1138 		 * Don't hash hosts already already hashed, with wildcard
1139 		 * characters or a CA/revocation marker.
1140 		 */
1141 		if (was_hashed || has_wild || l->marker != MRK_NONE) {
1142 			fprintf(ctx->out, "%s\n", l->line);
1143 			if (has_wild && !find_host) {
1144 				logit("%s:%lu: ignoring host name "
1145 				    "with wildcard: %.64s", l->path,
1146 				    l->linenum, l->hosts);
1147 			}
1148 			return 0;
1149 		}
1150 		/*
1151 		 * Split any comma-separated hostnames from the host list,
1152 		 * hash and store separately.
1153 		 */
1154 		ohosts = hosts = xstrdup(l->hosts);
1155 		while ((cp = strsep(&hosts, ",")) != NULL && *cp != '\0') {
1156 			lowercase(cp);
1157 			if ((hashed = host_hash(cp, NULL, 0)) == NULL)
1158 				fatal("hash_host failed");
1159 			fprintf(ctx->out, "%s %s\n", hashed, l->rawkey);
1160 			ctx->has_unhashed = 1;
1161 		}
1162 		free(ohosts);
1163 		return 0;
1164 	case HKF_STATUS_INVALID:
1165 		/* Retain invalid lines, but mark file as invalid. */
1166 		ctx->invalid = 1;
1167 		logit("%s:%lu: invalid line", l->path, l->linenum);
1168 		/* FALLTHROUGH */
1169 	default:
1170 		fprintf(ctx->out, "%s\n", l->line);
1171 		return 0;
1172 	}
1173 	/* NOTREACHED */
1174 	return -1;
1175 }
1176 
1177 static int
1178 known_hosts_find_delete(struct hostkey_foreach_line *l, void *_ctx)
1179 {
1180 	struct known_hosts_ctx *ctx = (struct known_hosts_ctx *)_ctx;
1181 	enum sshkey_fp_rep rep;
1182 	int fptype;
1183 	char *fp;
1184 
1185 	fptype = print_bubblebabble ? SSH_DIGEST_SHA1 : fingerprint_hash;
1186 	rep =    print_bubblebabble ? SSH_FP_BUBBLEBABBLE : SSH_FP_DEFAULT;
1187 
1188 	if (l->status == HKF_STATUS_MATCHED) {
1189 		if (delete_host) {
1190 			if (l->marker != MRK_NONE) {
1191 				/* Don't remove CA and revocation lines */
1192 				fprintf(ctx->out, "%s\n", l->line);
1193 			} else {
1194 				/*
1195 				 * Hostname matches and has no CA/revoke
1196 				 * marker, delete it by *not* writing the
1197 				 * line to ctx->out.
1198 				 */
1199 				ctx->found_key = 1;
1200 				if (!quiet)
1201 					printf("# Host %s found: line %lu\n",
1202 					    ctx->host, l->linenum);
1203 			}
1204 			return 0;
1205 		} else if (find_host) {
1206 			ctx->found_key = 1;
1207 			if (!quiet) {
1208 				printf("# Host %s found: line %lu %s\n",
1209 				    ctx->host,
1210 				    l->linenum, l->marker == MRK_CA ? "CA" :
1211 				    (l->marker == MRK_REVOKE ? "REVOKED" : ""));
1212 			}
1213 			if (hash_hosts)
1214 				known_hosts_hash(l, ctx);
1215 			else if (print_fingerprint) {
1216 				fp = sshkey_fingerprint(l->key, fptype, rep);
1217 				mprintf("%s %s %s %s\n", ctx->host,
1218 				    sshkey_type(l->key), fp, l->comment);
1219 				free(fp);
1220 			} else
1221 				fprintf(ctx->out, "%s\n", l->line);
1222 			return 0;
1223 		}
1224 	} else if (delete_host) {
1225 		/* Retain non-matching hosts when deleting */
1226 		if (l->status == HKF_STATUS_INVALID) {
1227 			ctx->invalid = 1;
1228 			logit("%s:%lu: invalid line", l->path, l->linenum);
1229 		}
1230 		fprintf(ctx->out, "%s\n", l->line);
1231 	}
1232 	return 0;
1233 }
1234 
1235 static void
1236 do_known_hosts(struct passwd *pw, const char *name)
1237 {
1238 	char *cp, tmp[PATH_MAX], old[PATH_MAX];
1239 	int r, fd, oerrno, inplace = 0;
1240 	struct known_hosts_ctx ctx;
1241 	u_int foreach_options;
1242 
1243 	if (!have_identity) {
1244 		cp = tilde_expand_filename(_PATH_SSH_USER_HOSTFILE, pw->pw_uid);
1245 		if (strlcpy(identity_file, cp, sizeof(identity_file)) >=
1246 		    sizeof(identity_file))
1247 			fatal("Specified known hosts path too long");
1248 		free(cp);
1249 		have_identity = 1;
1250 	}
1251 
1252 	memset(&ctx, 0, sizeof(ctx));
1253 	ctx.out = stdout;
1254 	ctx.host = name;
1255 
1256 	/*
1257 	 * Find hosts goes to stdout, hash and deletions happen in-place
1258 	 * A corner case is ssh-keygen -HF foo, which should go to stdout
1259 	 */
1260 	if (!find_host && (hash_hosts || delete_host)) {
1261 		if (strlcpy(tmp, identity_file, sizeof(tmp)) >= sizeof(tmp) ||
1262 		    strlcat(tmp, ".XXXXXXXXXX", sizeof(tmp)) >= sizeof(tmp) ||
1263 		    strlcpy(old, identity_file, sizeof(old)) >= sizeof(old) ||
1264 		    strlcat(old, ".old", sizeof(old)) >= sizeof(old))
1265 			fatal("known_hosts path too long");
1266 		umask(077);
1267 		if ((fd = mkstemp(tmp)) == -1)
1268 			fatal("mkstemp: %s", strerror(errno));
1269 		if ((ctx.out = fdopen(fd, "w")) == NULL) {
1270 			oerrno = errno;
1271 			unlink(tmp);
1272 			fatal("fdopen: %s", strerror(oerrno));
1273 		}
1274 		inplace = 1;
1275 	}
1276 	/* XXX support identity_file == "-" for stdin */
1277 	foreach_options = find_host ? HKF_WANT_MATCH : 0;
1278 	foreach_options |= print_fingerprint ? HKF_WANT_PARSE_KEY : 0;
1279 	if ((r = hostkeys_foreach(identity_file, (find_host || !hash_hosts) ?
1280 	    known_hosts_find_delete : known_hosts_hash, &ctx, name, NULL,
1281 	    foreach_options)) != 0) {
1282 		if (inplace)
1283 			unlink(tmp);
1284 		fatal("%s: hostkeys_foreach failed: %s", __func__, ssh_err(r));
1285 	}
1286 
1287 	if (inplace)
1288 		fclose(ctx.out);
1289 
1290 	if (ctx.invalid) {
1291 		error("%s is not a valid known_hosts file.", identity_file);
1292 		if (inplace) {
1293 			error("Not replacing existing known_hosts "
1294 			    "file because of errors");
1295 			unlink(tmp);
1296 		}
1297 		exit(1);
1298 	} else if (delete_host && !ctx.found_key) {
1299 		logit("Host %s not found in %s", name, identity_file);
1300 		if (inplace)
1301 			unlink(tmp);
1302 	} else if (inplace) {
1303 		/* Backup existing file */
1304 		if (unlink(old) == -1 && errno != ENOENT)
1305 			fatal("unlink %.100s: %s", old, strerror(errno));
1306 		if (link(identity_file, old) == -1)
1307 			fatal("link %.100s to %.100s: %s", identity_file, old,
1308 			    strerror(errno));
1309 		/* Move new one into place */
1310 		if (rename(tmp, identity_file) == -1) {
1311 			error("rename\"%s\" to \"%s\": %s", tmp, identity_file,
1312 			    strerror(errno));
1313 			unlink(tmp);
1314 			unlink(old);
1315 			exit(1);
1316 		}
1317 
1318 		printf("%s updated.\n", identity_file);
1319 		printf("Original contents retained as %s\n", old);
1320 		if (ctx.has_unhashed) {
1321 			logit("WARNING: %s contains unhashed entries", old);
1322 			logit("Delete this file to ensure privacy "
1323 			    "of hostnames");
1324 		}
1325 	}
1326 
1327 	exit (find_host && !ctx.found_key);
1328 }
1329 
1330 /*
1331  * Perform changing a passphrase.  The argument is the passwd structure
1332  * for the current user.
1333  */
1334 static void
1335 do_change_passphrase(struct passwd *pw)
1336 {
1337 	char *comment;
1338 	char *old_passphrase, *passphrase1, *passphrase2;
1339 	struct stat st;
1340 	struct sshkey *private;
1341 	int r;
1342 
1343 	if (!have_identity)
1344 		ask_filename(pw, "Enter file in which the key is");
1345 	if (stat(identity_file, &st) < 0)
1346 		fatal("%s: %s", identity_file, strerror(errno));
1347 	/* Try to load the file with empty passphrase. */
1348 	r = sshkey_load_private(identity_file, "", &private, &comment);
1349 	if (r == SSH_ERR_KEY_WRONG_PASSPHRASE) {
1350 		if (identity_passphrase)
1351 			old_passphrase = xstrdup(identity_passphrase);
1352 		else
1353 			old_passphrase =
1354 			    read_passphrase("Enter old passphrase: ",
1355 			    RP_ALLOW_STDIN);
1356 		r = sshkey_load_private(identity_file, old_passphrase,
1357 		    &private, &comment);
1358 		explicit_bzero(old_passphrase, strlen(old_passphrase));
1359 		free(old_passphrase);
1360 		if (r != 0)
1361 			goto badkey;
1362 	} else if (r != 0) {
1363  badkey:
1364 		fatal("Failed to load key %s: %s", identity_file, ssh_err(r));
1365 	}
1366 	if (comment)
1367 		mprintf("Key has comment '%s'\n", comment);
1368 
1369 	/* Ask the new passphrase (twice). */
1370 	if (identity_new_passphrase) {
1371 		passphrase1 = xstrdup(identity_new_passphrase);
1372 		passphrase2 = NULL;
1373 	} else {
1374 		passphrase1 =
1375 			read_passphrase("Enter new passphrase (empty for no "
1376 			    "passphrase): ", RP_ALLOW_STDIN);
1377 		passphrase2 = read_passphrase("Enter same passphrase again: ",
1378 		    RP_ALLOW_STDIN);
1379 
1380 		/* Verify that they are the same. */
1381 		if (strcmp(passphrase1, passphrase2) != 0) {
1382 			explicit_bzero(passphrase1, strlen(passphrase1));
1383 			explicit_bzero(passphrase2, strlen(passphrase2));
1384 			free(passphrase1);
1385 			free(passphrase2);
1386 			printf("Pass phrases do not match.  Try again.\n");
1387 			exit(1);
1388 		}
1389 		/* Destroy the other copy. */
1390 		explicit_bzero(passphrase2, strlen(passphrase2));
1391 		free(passphrase2);
1392 	}
1393 
1394 	/* Save the file using the new passphrase. */
1395 	if ((r = sshkey_save_private(private, identity_file, passphrase1,
1396 	    comment, use_new_format, new_format_cipher, rounds)) != 0) {
1397 		error("Saving key \"%s\" failed: %s.",
1398 		    identity_file, ssh_err(r));
1399 		explicit_bzero(passphrase1, strlen(passphrase1));
1400 		free(passphrase1);
1401 		sshkey_free(private);
1402 		free(comment);
1403 		exit(1);
1404 	}
1405 	/* Destroy the passphrase and the copy of the key in memory. */
1406 	explicit_bzero(passphrase1, strlen(passphrase1));
1407 	free(passphrase1);
1408 	sshkey_free(private);		 /* Destroys contents */
1409 	free(comment);
1410 
1411 	printf("Your identification has been saved with the new passphrase.\n");
1412 	exit(0);
1413 }
1414 
1415 /*
1416  * Print the SSHFP RR.
1417  */
1418 static int
1419 do_print_resource_record(struct passwd *pw, char *fname, char *hname)
1420 {
1421 	struct sshkey *public;
1422 	char *comment = NULL;
1423 	struct stat st;
1424 	int r;
1425 
1426 	if (fname == NULL)
1427 		fatal("%s: no filename", __func__);
1428 	if (stat(fname, &st) < 0) {
1429 		if (errno == ENOENT)
1430 			return 0;
1431 		fatal("%s: %s", fname, strerror(errno));
1432 	}
1433 	if ((r = sshkey_load_public(fname, &public, &comment)) != 0)
1434 		fatal("Failed to read v2 public key from \"%s\": %s.",
1435 		    fname, ssh_err(r));
1436 	export_dns_rr(hname, public, stdout, print_generic);
1437 	sshkey_free(public);
1438 	free(comment);
1439 	return 1;
1440 }
1441 
1442 /*
1443  * Change the comment of a private key file.
1444  */
1445 static void
1446 do_change_comment(struct passwd *pw)
1447 {
1448 	char new_comment[1024], *comment, *passphrase;
1449 	struct sshkey *private;
1450 	struct sshkey *public;
1451 	struct stat st;
1452 	FILE *f;
1453 	int r, fd;
1454 
1455 	if (!have_identity)
1456 		ask_filename(pw, "Enter file in which the key is");
1457 	if (stat(identity_file, &st) < 0)
1458 		fatal("%s: %s", identity_file, strerror(errno));
1459 	if ((r = sshkey_load_private(identity_file, "",
1460 	    &private, &comment)) == 0)
1461 		passphrase = xstrdup("");
1462 	else if (r != SSH_ERR_KEY_WRONG_PASSPHRASE)
1463 		fatal("Cannot load private key \"%s\": %s.",
1464 		    identity_file, ssh_err(r));
1465 	else {
1466 		if (identity_passphrase)
1467 			passphrase = xstrdup(identity_passphrase);
1468 		else if (identity_new_passphrase)
1469 			passphrase = xstrdup(identity_new_passphrase);
1470 		else
1471 			passphrase = read_passphrase("Enter passphrase: ",
1472 			    RP_ALLOW_STDIN);
1473 		/* Try to load using the passphrase. */
1474 		if ((r = sshkey_load_private(identity_file, passphrase,
1475 		    &private, &comment)) != 0) {
1476 			explicit_bzero(passphrase, strlen(passphrase));
1477 			free(passphrase);
1478 			fatal("Cannot load private key \"%s\": %s.",
1479 			    identity_file, ssh_err(r));
1480 		}
1481 	}
1482 
1483 	if (private->type != KEY_ED25519 && private->type != KEY_XMSS &&
1484 	    !use_new_format) {
1485 		error("Comments are only supported for keys stored in "
1486 		    "the new format (-o).");
1487 		explicit_bzero(passphrase, strlen(passphrase));
1488 		sshkey_free(private);
1489 		exit(1);
1490 	}
1491 	if (comment)
1492 		printf("Key now has comment '%s'\n", comment);
1493 	else
1494 		printf("Key now has no comment\n");
1495 
1496 	if (identity_comment) {
1497 		strlcpy(new_comment, identity_comment, sizeof(new_comment));
1498 	} else {
1499 		printf("Enter new comment: ");
1500 		fflush(stdout);
1501 		if (!fgets(new_comment, sizeof(new_comment), stdin)) {
1502 			explicit_bzero(passphrase, strlen(passphrase));
1503 			sshkey_free(private);
1504 			exit(1);
1505 		}
1506 		new_comment[strcspn(new_comment, "\n")] = '\0';
1507 	}
1508 
1509 	/* Save the file using the new passphrase. */
1510 	if ((r = sshkey_save_private(private, identity_file, passphrase,
1511 	    new_comment, use_new_format, new_format_cipher, rounds)) != 0) {
1512 		error("Saving key \"%s\" failed: %s",
1513 		    identity_file, ssh_err(r));
1514 		explicit_bzero(passphrase, strlen(passphrase));
1515 		free(passphrase);
1516 		sshkey_free(private);
1517 		free(comment);
1518 		exit(1);
1519 	}
1520 	explicit_bzero(passphrase, strlen(passphrase));
1521 	free(passphrase);
1522 	if ((r = sshkey_from_private(private, &public)) != 0)
1523 		fatal("sshkey_from_private failed: %s", ssh_err(r));
1524 	sshkey_free(private);
1525 
1526 	strlcat(identity_file, ".pub", sizeof(identity_file));
1527 	fd = open(identity_file, O_WRONLY | O_CREAT | O_TRUNC, 0644);
1528 	if (fd == -1)
1529 		fatal("Could not save your public key in %s", identity_file);
1530 	f = fdopen(fd, "w");
1531 	if (f == NULL)
1532 		fatal("fdopen %s failed: %s", identity_file, strerror(errno));
1533 	if ((r = sshkey_write(public, f)) != 0)
1534 		fatal("write key failed: %s", ssh_err(r));
1535 	sshkey_free(public);
1536 	fprintf(f, " %s\n", new_comment);
1537 	fclose(f);
1538 
1539 	free(comment);
1540 
1541 	printf("The comment in your key file has been changed.\n");
1542 	exit(0);
1543 }
1544 
1545 static void
1546 add_flag_option(struct sshbuf *c, const char *name)
1547 {
1548 	int r;
1549 
1550 	debug3("%s: %s", __func__, name);
1551 	if ((r = sshbuf_put_cstring(c, name)) != 0 ||
1552 	    (r = sshbuf_put_string(c, NULL, 0)) != 0)
1553 		fatal("%s: buffer error: %s", __func__, ssh_err(r));
1554 }
1555 
1556 static void
1557 add_string_option(struct sshbuf *c, const char *name, const char *value)
1558 {
1559 	struct sshbuf *b;
1560 	int r;
1561 
1562 	debug3("%s: %s=%s", __func__, name, value);
1563 	if ((b = sshbuf_new()) == NULL)
1564 		fatal("%s: sshbuf_new failed", __func__);
1565 	if ((r = sshbuf_put_cstring(b, value)) != 0 ||
1566 	    (r = sshbuf_put_cstring(c, name)) != 0 ||
1567 	    (r = sshbuf_put_stringb(c, b)) != 0)
1568 		fatal("%s: buffer error: %s", __func__, ssh_err(r));
1569 
1570 	sshbuf_free(b);
1571 }
1572 
1573 #define OPTIONS_CRITICAL	1
1574 #define OPTIONS_EXTENSIONS	2
1575 static void
1576 prepare_options_buf(struct sshbuf *c, int which)
1577 {
1578 	size_t i;
1579 
1580 	sshbuf_reset(c);
1581 	if ((which & OPTIONS_CRITICAL) != 0 &&
1582 	    certflags_command != NULL)
1583 		add_string_option(c, "force-command", certflags_command);
1584 	if ((which & OPTIONS_EXTENSIONS) != 0 &&
1585 	    (certflags_flags & CERTOPT_X_FWD) != 0)
1586 		add_flag_option(c, "permit-X11-forwarding");
1587 	if ((which & OPTIONS_EXTENSIONS) != 0 &&
1588 	    (certflags_flags & CERTOPT_AGENT_FWD) != 0)
1589 		add_flag_option(c, "permit-agent-forwarding");
1590 	if ((which & OPTIONS_EXTENSIONS) != 0 &&
1591 	    (certflags_flags & CERTOPT_PORT_FWD) != 0)
1592 		add_flag_option(c, "permit-port-forwarding");
1593 	if ((which & OPTIONS_EXTENSIONS) != 0 &&
1594 	    (certflags_flags & CERTOPT_PTY) != 0)
1595 		add_flag_option(c, "permit-pty");
1596 	if ((which & OPTIONS_EXTENSIONS) != 0 &&
1597 	    (certflags_flags & CERTOPT_USER_RC) != 0)
1598 		add_flag_option(c, "permit-user-rc");
1599 	if ((which & OPTIONS_CRITICAL) != 0 &&
1600 	    certflags_src_addr != NULL)
1601 		add_string_option(c, "source-address", certflags_src_addr);
1602 	for (i = 0; i < ncert_userext; i++) {
1603 		if ((cert_userext[i].crit && (which & OPTIONS_EXTENSIONS)) ||
1604 		    (!cert_userext[i].crit && (which & OPTIONS_CRITICAL)))
1605 			continue;
1606 		if (cert_userext[i].val == NULL)
1607 			add_flag_option(c, cert_userext[i].key);
1608 		else {
1609 			add_string_option(c, cert_userext[i].key,
1610 			    cert_userext[i].val);
1611 		}
1612 	}
1613 }
1614 
1615 static struct sshkey *
1616 load_pkcs11_key(char *path)
1617 {
1618 #ifdef ENABLE_PKCS11
1619 	struct sshkey **keys = NULL, *public, *private = NULL;
1620 	int r, i, nkeys;
1621 
1622 	if ((r = sshkey_load_public(path, &public, NULL)) != 0)
1623 		fatal("Couldn't load CA public key \"%s\": %s",
1624 		    path, ssh_err(r));
1625 
1626 	nkeys = pkcs11_add_provider(pkcs11provider, identity_passphrase, &keys);
1627 	debug3("%s: %d keys", __func__, nkeys);
1628 	if (nkeys <= 0)
1629 		fatal("cannot read public key from pkcs11");
1630 	for (i = 0; i < nkeys; i++) {
1631 		if (sshkey_equal_public(public, keys[i])) {
1632 			private = keys[i];
1633 			continue;
1634 		}
1635 		sshkey_free(keys[i]);
1636 	}
1637 	free(keys);
1638 	sshkey_free(public);
1639 	return private;
1640 #else
1641 	fatal("no pkcs11 support");
1642 #endif /* ENABLE_PKCS11 */
1643 }
1644 
1645 /* Signer for sshkey_certify_custom that uses the agent */
1646 static int
1647 agent_signer(const struct sshkey *key, u_char **sigp, size_t *lenp,
1648     const u_char *data, size_t datalen,
1649     const char *alg, u_int compat, void *ctx)
1650 {
1651 	int *agent_fdp = (int *)ctx;
1652 
1653 	return ssh_agent_sign(*agent_fdp, key, sigp, lenp,
1654 	    data, datalen, alg, compat);
1655 }
1656 
1657 static void
1658 do_ca_sign(struct passwd *pw, int argc, char **argv)
1659 {
1660 	int r, i, fd, found, agent_fd = -1;
1661 	u_int n;
1662 	struct sshkey *ca, *public;
1663 	char valid[64], *otmp, *tmp, *cp, *out, *comment, **plist = NULL;
1664 	FILE *f;
1665 	struct ssh_identitylist *agent_ids;
1666 	size_t j;
1667 
1668 #ifdef ENABLE_PKCS11
1669 	pkcs11_init(1);
1670 #endif
1671 	tmp = tilde_expand_filename(ca_key_path, pw->pw_uid);
1672 	if (pkcs11provider != NULL) {
1673 		/* If a PKCS#11 token was specified then try to use it */
1674 		if ((ca = load_pkcs11_key(tmp)) == NULL)
1675 			fatal("No PKCS#11 key matching %s found", ca_key_path);
1676 	} else if (prefer_agent) {
1677 		/*
1678 		 * Agent signature requested. Try to use agent after making
1679 		 * sure the public key specified is actually present in the
1680 		 * agent.
1681 		 */
1682 		if ((r = sshkey_load_public(tmp, &ca, NULL)) != 0)
1683 			fatal("Cannot load CA public key %s: %s",
1684 			    tmp, ssh_err(r));
1685 		if ((r = ssh_get_authentication_socket(&agent_fd)) != 0)
1686 			fatal("Cannot use public key for CA signature: %s",
1687 			    ssh_err(r));
1688 		if ((r = ssh_fetch_identitylist(agent_fd, &agent_ids)) != 0)
1689 			fatal("Retrieve agent key list: %s", ssh_err(r));
1690 		found = 0;
1691 		for (j = 0; j < agent_ids->nkeys; j++) {
1692 			if (sshkey_equal(ca, agent_ids->keys[j])) {
1693 				found = 1;
1694 				break;
1695 			}
1696 		}
1697 		if (!found)
1698 			fatal("CA key %s not found in agent", tmp);
1699 		ssh_free_identitylist(agent_ids);
1700 		ca->flags |= SSHKEY_FLAG_EXT;
1701 	} else {
1702 		/* CA key is assumed to be a private key on the filesystem */
1703 		ca = load_identity(tmp);
1704 	}
1705 	free(tmp);
1706 
1707 	if (key_type_name != NULL &&
1708 	    sshkey_type_from_name(key_type_name) != ca->type)  {
1709 		fatal("CA key type %s doesn't match specified %s",
1710 		    sshkey_ssh_name(ca), key_type_name);
1711 	}
1712 
1713 	for (i = 0; i < argc; i++) {
1714 		/* Split list of principals */
1715 		n = 0;
1716 		if (cert_principals != NULL) {
1717 			otmp = tmp = xstrdup(cert_principals);
1718 			plist = NULL;
1719 			for (; (cp = strsep(&tmp, ",")) != NULL; n++) {
1720 				plist = xreallocarray(plist, n + 1, sizeof(*plist));
1721 				if (*(plist[n] = xstrdup(cp)) == '\0')
1722 					fatal("Empty principal name");
1723 			}
1724 			free(otmp);
1725 		}
1726 		if (n > SSHKEY_CERT_MAX_PRINCIPALS)
1727 			fatal("Too many certificate principals specified");
1728 
1729 		tmp = tilde_expand_filename(argv[i], pw->pw_uid);
1730 		if ((r = sshkey_load_public(tmp, &public, &comment)) != 0)
1731 			fatal("%s: unable to open \"%s\": %s",
1732 			    __func__, tmp, ssh_err(r));
1733 		if (public->type != KEY_RSA && public->type != KEY_DSA &&
1734 		    public->type != KEY_ECDSA && public->type != KEY_ED25519 &&
1735 		    public->type != KEY_XMSS)
1736 			fatal("%s: key \"%s\" type %s cannot be certified",
1737 			    __func__, tmp, sshkey_type(public));
1738 
1739 		/* Prepare certificate to sign */
1740 		if ((r = sshkey_to_certified(public)) != 0)
1741 			fatal("Could not upgrade key %s to certificate: %s",
1742 			    tmp, ssh_err(r));
1743 		public->cert->type = cert_key_type;
1744 		public->cert->serial = (u_int64_t)cert_serial;
1745 		public->cert->key_id = xstrdup(cert_key_id);
1746 		public->cert->nprincipals = n;
1747 		public->cert->principals = plist;
1748 		public->cert->valid_after = cert_valid_from;
1749 		public->cert->valid_before = cert_valid_to;
1750 		prepare_options_buf(public->cert->critical, OPTIONS_CRITICAL);
1751 		prepare_options_buf(public->cert->extensions,
1752 		    OPTIONS_EXTENSIONS);
1753 		if ((r = sshkey_from_private(ca,
1754 		    &public->cert->signature_key)) != 0)
1755 			fatal("sshkey_from_private (ca key): %s", ssh_err(r));
1756 
1757 		if (agent_fd != -1 && (ca->flags & SSHKEY_FLAG_EXT) != 0) {
1758 			if ((r = sshkey_certify_custom(public, ca,
1759 			    key_type_name, agent_signer, &agent_fd)) != 0)
1760 				fatal("Couldn't certify key %s via agent: %s",
1761 				    tmp, ssh_err(r));
1762 		} else {
1763 			if ((sshkey_certify(public, ca, key_type_name)) != 0)
1764 				fatal("Couldn't certify key %s: %s",
1765 				    tmp, ssh_err(r));
1766 		}
1767 
1768 		if ((cp = strrchr(tmp, '.')) != NULL && strcmp(cp, ".pub") == 0)
1769 			*cp = '\0';
1770 		xasprintf(&out, "%s-cert.pub", tmp);
1771 		free(tmp);
1772 
1773 		if ((fd = open(out, O_WRONLY|O_CREAT|O_TRUNC, 0644)) == -1)
1774 			fatal("Could not open \"%s\" for writing: %s", out,
1775 			    strerror(errno));
1776 		if ((f = fdopen(fd, "w")) == NULL)
1777 			fatal("%s: fdopen: %s", __func__, strerror(errno));
1778 		if ((r = sshkey_write(public, f)) != 0)
1779 			fatal("Could not write certified key to %s: %s",
1780 			    out, ssh_err(r));
1781 		fprintf(f, " %s\n", comment);
1782 		fclose(f);
1783 
1784 		if (!quiet) {
1785 			sshkey_format_cert_validity(public->cert,
1786 			    valid, sizeof(valid));
1787 			logit("Signed %s key %s: id \"%s\" serial %llu%s%s "
1788 			    "valid %s", sshkey_cert_type(public),
1789 			    out, public->cert->key_id,
1790 			    (unsigned long long)public->cert->serial,
1791 			    cert_principals != NULL ? " for " : "",
1792 			    cert_principals != NULL ? cert_principals : "",
1793 			    valid);
1794 		}
1795 
1796 		sshkey_free(public);
1797 		free(out);
1798 	}
1799 #ifdef ENABLE_PKCS11
1800 	pkcs11_terminate();
1801 #endif
1802 	exit(0);
1803 }
1804 
1805 static u_int64_t
1806 parse_relative_time(const char *s, time_t now)
1807 {
1808 	int64_t mul, secs;
1809 
1810 	mul = *s == '-' ? -1 : 1;
1811 
1812 	if ((secs = convtime(s + 1)) == -1)
1813 		fatal("Invalid relative certificate time %s", s);
1814 	if (mul == -1 && secs > now)
1815 		fatal("Certificate time %s cannot be represented", s);
1816 	return now + (u_int64_t)(secs * mul);
1817 }
1818 
1819 static void
1820 parse_cert_times(char *timespec)
1821 {
1822 	char *from, *to;
1823 	time_t now = time(NULL);
1824 	int64_t secs;
1825 
1826 	/* +timespec relative to now */
1827 	if (*timespec == '+' && strchr(timespec, ':') == NULL) {
1828 		if ((secs = convtime(timespec + 1)) == -1)
1829 			fatal("Invalid relative certificate life %s", timespec);
1830 		cert_valid_to = now + secs;
1831 		/*
1832 		 * Backdate certificate one minute to avoid problems on hosts
1833 		 * with poorly-synchronised clocks.
1834 		 */
1835 		cert_valid_from = ((now - 59)/ 60) * 60;
1836 		return;
1837 	}
1838 
1839 	/*
1840 	 * from:to, where
1841 	 * from := [+-]timespec | YYYYMMDD | YYYYMMDDHHMMSS | "always"
1842 	 *   to := [+-]timespec | YYYYMMDD | YYYYMMDDHHMMSS | "forever"
1843 	 */
1844 	from = xstrdup(timespec);
1845 	to = strchr(from, ':');
1846 	if (to == NULL || from == to || *(to + 1) == '\0')
1847 		fatal("Invalid certificate life specification %s", timespec);
1848 	*to++ = '\0';
1849 
1850 	if (*from == '-' || *from == '+')
1851 		cert_valid_from = parse_relative_time(from, now);
1852 	else if (strcmp(from, "always") == 0)
1853 		cert_valid_from = 0;
1854 	else if (parse_absolute_time(from, &cert_valid_from) != 0)
1855 		fatal("Invalid from time \"%s\"", from);
1856 
1857 	if (*to == '-' || *to == '+')
1858 		cert_valid_to = parse_relative_time(to, now);
1859 	else if (strcmp(to, "forever") == 0)
1860 		cert_valid_to = ~(u_int64_t)0;
1861 	else if (parse_absolute_time(to, &cert_valid_to) != 0)
1862 		fatal("Invalid to time \"%s\"", to);
1863 
1864 	if (cert_valid_to <= cert_valid_from)
1865 		fatal("Empty certificate validity interval");
1866 	free(from);
1867 }
1868 
1869 static void
1870 add_cert_option(char *opt)
1871 {
1872 	char *val, *cp;
1873 	int iscrit = 0;
1874 
1875 	if (strcasecmp(opt, "clear") == 0)
1876 		certflags_flags = 0;
1877 	else if (strcasecmp(opt, "no-x11-forwarding") == 0)
1878 		certflags_flags &= ~CERTOPT_X_FWD;
1879 	else if (strcasecmp(opt, "permit-x11-forwarding") == 0)
1880 		certflags_flags |= CERTOPT_X_FWD;
1881 	else if (strcasecmp(opt, "no-agent-forwarding") == 0)
1882 		certflags_flags &= ~CERTOPT_AGENT_FWD;
1883 	else if (strcasecmp(opt, "permit-agent-forwarding") == 0)
1884 		certflags_flags |= CERTOPT_AGENT_FWD;
1885 	else if (strcasecmp(opt, "no-port-forwarding") == 0)
1886 		certflags_flags &= ~CERTOPT_PORT_FWD;
1887 	else if (strcasecmp(opt, "permit-port-forwarding") == 0)
1888 		certflags_flags |= CERTOPT_PORT_FWD;
1889 	else if (strcasecmp(opt, "no-pty") == 0)
1890 		certflags_flags &= ~CERTOPT_PTY;
1891 	else if (strcasecmp(opt, "permit-pty") == 0)
1892 		certflags_flags |= CERTOPT_PTY;
1893 	else if (strcasecmp(opt, "no-user-rc") == 0)
1894 		certflags_flags &= ~CERTOPT_USER_RC;
1895 	else if (strcasecmp(opt, "permit-user-rc") == 0)
1896 		certflags_flags |= CERTOPT_USER_RC;
1897 	else if (strncasecmp(opt, "force-command=", 14) == 0) {
1898 		val = opt + 14;
1899 		if (*val == '\0')
1900 			fatal("Empty force-command option");
1901 		if (certflags_command != NULL)
1902 			fatal("force-command already specified");
1903 		certflags_command = xstrdup(val);
1904 	} else if (strncasecmp(opt, "source-address=", 15) == 0) {
1905 		val = opt + 15;
1906 		if (*val == '\0')
1907 			fatal("Empty source-address option");
1908 		if (certflags_src_addr != NULL)
1909 			fatal("source-address already specified");
1910 		if (addr_match_cidr_list(NULL, val) != 0)
1911 			fatal("Invalid source-address list");
1912 		certflags_src_addr = xstrdup(val);
1913 	} else if (strncasecmp(opt, "extension:", 10) == 0 ||
1914 		   (iscrit = (strncasecmp(opt, "critical:", 9) == 0))) {
1915 		val = xstrdup(strchr(opt, ':') + 1);
1916 		if ((cp = strchr(val, '=')) != NULL)
1917 			*cp++ = '\0';
1918 		cert_userext = xreallocarray(cert_userext, ncert_userext + 1,
1919 		    sizeof(*cert_userext));
1920 		cert_userext[ncert_userext].key = val;
1921 		cert_userext[ncert_userext].val = cp == NULL ?
1922 		    NULL : xstrdup(cp);
1923 		cert_userext[ncert_userext].crit = iscrit;
1924 		ncert_userext++;
1925 	} else
1926 		fatal("Unsupported certificate option \"%s\"", opt);
1927 }
1928 
1929 static void
1930 show_options(struct sshbuf *optbuf, int in_critical)
1931 {
1932 	char *name, *arg;
1933 	struct sshbuf *options, *option = NULL;
1934 	int r;
1935 
1936 	if ((options = sshbuf_fromb(optbuf)) == NULL)
1937 		fatal("%s: sshbuf_fromb failed", __func__);
1938 	while (sshbuf_len(options) != 0) {
1939 		sshbuf_free(option);
1940 		option = NULL;
1941 		if ((r = sshbuf_get_cstring(options, &name, NULL)) != 0 ||
1942 		    (r = sshbuf_froms(options, &option)) != 0)
1943 			fatal("%s: buffer error: %s", __func__, ssh_err(r));
1944 		printf("                %s", name);
1945 		if (!in_critical &&
1946 		    (strcmp(name, "permit-X11-forwarding") == 0 ||
1947 		    strcmp(name, "permit-agent-forwarding") == 0 ||
1948 		    strcmp(name, "permit-port-forwarding") == 0 ||
1949 		    strcmp(name, "permit-pty") == 0 ||
1950 		    strcmp(name, "permit-user-rc") == 0))
1951 			printf("\n");
1952 		else if (in_critical &&
1953 		    (strcmp(name, "force-command") == 0 ||
1954 		    strcmp(name, "source-address") == 0)) {
1955 			if ((r = sshbuf_get_cstring(option, &arg, NULL)) != 0)
1956 				fatal("%s: buffer error: %s",
1957 				    __func__, ssh_err(r));
1958 			printf(" %s\n", arg);
1959 			free(arg);
1960 		} else {
1961 			printf(" UNKNOWN OPTION (len %zu)\n",
1962 			    sshbuf_len(option));
1963 			sshbuf_reset(option);
1964 		}
1965 		free(name);
1966 		if (sshbuf_len(option) != 0)
1967 			fatal("Option corrupt: extra data at end");
1968 	}
1969 	sshbuf_free(option);
1970 	sshbuf_free(options);
1971 }
1972 
1973 static void
1974 print_cert(struct sshkey *key)
1975 {
1976 	char valid[64], *key_fp, *ca_fp;
1977 	u_int i;
1978 
1979 	key_fp = sshkey_fingerprint(key, fingerprint_hash, SSH_FP_DEFAULT);
1980 	ca_fp = sshkey_fingerprint(key->cert->signature_key,
1981 	    fingerprint_hash, SSH_FP_DEFAULT);
1982 	if (key_fp == NULL || ca_fp == NULL)
1983 		fatal("%s: sshkey_fingerprint fail", __func__);
1984 	sshkey_format_cert_validity(key->cert, valid, sizeof(valid));
1985 
1986 	printf("        Type: %s %s certificate\n", sshkey_ssh_name(key),
1987 	    sshkey_cert_type(key));
1988 	printf("        Public key: %s %s\n", sshkey_type(key), key_fp);
1989 	printf("        Signing CA: %s %s (using %s)\n",
1990 	    sshkey_type(key->cert->signature_key), ca_fp,
1991 	    key->cert->signature_type);
1992 	printf("        Key ID: \"%s\"\n", key->cert->key_id);
1993 	printf("        Serial: %llu\n", (unsigned long long)key->cert->serial);
1994 	printf("        Valid: %s\n", valid);
1995 	printf("        Principals: ");
1996 	if (key->cert->nprincipals == 0)
1997 		printf("(none)\n");
1998 	else {
1999 		for (i = 0; i < key->cert->nprincipals; i++)
2000 			printf("\n                %s",
2001 			    key->cert->principals[i]);
2002 		printf("\n");
2003 	}
2004 	printf("        Critical Options: ");
2005 	if (sshbuf_len(key->cert->critical) == 0)
2006 		printf("(none)\n");
2007 	else {
2008 		printf("\n");
2009 		show_options(key->cert->critical, 1);
2010 	}
2011 	printf("        Extensions: ");
2012 	if (sshbuf_len(key->cert->extensions) == 0)
2013 		printf("(none)\n");
2014 	else {
2015 		printf("\n");
2016 		show_options(key->cert->extensions, 0);
2017 	}
2018 }
2019 
2020 static void
2021 do_show_cert(struct passwd *pw)
2022 {
2023 	struct sshkey *key = NULL;
2024 	struct stat st;
2025 	int r, is_stdin = 0, ok = 0;
2026 	FILE *f;
2027 	char *cp, *line = NULL;
2028 	const char *path;
2029 	size_t linesize = 0;
2030 	u_long lnum = 0;
2031 
2032 	if (!have_identity)
2033 		ask_filename(pw, "Enter file in which the key is");
2034 	if (strcmp(identity_file, "-") != 0 && stat(identity_file, &st) < 0)
2035 		fatal("%s: %s: %s", __progname, identity_file, strerror(errno));
2036 
2037 	path = identity_file;
2038 	if (strcmp(path, "-") == 0) {
2039 		f = stdin;
2040 		path = "(stdin)";
2041 		is_stdin = 1;
2042 	} else if ((f = fopen(identity_file, "r")) == NULL)
2043 		fatal("fopen %s: %s", identity_file, strerror(errno));
2044 
2045 	while (getline(&line, &linesize, f) != -1) {
2046 		lnum++;
2047 		sshkey_free(key);
2048 		key = NULL;
2049 		/* Trim leading space and comments */
2050 		cp = line + strspn(line, " \t");
2051 		if (*cp == '#' || *cp == '\0')
2052 			continue;
2053 		if ((key = sshkey_new(KEY_UNSPEC)) == NULL)
2054 			fatal("sshkey_new");
2055 		if ((r = sshkey_read(key, &cp)) != 0) {
2056 			error("%s:%lu: invalid key: %s", path,
2057 			    lnum, ssh_err(r));
2058 			continue;
2059 		}
2060 		if (!sshkey_is_cert(key)) {
2061 			error("%s:%lu is not a certificate", path, lnum);
2062 			continue;
2063 		}
2064 		ok = 1;
2065 		if (!is_stdin && lnum == 1)
2066 			printf("%s:\n", path);
2067 		else
2068 			printf("%s:%lu:\n", path, lnum);
2069 		print_cert(key);
2070 	}
2071 	free(line);
2072 	sshkey_free(key);
2073 	fclose(f);
2074 	exit(ok ? 0 : 1);
2075 }
2076 
2077 #ifdef WITH_OPENSSL
2078 static void
2079 load_krl(const char *path, struct ssh_krl **krlp)
2080 {
2081 	struct sshbuf *krlbuf;
2082 	int r, fd;
2083 
2084 	if ((krlbuf = sshbuf_new()) == NULL)
2085 		fatal("sshbuf_new failed");
2086 	if ((fd = open(path, O_RDONLY)) == -1)
2087 		fatal("open %s: %s", path, strerror(errno));
2088 	if ((r = sshkey_load_file(fd, krlbuf)) != 0)
2089 		fatal("Unable to load KRL: %s", ssh_err(r));
2090 	close(fd);
2091 	/* XXX check sigs */
2092 	if ((r = ssh_krl_from_blob(krlbuf, krlp, NULL, 0)) != 0 ||
2093 	    *krlp == NULL)
2094 		fatal("Invalid KRL file: %s", ssh_err(r));
2095 	sshbuf_free(krlbuf);
2096 }
2097 
2098 static void
2099 hash_to_blob(const char *cp, u_char **blobp, size_t *lenp,
2100     const char *file, u_long lnum)
2101 {
2102 	char *tmp;
2103 	size_t tlen;
2104 	struct sshbuf *b;
2105 	int r;
2106 
2107 	if (strncmp(cp, "SHA256:", 7) != 0)
2108 		fatal("%s:%lu: unsupported hash algorithm", file, lnum);
2109 	cp += 7;
2110 
2111 	/*
2112 	 * OpenSSH base64 hashes omit trailing '='
2113 	 * characters; put them back for decode.
2114 	 */
2115 	tlen = strlen(cp);
2116 	tmp = xmalloc(tlen + 4 + 1);
2117 	strlcpy(tmp, cp, tlen + 1);
2118 	while ((tlen % 4) != 0) {
2119 		tmp[tlen++] = '=';
2120 		tmp[tlen] = '\0';
2121 	}
2122 	if ((b = sshbuf_new()) == NULL)
2123 		fatal("%s: sshbuf_new failed", __func__);
2124 	if ((r = sshbuf_b64tod(b, tmp)) != 0)
2125 		fatal("%s:%lu: decode hash failed: %s", file, lnum, ssh_err(r));
2126 	free(tmp);
2127 	*lenp = sshbuf_len(b);
2128 	*blobp = xmalloc(*lenp);
2129 	memcpy(*blobp, sshbuf_ptr(b), *lenp);
2130 	sshbuf_free(b);
2131 }
2132 
2133 static void
2134 update_krl_from_file(struct passwd *pw, const char *file, int wild_ca,
2135     const struct sshkey *ca, struct ssh_krl *krl)
2136 {
2137 	struct sshkey *key = NULL;
2138 	u_long lnum = 0;
2139 	char *path, *cp, *ep, *line = NULL;
2140 	u_char *blob = NULL;
2141 	size_t blen = 0, linesize = 0;
2142 	unsigned long long serial, serial2;
2143 	int i, was_explicit_key, was_sha1, was_sha256, was_hash, r;
2144 	FILE *krl_spec;
2145 
2146 	path = tilde_expand_filename(file, pw->pw_uid);
2147 	if (strcmp(path, "-") == 0) {
2148 		krl_spec = stdin;
2149 		free(path);
2150 		path = xstrdup("(standard input)");
2151 	} else if ((krl_spec = fopen(path, "r")) == NULL)
2152 		fatal("fopen %s: %s", path, strerror(errno));
2153 
2154 	if (!quiet)
2155 		printf("Revoking from %s\n", path);
2156 	while (getline(&line, &linesize, krl_spec) != -1) {
2157 		lnum++;
2158 		was_explicit_key = was_sha1 = was_sha256 = was_hash = 0;
2159 		cp = line + strspn(line, " \t");
2160 		/* Trim trailing space, comments and strip \n */
2161 		for (i = 0, r = -1; cp[i] != '\0'; i++) {
2162 			if (cp[i] == '#' || cp[i] == '\n') {
2163 				cp[i] = '\0';
2164 				break;
2165 			}
2166 			if (cp[i] == ' ' || cp[i] == '\t') {
2167 				/* Remember the start of a span of whitespace */
2168 				if (r == -1)
2169 					r = i;
2170 			} else
2171 				r = -1;
2172 		}
2173 		if (r != -1)
2174 			cp[r] = '\0';
2175 		if (*cp == '\0')
2176 			continue;
2177 		if (strncasecmp(cp, "serial:", 7) == 0) {
2178 			if (ca == NULL && !wild_ca) {
2179 				fatal("revoking certificates by serial number "
2180 				    "requires specification of a CA key");
2181 			}
2182 			cp += 7;
2183 			cp = cp + strspn(cp, " \t");
2184 			errno = 0;
2185 			serial = strtoull(cp, &ep, 0);
2186 			if (*cp == '\0' || (*ep != '\0' && *ep != '-'))
2187 				fatal("%s:%lu: invalid serial \"%s\"",
2188 				    path, lnum, cp);
2189 			if (errno == ERANGE && serial == ULLONG_MAX)
2190 				fatal("%s:%lu: serial out of range",
2191 				    path, lnum);
2192 			serial2 = serial;
2193 			if (*ep == '-') {
2194 				cp = ep + 1;
2195 				errno = 0;
2196 				serial2 = strtoull(cp, &ep, 0);
2197 				if (*cp == '\0' || *ep != '\0')
2198 					fatal("%s:%lu: invalid serial \"%s\"",
2199 					    path, lnum, cp);
2200 				if (errno == ERANGE && serial2 == ULLONG_MAX)
2201 					fatal("%s:%lu: serial out of range",
2202 					    path, lnum);
2203 				if (serial2 <= serial)
2204 					fatal("%s:%lu: invalid serial range "
2205 					    "%llu:%llu", path, lnum,
2206 					    (unsigned long long)serial,
2207 					    (unsigned long long)serial2);
2208 			}
2209 			if (ssh_krl_revoke_cert_by_serial_range(krl,
2210 			    ca, serial, serial2) != 0) {
2211 				fatal("%s: revoke serial failed",
2212 				    __func__);
2213 			}
2214 		} else if (strncasecmp(cp, "id:", 3) == 0) {
2215 			if (ca == NULL && !wild_ca) {
2216 				fatal("revoking certificates by key ID "
2217 				    "requires specification of a CA key");
2218 			}
2219 			cp += 3;
2220 			cp = cp + strspn(cp, " \t");
2221 			if (ssh_krl_revoke_cert_by_key_id(krl, ca, cp) != 0)
2222 				fatal("%s: revoke key ID failed", __func__);
2223 		} else if (strncasecmp(cp, "hash:", 5) == 0) {
2224 			cp += 5;
2225 			cp = cp + strspn(cp, " \t");
2226 			hash_to_blob(cp, &blob, &blen, file, lnum);
2227 			r = ssh_krl_revoke_key_sha256(krl, blob, blen);
2228 		} else {
2229 			if (strncasecmp(cp, "key:", 4) == 0) {
2230 				cp += 4;
2231 				cp = cp + strspn(cp, " \t");
2232 				was_explicit_key = 1;
2233 			} else if (strncasecmp(cp, "sha1:", 5) == 0) {
2234 				cp += 5;
2235 				cp = cp + strspn(cp, " \t");
2236 				was_sha1 = 1;
2237 			} else if (strncasecmp(cp, "sha256:", 7) == 0) {
2238 				cp += 7;
2239 				cp = cp + strspn(cp, " \t");
2240 				was_sha256 = 1;
2241 				/*
2242 				 * Just try to process the line as a key.
2243 				 * Parsing will fail if it isn't.
2244 				 */
2245 			}
2246 			if ((key = sshkey_new(KEY_UNSPEC)) == NULL)
2247 				fatal("sshkey_new");
2248 			if ((r = sshkey_read(key, &cp)) != 0)
2249 				fatal("%s:%lu: invalid key: %s",
2250 				    path, lnum, ssh_err(r));
2251 			if (was_explicit_key)
2252 				r = ssh_krl_revoke_key_explicit(krl, key);
2253 			else if (was_sha1) {
2254 				if (sshkey_fingerprint_raw(key,
2255 				    SSH_DIGEST_SHA1, &blob, &blen) != 0) {
2256 					fatal("%s:%lu: fingerprint failed",
2257 					    file, lnum);
2258 				}
2259 				r = ssh_krl_revoke_key_sha1(krl, blob, blen);
2260 			} else if (was_sha256) {
2261 				if (sshkey_fingerprint_raw(key,
2262 				    SSH_DIGEST_SHA256, &blob, &blen) != 0) {
2263 					fatal("%s:%lu: fingerprint failed",
2264 					    file, lnum);
2265 				}
2266 				r = ssh_krl_revoke_key_sha256(krl, blob, blen);
2267 			} else
2268 				r = ssh_krl_revoke_key(krl, key);
2269 			if (r != 0)
2270 				fatal("%s: revoke key failed: %s",
2271 				    __func__, ssh_err(r));
2272 			freezero(blob, blen);
2273 			blob = NULL;
2274 			blen = 0;
2275 			sshkey_free(key);
2276 		}
2277 	}
2278 	if (strcmp(path, "-") != 0)
2279 		fclose(krl_spec);
2280 	free(line);
2281 	free(path);
2282 }
2283 
2284 static void
2285 do_gen_krl(struct passwd *pw, int updating, int argc, char **argv)
2286 {
2287 	struct ssh_krl *krl;
2288 	struct stat sb;
2289 	struct sshkey *ca = NULL;
2290 	int fd, i, r, wild_ca = 0;
2291 	char *tmp;
2292 	struct sshbuf *kbuf;
2293 
2294 	if (*identity_file == '\0')
2295 		fatal("KRL generation requires an output file");
2296 	if (stat(identity_file, &sb) == -1) {
2297 		if (errno != ENOENT)
2298 			fatal("Cannot access KRL \"%s\": %s",
2299 			    identity_file, strerror(errno));
2300 		if (updating)
2301 			fatal("KRL \"%s\" does not exist", identity_file);
2302 	}
2303 	if (ca_key_path != NULL) {
2304 		if (strcasecmp(ca_key_path, "none") == 0)
2305 			wild_ca = 1;
2306 		else {
2307 			tmp = tilde_expand_filename(ca_key_path, pw->pw_uid);
2308 			if ((r = sshkey_load_public(tmp, &ca, NULL)) != 0)
2309 				fatal("Cannot load CA public key %s: %s",
2310 				    tmp, ssh_err(r));
2311 			free(tmp);
2312 		}
2313 	}
2314 
2315 	if (updating)
2316 		load_krl(identity_file, &krl);
2317 	else if ((krl = ssh_krl_init()) == NULL)
2318 		fatal("couldn't create KRL");
2319 
2320 	if (cert_serial != 0)
2321 		ssh_krl_set_version(krl, cert_serial);
2322 	if (identity_comment != NULL)
2323 		ssh_krl_set_comment(krl, identity_comment);
2324 
2325 	for (i = 0; i < argc; i++)
2326 		update_krl_from_file(pw, argv[i], wild_ca, ca, krl);
2327 
2328 	if ((kbuf = sshbuf_new()) == NULL)
2329 		fatal("sshbuf_new failed");
2330 	if (ssh_krl_to_blob(krl, kbuf, NULL, 0) != 0)
2331 		fatal("Couldn't generate KRL");
2332 	if ((fd = open(identity_file, O_WRONLY|O_CREAT|O_TRUNC, 0644)) == -1)
2333 		fatal("open %s: %s", identity_file, strerror(errno));
2334 	if (atomicio(vwrite, fd, sshbuf_mutable_ptr(kbuf), sshbuf_len(kbuf)) !=
2335 	    sshbuf_len(kbuf))
2336 		fatal("write %s: %s", identity_file, strerror(errno));
2337 	close(fd);
2338 	sshbuf_free(kbuf);
2339 	ssh_krl_free(krl);
2340 	sshkey_free(ca);
2341 }
2342 
2343 static void
2344 do_check_krl(struct passwd *pw, int argc, char **argv)
2345 {
2346 	int i, r, ret = 0;
2347 	char *comment;
2348 	struct ssh_krl *krl;
2349 	struct sshkey *k;
2350 
2351 	if (*identity_file == '\0')
2352 		fatal("KRL checking requires an input file");
2353 	load_krl(identity_file, &krl);
2354 	for (i = 0; i < argc; i++) {
2355 		if ((r = sshkey_load_public(argv[i], &k, &comment)) != 0)
2356 			fatal("Cannot load public key %s: %s",
2357 			    argv[i], ssh_err(r));
2358 		r = ssh_krl_check_key(krl, k);
2359 		printf("%s%s%s%s: %s\n", argv[i],
2360 		    *comment ? " (" : "", comment, *comment ? ")" : "",
2361 		    r == 0 ? "ok" : "REVOKED");
2362 		if (r != 0)
2363 			ret = 1;
2364 		sshkey_free(k);
2365 		free(comment);
2366 	}
2367 	ssh_krl_free(krl);
2368 	exit(ret);
2369 }
2370 #endif
2371 
2372 static void
2373 usage(void)
2374 {
2375 	fprintf(stderr,
2376 	    "usage: ssh-keygen [-q] [-b bits] [-t dsa | ecdsa | ed25519 | rsa]\n"
2377 	    "                  [-N new_passphrase] [-C comment] [-f output_keyfile]\n"
2378 	    "       ssh-keygen -p [-P old_passphrase] [-N new_passphrase] [-f keyfile]\n"
2379 	    "       ssh-keygen -i [-m key_format] [-f input_keyfile]\n"
2380 	    "       ssh-keygen -e [-m key_format] [-f input_keyfile]\n"
2381 	    "       ssh-keygen -y [-f input_keyfile]\n"
2382 	    "       ssh-keygen -c [-P passphrase] [-C comment] [-f keyfile]\n"
2383 	    "       ssh-keygen -l [-v] [-E fingerprint_hash] [-f input_keyfile]\n"
2384 	    "       ssh-keygen -B [-f input_keyfile]\n");
2385 #ifdef ENABLE_PKCS11
2386 	fprintf(stderr,
2387 	    "       ssh-keygen -D pkcs11\n");
2388 #endif
2389 	fprintf(stderr,
2390 	    "       ssh-keygen -F hostname [-f known_hosts_file] [-l]\n"
2391 	    "       ssh-keygen -H [-f known_hosts_file]\n"
2392 	    "       ssh-keygen -R hostname [-f known_hosts_file]\n"
2393 	    "       ssh-keygen -r hostname [-f input_keyfile] [-g]\n"
2394 #ifdef WITH_OPENSSL
2395 	    "       ssh-keygen -G output_file [-v] [-b bits] [-M memory] [-S start_point]\n"
2396 	    "       ssh-keygen -T output_file -f input_file [-v] [-a rounds] [-J num_lines]\n"
2397 	    "                  [-j start_line] [-K checkpt] [-W generator]\n"
2398 #endif
2399 	    "       ssh-keygen -s ca_key -I certificate_identity [-h] [-U]\n"
2400 	    "                  [-D pkcs11_provider] [-n principals] [-O option]\n"
2401 	    "                  [-V validity_interval] [-z serial_number] file ...\n"
2402 	    "       ssh-keygen -L [-f input_keyfile]\n"
2403 	    "       ssh-keygen -A\n"
2404 	    "       ssh-keygen -k -f krl_file [-u] [-s ca_public] [-z version_number]\n"
2405 	    "                  file ...\n"
2406 	    "       ssh-keygen -Q -f krl_file file ...\n");
2407 	exit(1);
2408 }
2409 
2410 /*
2411  * Main program for key management.
2412  */
2413 int
2414 main(int argc, char **argv)
2415 {
2416 	char dotsshdir[PATH_MAX], comment[1024], *passphrase1, *passphrase2;
2417 	char *rr_hostname = NULL, *ep, *fp, *ra;
2418 	struct sshkey *private, *public;
2419 	struct passwd *pw;
2420 	struct stat st;
2421 	int r, opt, type, fd;
2422 	int gen_all_hostkeys = 0, gen_krl = 0, update_krl = 0, check_krl = 0;
2423 	FILE *f;
2424 	const char *errstr;
2425 #ifdef WITH_OPENSSL
2426 	/* Moduli generation/screening */
2427 	char out_file[PATH_MAX], *checkpoint = NULL;
2428 	u_int32_t memory = 0, generator_wanted = 0;
2429 	int do_gen_candidates = 0, do_screen_candidates = 0;
2430 	unsigned long start_lineno = 0, lines_to_process = 0;
2431 	BIGNUM *start = NULL;
2432 #endif
2433 
2434 	extern int optind;
2435 	extern char *optarg;
2436 
2437 	ssh_malloc_init();	/* must be called before any mallocs */
2438 	/* Ensure that fds 0, 1 and 2 are open or directed to /dev/null */
2439 	sanitise_stdfd();
2440 
2441 	OpenSSL_add_all_algorithms();
2442 	log_init(argv[0], SYSLOG_LEVEL_INFO, SYSLOG_FACILITY_USER, 1);
2443 
2444 	setlocale(LC_CTYPE, "");
2445 
2446 	/* we need this for the home * directory.  */
2447 	pw = getpwuid(getuid());
2448 	if (!pw)
2449 		fatal("No user exists for uid %lu", (u_long)getuid());
2450 	if (gethostname(hostname, sizeof(hostname)) < 0)
2451 		fatal("gethostname: %s", strerror(errno));
2452 
2453 	/* Remaining characters: Ydw */
2454 	while ((opt = getopt(argc, argv, "ABHLQUXceghiklopquvxy"
2455 	    "C:D:E:F:G:I:J:K:M:N:O:P:R:S:T:V:W:Z:"
2456 	    "a:b:f:g:j:m:n:r:s:t:z:")) != -1) {
2457 		switch (opt) {
2458 		case 'A':
2459 			gen_all_hostkeys = 1;
2460 			break;
2461 		case 'b':
2462 			bits = (u_int32_t)strtonum(optarg, 10, 32768, &errstr);
2463 			if (errstr)
2464 				fatal("Bits has bad value %s (%s)",
2465 					optarg, errstr);
2466 			break;
2467 		case 'E':
2468 			fingerprint_hash = ssh_digest_alg_by_name(optarg);
2469 			if (fingerprint_hash == -1)
2470 				fatal("Invalid hash algorithm \"%s\"", optarg);
2471 			break;
2472 		case 'F':
2473 			find_host = 1;
2474 			rr_hostname = optarg;
2475 			break;
2476 		case 'H':
2477 			hash_hosts = 1;
2478 			break;
2479 		case 'I':
2480 			cert_key_id = optarg;
2481 			break;
2482 		case 'R':
2483 			delete_host = 1;
2484 			rr_hostname = optarg;
2485 			break;
2486 		case 'L':
2487 			show_cert = 1;
2488 			break;
2489 		case 'l':
2490 			print_fingerprint = 1;
2491 			break;
2492 		case 'B':
2493 			print_bubblebabble = 1;
2494 			break;
2495 		case 'm':
2496 			if (strcasecmp(optarg, "RFC4716") == 0 ||
2497 			    strcasecmp(optarg, "ssh2") == 0) {
2498 				convert_format = FMT_RFC4716;
2499 				break;
2500 			}
2501 			if (strcasecmp(optarg, "PKCS8") == 0) {
2502 				convert_format = FMT_PKCS8;
2503 				break;
2504 			}
2505 			if (strcasecmp(optarg, "PEM") == 0) {
2506 				convert_format = FMT_PEM;
2507 				use_new_format = 0;
2508 				break;
2509 			}
2510 			fatal("Unsupported conversion format \"%s\"", optarg);
2511 		case 'n':
2512 			cert_principals = optarg;
2513 			break;
2514 		case 'o':
2515 			/* no-op; new format is already the default */
2516 			break;
2517 		case 'p':
2518 			change_passphrase = 1;
2519 			break;
2520 		case 'c':
2521 			change_comment = 1;
2522 			break;
2523 		case 'f':
2524 			if (strlcpy(identity_file, optarg,
2525 			    sizeof(identity_file)) >= sizeof(identity_file))
2526 				fatal("Identity filename too long");
2527 			have_identity = 1;
2528 			break;
2529 		case 'g':
2530 			print_generic = 1;
2531 			break;
2532 		case 'P':
2533 			identity_passphrase = optarg;
2534 			break;
2535 		case 'N':
2536 			identity_new_passphrase = optarg;
2537 			break;
2538 		case 'Q':
2539 			check_krl = 1;
2540 			break;
2541 		case 'O':
2542 			add_cert_option(optarg);
2543 			break;
2544 		case 'Z':
2545 			new_format_cipher = optarg;
2546 			break;
2547 		case 'C':
2548 			identity_comment = optarg;
2549 			break;
2550 		case 'q':
2551 			quiet = 1;
2552 			break;
2553 		case 'e':
2554 		case 'x':
2555 			/* export key */
2556 			convert_to = 1;
2557 			break;
2558 		case 'h':
2559 			cert_key_type = SSH2_CERT_TYPE_HOST;
2560 			certflags_flags = 0;
2561 			break;
2562 		case 'k':
2563 			gen_krl = 1;
2564 			break;
2565 		case 'i':
2566 		case 'X':
2567 			/* import key */
2568 			convert_from = 1;
2569 			break;
2570 		case 'y':
2571 			print_public = 1;
2572 			break;
2573 		case 's':
2574 			ca_key_path = optarg;
2575 			break;
2576 		case 't':
2577 			key_type_name = optarg;
2578 			break;
2579 		case 'D':
2580 			pkcs11provider = optarg;
2581 			break;
2582 		case 'U':
2583 			prefer_agent = 1;
2584 			break;
2585 		case 'u':
2586 			update_krl = 1;
2587 			break;
2588 		case 'v':
2589 			if (log_level == SYSLOG_LEVEL_INFO)
2590 				log_level = SYSLOG_LEVEL_DEBUG1;
2591 			else {
2592 				if (log_level >= SYSLOG_LEVEL_DEBUG1 &&
2593 				    log_level < SYSLOG_LEVEL_DEBUG3)
2594 					log_level++;
2595 			}
2596 			break;
2597 		case 'r':
2598 			rr_hostname = optarg;
2599 			break;
2600 		case 'a':
2601 			rounds = (int)strtonum(optarg, 1, INT_MAX, &errstr);
2602 			if (errstr)
2603 				fatal("Invalid number: %s (%s)",
2604 					optarg, errstr);
2605 			break;
2606 		case 'V':
2607 			parse_cert_times(optarg);
2608 			break;
2609 		case 'z':
2610 			errno = 0;
2611 			cert_serial = strtoull(optarg, &ep, 10);
2612 			if (*optarg < '0' || *optarg > '9' || *ep != '\0' ||
2613 			    (errno == ERANGE && cert_serial == ULLONG_MAX))
2614 				fatal("Invalid serial number \"%s\"", optarg);
2615 			break;
2616 #ifdef WITH_OPENSSL
2617 		/* Moduli generation/screening */
2618 		case 'G':
2619 			do_gen_candidates = 1;
2620 			if (strlcpy(out_file, optarg, sizeof(out_file)) >=
2621 			    sizeof(out_file))
2622 				fatal("Output filename too long");
2623 			break;
2624 		case 'J':
2625 			lines_to_process = strtoul(optarg, NULL, 10);
2626 			break;
2627 		case 'j':
2628 			start_lineno = strtoul(optarg, NULL, 10);
2629 			break;
2630 		case 'K':
2631 			if (strlen(optarg) >= PATH_MAX)
2632 				fatal("Checkpoint filename too long");
2633 			checkpoint = xstrdup(optarg);
2634 			break;
2635 		case 'M':
2636 			memory = (u_int32_t)strtonum(optarg, 1, UINT_MAX,
2637 			    &errstr);
2638 			if (errstr)
2639 				fatal("Memory limit is %s: %s", errstr, optarg);
2640 			break;
2641 		case 'S':
2642 			/* XXX - also compare length against bits */
2643 			if (BN_hex2bn(&start, optarg) == 0)
2644 				fatal("Invalid start point.");
2645 			break;
2646 		case 'T':
2647 			do_screen_candidates = 1;
2648 			if (strlcpy(out_file, optarg, sizeof(out_file)) >=
2649 			    sizeof(out_file))
2650 				fatal("Output filename too long");
2651 			break;
2652 		case 'W':
2653 			generator_wanted = (u_int32_t)strtonum(optarg, 1,
2654 			    UINT_MAX, &errstr);
2655 			if (errstr != NULL)
2656 				fatal("Desired generator invalid: %s (%s)",
2657 				    optarg, errstr);
2658 			break;
2659 #endif /* WITH_OPENSSL */
2660 		case '?':
2661 		default:
2662 			usage();
2663 		}
2664 	}
2665 
2666 	/* reinit */
2667 	log_init(argv[0], log_level, SYSLOG_FACILITY_USER, 1);
2668 
2669 	argv += optind;
2670 	argc -= optind;
2671 
2672 	if (ca_key_path != NULL) {
2673 		if (argc < 1 && !gen_krl) {
2674 			error("Too few arguments.");
2675 			usage();
2676 		}
2677 	} else if (argc > 0 && !gen_krl && !check_krl) {
2678 		error("Too many arguments.");
2679 		usage();
2680 	}
2681 	if (change_passphrase && change_comment) {
2682 		error("Can only have one of -p and -c.");
2683 		usage();
2684 	}
2685 	if (print_fingerprint && (delete_host || hash_hosts)) {
2686 		error("Cannot use -l with -H or -R.");
2687 		usage();
2688 	}
2689 #ifdef WITH_OPENSSL
2690 	if (gen_krl) {
2691 		do_gen_krl(pw, update_krl, argc, argv);
2692 		return (0);
2693 	}
2694 	if (check_krl) {
2695 		do_check_krl(pw, argc, argv);
2696 		return (0);
2697 	}
2698 #endif
2699 	if (ca_key_path != NULL) {
2700 		if (cert_key_id == NULL)
2701 			fatal("Must specify key id (-I) when certifying");
2702 		do_ca_sign(pw, argc, argv);
2703 	}
2704 	if (show_cert)
2705 		do_show_cert(pw);
2706 	if (delete_host || hash_hosts || find_host)
2707 		do_known_hosts(pw, rr_hostname);
2708 	if (pkcs11provider != NULL)
2709 		do_download(pw);
2710 	if (print_fingerprint || print_bubblebabble)
2711 		do_fingerprint(pw);
2712 	if (change_passphrase)
2713 		do_change_passphrase(pw);
2714 	if (change_comment)
2715 		do_change_comment(pw);
2716 #ifdef WITH_OPENSSL
2717 	if (convert_to)
2718 		do_convert_to(pw);
2719 	if (convert_from)
2720 		do_convert_from(pw);
2721 #endif
2722 	if (print_public)
2723 		do_print_public(pw);
2724 	if (rr_hostname != NULL) {
2725 		unsigned int n = 0;
2726 
2727 		if (have_identity) {
2728 			n = do_print_resource_record(pw,
2729 			    identity_file, rr_hostname);
2730 			if (n == 0)
2731 				fatal("%s: %s", identity_file, strerror(errno));
2732 			exit(0);
2733 		} else {
2734 
2735 			n += do_print_resource_record(pw,
2736 			    _PATH_HOST_RSA_KEY_FILE, rr_hostname);
2737 			n += do_print_resource_record(pw,
2738 			    _PATH_HOST_DSA_KEY_FILE, rr_hostname);
2739 			n += do_print_resource_record(pw,
2740 			    _PATH_HOST_ECDSA_KEY_FILE, rr_hostname);
2741 			n += do_print_resource_record(pw,
2742 			    _PATH_HOST_ED25519_KEY_FILE, rr_hostname);
2743 			n += do_print_resource_record(pw,
2744 			    _PATH_HOST_XMSS_KEY_FILE, rr_hostname);
2745 			if (n == 0)
2746 				fatal("no keys found.");
2747 			exit(0);
2748 		}
2749 	}
2750 
2751 #ifdef WITH_OPENSSL
2752 	if (do_gen_candidates) {
2753 		FILE *out = fopen(out_file, "w");
2754 
2755 		if (out == NULL) {
2756 			error("Couldn't open modulus candidate file \"%s\": %s",
2757 			    out_file, strerror(errno));
2758 			return (1);
2759 		}
2760 		if (bits == 0)
2761 			bits = DEFAULT_BITS;
2762 		if (gen_candidates(out, memory, bits, start) != 0)
2763 			fatal("modulus candidate generation failed");
2764 
2765 		return (0);
2766 	}
2767 
2768 	if (do_screen_candidates) {
2769 		FILE *in;
2770 		FILE *out = fopen(out_file, "a");
2771 
2772 		if (have_identity && strcmp(identity_file, "-") != 0) {
2773 			if ((in = fopen(identity_file, "r")) == NULL) {
2774 				fatal("Couldn't open modulus candidate "
2775 				    "file \"%s\": %s", identity_file,
2776 				    strerror(errno));
2777 			}
2778 		} else
2779 			in = stdin;
2780 
2781 		if (out == NULL) {
2782 			fatal("Couldn't open moduli file \"%s\": %s",
2783 			    out_file, strerror(errno));
2784 		}
2785 		if (prime_test(in, out, rounds == 0 ? 100 : rounds,
2786 		    generator_wanted, checkpoint,
2787 		    start_lineno, lines_to_process) != 0)
2788 			fatal("modulus screening failed");
2789 		return (0);
2790 	}
2791 #endif
2792 
2793 	if (gen_all_hostkeys) {
2794 		do_gen_all_hostkeys(pw);
2795 		return (0);
2796 	}
2797 
2798 	if (key_type_name == NULL)
2799 		key_type_name = DEFAULT_KEY_TYPE_NAME;
2800 
2801 	type = sshkey_type_from_name(key_type_name);
2802 	type_bits_valid(type, key_type_name, &bits);
2803 
2804 	if (!quiet)
2805 		printf("Generating public/private %s key pair.\n",
2806 		    key_type_name);
2807 	if ((r = sshkey_generate(type, bits, &private)) != 0)
2808 		fatal("sshkey_generate failed");
2809 	if ((r = sshkey_from_private(private, &public)) != 0)
2810 		fatal("sshkey_from_private failed: %s\n", ssh_err(r));
2811 
2812 	if (!have_identity)
2813 		ask_filename(pw, "Enter file in which to save the key");
2814 
2815 	/* Create ~/.ssh directory if it doesn't already exist. */
2816 	snprintf(dotsshdir, sizeof dotsshdir, "%s/%s",
2817 	    pw->pw_dir, _PATH_SSH_USER_DIR);
2818 	if (strstr(identity_file, dotsshdir) != NULL) {
2819 		if (stat(dotsshdir, &st) < 0) {
2820 			if (errno != ENOENT) {
2821 				error("Could not stat %s: %s", dotsshdir,
2822 				    strerror(errno));
2823 			} else if (mkdir(dotsshdir, 0700) < 0) {
2824 				error("Could not create directory '%s': %s",
2825 				    dotsshdir, strerror(errno));
2826 			} else if (!quiet)
2827 				printf("Created directory '%s'.\n", dotsshdir);
2828 		}
2829 	}
2830 	/* If the file already exists, ask the user to confirm. */
2831 	if (stat(identity_file, &st) >= 0) {
2832 		char yesno[3];
2833 		printf("%s already exists.\n", identity_file);
2834 		printf("Overwrite (y/n)? ");
2835 		fflush(stdout);
2836 		if (fgets(yesno, sizeof(yesno), stdin) == NULL)
2837 			exit(1);
2838 		if (yesno[0] != 'y' && yesno[0] != 'Y')
2839 			exit(1);
2840 	}
2841 	/* Ask for a passphrase (twice). */
2842 	if (identity_passphrase)
2843 		passphrase1 = xstrdup(identity_passphrase);
2844 	else if (identity_new_passphrase)
2845 		passphrase1 = xstrdup(identity_new_passphrase);
2846 	else {
2847 passphrase_again:
2848 		passphrase1 =
2849 			read_passphrase("Enter passphrase (empty for no "
2850 			    "passphrase): ", RP_ALLOW_STDIN);
2851 		passphrase2 = read_passphrase("Enter same passphrase again: ",
2852 		    RP_ALLOW_STDIN);
2853 		if (strcmp(passphrase1, passphrase2) != 0) {
2854 			/*
2855 			 * The passphrases do not match.  Clear them and
2856 			 * retry.
2857 			 */
2858 			explicit_bzero(passphrase1, strlen(passphrase1));
2859 			explicit_bzero(passphrase2, strlen(passphrase2));
2860 			free(passphrase1);
2861 			free(passphrase2);
2862 			printf("Passphrases do not match.  Try again.\n");
2863 			goto passphrase_again;
2864 		}
2865 		/* Clear the other copy of the passphrase. */
2866 		explicit_bzero(passphrase2, strlen(passphrase2));
2867 		free(passphrase2);
2868 	}
2869 
2870 	if (identity_comment) {
2871 		strlcpy(comment, identity_comment, sizeof(comment));
2872 	} else {
2873 		/* Create default comment field for the passphrase. */
2874 		snprintf(comment, sizeof comment, "%s@%s", pw->pw_name, hostname);
2875 	}
2876 
2877 	/* Save the key with the given passphrase and comment. */
2878 	if ((r = sshkey_save_private(private, identity_file, passphrase1,
2879 	    comment, use_new_format, new_format_cipher, rounds)) != 0) {
2880 		error("Saving key \"%s\" failed: %s",
2881 		    identity_file, ssh_err(r));
2882 		explicit_bzero(passphrase1, strlen(passphrase1));
2883 		free(passphrase1);
2884 		exit(1);
2885 	}
2886 	/* Clear the passphrase. */
2887 	explicit_bzero(passphrase1, strlen(passphrase1));
2888 	free(passphrase1);
2889 
2890 	/* Clear the private key and the random number generator. */
2891 	sshkey_free(private);
2892 
2893 	if (!quiet)
2894 		printf("Your identification has been saved in %s.\n", identity_file);
2895 
2896 	strlcat(identity_file, ".pub", sizeof(identity_file));
2897 	if ((fd = open(identity_file, O_WRONLY|O_CREAT|O_TRUNC, 0644)) == -1)
2898 		fatal("Unable to save public key to %s: %s",
2899 		    identity_file, strerror(errno));
2900 	if ((f = fdopen(fd, "w")) == NULL)
2901 		fatal("fdopen %s failed: %s", identity_file, strerror(errno));
2902 	if ((r = sshkey_write(public, f)) != 0)
2903 		error("write key failed: %s", ssh_err(r));
2904 	fprintf(f, " %s\n", comment);
2905 	if (ferror(f) || fclose(f) != 0)
2906 		fatal("write public failed: %s", strerror(errno));
2907 
2908 	if (!quiet) {
2909 		fp = sshkey_fingerprint(public, fingerprint_hash,
2910 		    SSH_FP_DEFAULT);
2911 		ra = sshkey_fingerprint(public, fingerprint_hash,
2912 		    SSH_FP_RANDOMART);
2913 		if (fp == NULL || ra == NULL)
2914 			fatal("sshkey_fingerprint failed");
2915 		printf("Your public key has been saved in %s.\n",
2916 		    identity_file);
2917 		printf("The key fingerprint is:\n");
2918 		printf("%s %s\n", fp, comment);
2919 		printf("The key's randomart image is:\n");
2920 		printf("%s\n", ra);
2921 		free(ra);
2922 		free(fp);
2923 	}
2924 
2925 	sshkey_free(public);
2926 	exit(0);
2927 }
2928