xref: /freebsd/crypto/openssh/ssh-agent.c (revision 6af83ee0d2941d18880b6aaa2b4facd1d30c6106)
1 /*
2  * Author: Tatu Ylonen <ylo@cs.hut.fi>
3  * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
4  *                    All rights reserved
5  * The authentication agent program.
6  *
7  * As far as I am concerned, the code I have written for this software
8  * can be used freely for any purpose.  Any derived versions of this
9  * software must be clearly marked as such, and if the derived work is
10  * incompatible with the protocol description in the RFC file, it must be
11  * called by a name other than "ssh" or "Secure Shell".
12  *
13  * Copyright (c) 2000, 2001 Markus Friedl.  All rights reserved.
14  *
15  * Redistribution and use in source and binary forms, with or without
16  * modification, are permitted provided that the following conditions
17  * are met:
18  * 1. Redistributions of source code must retain the above copyright
19  *    notice, this list of conditions and the following disclaimer.
20  * 2. Redistributions in binary form must reproduce the above copyright
21  *    notice, this list of conditions and the following disclaimer in the
22  *    documentation and/or other materials provided with the distribution.
23  *
24  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
25  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
26  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
27  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
28  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
29  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
30  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
31  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
32  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
33  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
34  */
35 
36 #include "includes.h"
37 #include "openbsd-compat/sys-queue.h"
38 RCSID("$OpenBSD: ssh-agent.c,v 1.120 2004/08/11 21:43:05 avsm Exp $");
39 RCSID("$FreeBSD$");
40 
41 #include <openssl/evp.h>
42 #include <openssl/md5.h>
43 
44 #include "ssh.h"
45 #include "rsa.h"
46 #include "buffer.h"
47 #include "bufaux.h"
48 #include "xmalloc.h"
49 #include "getput.h"
50 #include "key.h"
51 #include "authfd.h"
52 #include "compat.h"
53 #include "log.h"
54 #include "misc.h"
55 
56 #ifdef SMARTCARD
57 #include "scard.h"
58 #endif
59 
60 #if defined(HAVE_SYS_PRCTL_H)
61 #include <sys/prctl.h>	/* For prctl() and PR_SET_DUMPABLE */
62 #endif
63 
64 typedef enum {
65 	AUTH_UNUSED,
66 	AUTH_SOCKET,
67 	AUTH_CONNECTION
68 } sock_type;
69 
70 typedef struct {
71 	int fd;
72 	sock_type type;
73 	Buffer input;
74 	Buffer output;
75 	Buffer request;
76 } SocketEntry;
77 
78 u_int sockets_alloc = 0;
79 SocketEntry *sockets = NULL;
80 
81 typedef struct identity {
82 	TAILQ_ENTRY(identity) next;
83 	Key *key;
84 	char *comment;
85 	u_int death;
86 	u_int confirm;
87 } Identity;
88 
89 typedef struct {
90 	int nentries;
91 	TAILQ_HEAD(idqueue, identity) idlist;
92 } Idtab;
93 
94 /* private key table, one per protocol version */
95 Idtab idtable[3];
96 
97 int max_fd = 0;
98 
99 /* pid of shell == parent of agent */
100 pid_t parent_pid = -1;
101 
102 /* pathname and directory for AUTH_SOCKET */
103 char socket_name[1024];
104 char socket_dir[1024];
105 
106 /* locking */
107 int locked = 0;
108 char *lock_passwd = NULL;
109 
110 extern char *__progname;
111 
112 /* Default lifetime (0 == forever) */
113 static int lifetime = 0;
114 
115 static void
116 close_socket(SocketEntry *e)
117 {
118 	close(e->fd);
119 	e->fd = -1;
120 	e->type = AUTH_UNUSED;
121 	buffer_free(&e->input);
122 	buffer_free(&e->output);
123 	buffer_free(&e->request);
124 }
125 
126 static void
127 idtab_init(void)
128 {
129 	int i;
130 
131 	for (i = 0; i <=2; i++) {
132 		TAILQ_INIT(&idtable[i].idlist);
133 		idtable[i].nentries = 0;
134 	}
135 }
136 
137 /* return private key table for requested protocol version */
138 static Idtab *
139 idtab_lookup(int version)
140 {
141 	if (version < 1 || version > 2)
142 		fatal("internal error, bad protocol version %d", version);
143 	return &idtable[version];
144 }
145 
146 static void
147 free_identity(Identity *id)
148 {
149 	key_free(id->key);
150 	xfree(id->comment);
151 	xfree(id);
152 }
153 
154 /* return matching private key for given public key */
155 static Identity *
156 lookup_identity(Key *key, int version)
157 {
158 	Identity *id;
159 
160 	Idtab *tab = idtab_lookup(version);
161 	TAILQ_FOREACH(id, &tab->idlist, next) {
162 		if (key_equal(key, id->key))
163 			return (id);
164 	}
165 	return (NULL);
166 }
167 
168 /* Check confirmation of keysign request */
169 static int
170 confirm_key(Identity *id)
171 {
172 	char *p, prompt[1024];
173 	int ret = -1;
174 
175 	p = key_fingerprint(id->key, SSH_FP_MD5, SSH_FP_HEX);
176 	snprintf(prompt, sizeof(prompt), "Allow use of key %s?\n"
177 	    "Key fingerprint %s.", id->comment, p);
178 	xfree(p);
179 	p = read_passphrase(prompt, RP_ALLOW_EOF);
180 	if (p != NULL) {
181 		/*
182 		 * Accept empty responses and responses consisting
183 		 * of the word "yes" as affirmative.
184 		 */
185 		if (*p == '\0' || *p == '\n' || strcasecmp(p, "yes") == 0)
186 			ret = 0;
187 		xfree(p);
188 	}
189 	return (ret);
190 }
191 
192 /* send list of supported public keys to 'client' */
193 static void
194 process_request_identities(SocketEntry *e, int version)
195 {
196 	Idtab *tab = idtab_lookup(version);
197 	Identity *id;
198 	Buffer msg;
199 
200 	buffer_init(&msg);
201 	buffer_put_char(&msg, (version == 1) ?
202 	    SSH_AGENT_RSA_IDENTITIES_ANSWER : SSH2_AGENT_IDENTITIES_ANSWER);
203 	buffer_put_int(&msg, tab->nentries);
204 	TAILQ_FOREACH(id, &tab->idlist, next) {
205 		if (id->key->type == KEY_RSA1) {
206 			buffer_put_int(&msg, BN_num_bits(id->key->rsa->n));
207 			buffer_put_bignum(&msg, id->key->rsa->e);
208 			buffer_put_bignum(&msg, id->key->rsa->n);
209 		} else {
210 			u_char *blob;
211 			u_int blen;
212 			key_to_blob(id->key, &blob, &blen);
213 			buffer_put_string(&msg, blob, blen);
214 			xfree(blob);
215 		}
216 		buffer_put_cstring(&msg, id->comment);
217 	}
218 	buffer_put_int(&e->output, buffer_len(&msg));
219 	buffer_append(&e->output, buffer_ptr(&msg), buffer_len(&msg));
220 	buffer_free(&msg);
221 }
222 
223 /* ssh1 only */
224 static void
225 process_authentication_challenge1(SocketEntry *e)
226 {
227 	u_char buf[32], mdbuf[16], session_id[16];
228 	u_int response_type;
229 	BIGNUM *challenge;
230 	Identity *id;
231 	int i, len;
232 	Buffer msg;
233 	MD5_CTX md;
234 	Key *key;
235 
236 	buffer_init(&msg);
237 	key = key_new(KEY_RSA1);
238 	if ((challenge = BN_new()) == NULL)
239 		fatal("process_authentication_challenge1: BN_new failed");
240 
241 	(void) buffer_get_int(&e->request);			/* ignored */
242 	buffer_get_bignum(&e->request, key->rsa->e);
243 	buffer_get_bignum(&e->request, key->rsa->n);
244 	buffer_get_bignum(&e->request, challenge);
245 
246 	/* Only protocol 1.1 is supported */
247 	if (buffer_len(&e->request) == 0)
248 		goto failure;
249 	buffer_get(&e->request, session_id, 16);
250 	response_type = buffer_get_int(&e->request);
251 	if (response_type != 1)
252 		goto failure;
253 
254 	id = lookup_identity(key, 1);
255 	if (id != NULL && (!id->confirm || confirm_key(id) == 0)) {
256 		Key *private = id->key;
257 		/* Decrypt the challenge using the private key. */
258 		if (rsa_private_decrypt(challenge, challenge, private->rsa) <= 0)
259 			goto failure;
260 
261 		/* The response is MD5 of decrypted challenge plus session id. */
262 		len = BN_num_bytes(challenge);
263 		if (len <= 0 || len > 32) {
264 			logit("process_authentication_challenge: bad challenge length %d", len);
265 			goto failure;
266 		}
267 		memset(buf, 0, 32);
268 		BN_bn2bin(challenge, buf + 32 - len);
269 		MD5_Init(&md);
270 		MD5_Update(&md, buf, 32);
271 		MD5_Update(&md, session_id, 16);
272 		MD5_Final(mdbuf, &md);
273 
274 		/* Send the response. */
275 		buffer_put_char(&msg, SSH_AGENT_RSA_RESPONSE);
276 		for (i = 0; i < 16; i++)
277 			buffer_put_char(&msg, mdbuf[i]);
278 		goto send;
279 	}
280 
281 failure:
282 	/* Unknown identity or protocol error.  Send failure. */
283 	buffer_put_char(&msg, SSH_AGENT_FAILURE);
284 send:
285 	buffer_put_int(&e->output, buffer_len(&msg));
286 	buffer_append(&e->output, buffer_ptr(&msg), buffer_len(&msg));
287 	key_free(key);
288 	BN_clear_free(challenge);
289 	buffer_free(&msg);
290 }
291 
292 /* ssh2 only */
293 static void
294 process_sign_request2(SocketEntry *e)
295 {
296 	u_char *blob, *data, *signature = NULL;
297 	u_int blen, dlen, slen = 0;
298 	extern int datafellows;
299 	int ok = -1, flags;
300 	Buffer msg;
301 	Key *key;
302 
303 	datafellows = 0;
304 
305 	blob = buffer_get_string(&e->request, &blen);
306 	data = buffer_get_string(&e->request, &dlen);
307 
308 	flags = buffer_get_int(&e->request);
309 	if (flags & SSH_AGENT_OLD_SIGNATURE)
310 		datafellows = SSH_BUG_SIGBLOB;
311 
312 	key = key_from_blob(blob, blen);
313 	if (key != NULL) {
314 		Identity *id = lookup_identity(key, 2);
315 		if (id != NULL && (!id->confirm || confirm_key(id) == 0))
316 			ok = key_sign(id->key, &signature, &slen, data, dlen);
317 	}
318 	key_free(key);
319 	buffer_init(&msg);
320 	if (ok == 0) {
321 		buffer_put_char(&msg, SSH2_AGENT_SIGN_RESPONSE);
322 		buffer_put_string(&msg, signature, slen);
323 	} else {
324 		buffer_put_char(&msg, SSH_AGENT_FAILURE);
325 	}
326 	buffer_put_int(&e->output, buffer_len(&msg));
327 	buffer_append(&e->output, buffer_ptr(&msg),
328 	    buffer_len(&msg));
329 	buffer_free(&msg);
330 	xfree(data);
331 	xfree(blob);
332 	if (signature != NULL)
333 		xfree(signature);
334 }
335 
336 /* shared */
337 static void
338 process_remove_identity(SocketEntry *e, int version)
339 {
340 	u_int blen, bits;
341 	int success = 0;
342 	Key *key = NULL;
343 	u_char *blob;
344 
345 	switch (version) {
346 	case 1:
347 		key = key_new(KEY_RSA1);
348 		bits = buffer_get_int(&e->request);
349 		buffer_get_bignum(&e->request, key->rsa->e);
350 		buffer_get_bignum(&e->request, key->rsa->n);
351 
352 		if (bits != key_size(key))
353 			logit("Warning: identity keysize mismatch: actual %u, announced %u",
354 			    key_size(key), bits);
355 		break;
356 	case 2:
357 		blob = buffer_get_string(&e->request, &blen);
358 		key = key_from_blob(blob, blen);
359 		xfree(blob);
360 		break;
361 	}
362 	if (key != NULL) {
363 		Identity *id = lookup_identity(key, version);
364 		if (id != NULL) {
365 			/*
366 			 * We have this key.  Free the old key.  Since we
367 			 * don\'t want to leave empty slots in the middle of
368 			 * the array, we actually free the key there and move
369 			 * all the entries between the empty slot and the end
370 			 * of the array.
371 			 */
372 			Idtab *tab = idtab_lookup(version);
373 			if (tab->nentries < 1)
374 				fatal("process_remove_identity: "
375 				    "internal error: tab->nentries %d",
376 				    tab->nentries);
377 			TAILQ_REMOVE(&tab->idlist, id, next);
378 			free_identity(id);
379 			tab->nentries--;
380 			success = 1;
381 		}
382 		key_free(key);
383 	}
384 	buffer_put_int(&e->output, 1);
385 	buffer_put_char(&e->output,
386 	    success ? SSH_AGENT_SUCCESS : SSH_AGENT_FAILURE);
387 }
388 
389 static void
390 process_remove_all_identities(SocketEntry *e, int version)
391 {
392 	Idtab *tab = idtab_lookup(version);
393 	Identity *id;
394 
395 	/* Loop over all identities and clear the keys. */
396 	for (id = TAILQ_FIRST(&tab->idlist); id;
397 	    id = TAILQ_FIRST(&tab->idlist)) {
398 		TAILQ_REMOVE(&tab->idlist, id, next);
399 		free_identity(id);
400 	}
401 
402 	/* Mark that there are no identities. */
403 	tab->nentries = 0;
404 
405 	/* Send success. */
406 	buffer_put_int(&e->output, 1);
407 	buffer_put_char(&e->output, SSH_AGENT_SUCCESS);
408 }
409 
410 static void
411 reaper(void)
412 {
413 	u_int now = time(NULL);
414 	Identity *id, *nxt;
415 	int version;
416 	Idtab *tab;
417 
418 	for (version = 1; version < 3; version++) {
419 		tab = idtab_lookup(version);
420 		for (id = TAILQ_FIRST(&tab->idlist); id; id = nxt) {
421 			nxt = TAILQ_NEXT(id, next);
422 			if (id->death != 0 && now >= id->death) {
423 				TAILQ_REMOVE(&tab->idlist, id, next);
424 				free_identity(id);
425 				tab->nentries--;
426 			}
427 		}
428 	}
429 }
430 
431 static void
432 process_add_identity(SocketEntry *e, int version)
433 {
434 	Idtab *tab = idtab_lookup(version);
435 	int type, success = 0, death = 0, confirm = 0;
436 	char *type_name, *comment;
437 	Key *k = NULL;
438 
439 	switch (version) {
440 	case 1:
441 		k = key_new_private(KEY_RSA1);
442 		(void) buffer_get_int(&e->request);		/* ignored */
443 		buffer_get_bignum(&e->request, k->rsa->n);
444 		buffer_get_bignum(&e->request, k->rsa->e);
445 		buffer_get_bignum(&e->request, k->rsa->d);
446 		buffer_get_bignum(&e->request, k->rsa->iqmp);
447 
448 		/* SSH and SSL have p and q swapped */
449 		buffer_get_bignum(&e->request, k->rsa->q);	/* p */
450 		buffer_get_bignum(&e->request, k->rsa->p);	/* q */
451 
452 		/* Generate additional parameters */
453 		rsa_generate_additional_parameters(k->rsa);
454 		break;
455 	case 2:
456 		type_name = buffer_get_string(&e->request, NULL);
457 		type = key_type_from_name(type_name);
458 		xfree(type_name);
459 		switch (type) {
460 		case KEY_DSA:
461 			k = key_new_private(type);
462 			buffer_get_bignum2(&e->request, k->dsa->p);
463 			buffer_get_bignum2(&e->request, k->dsa->q);
464 			buffer_get_bignum2(&e->request, k->dsa->g);
465 			buffer_get_bignum2(&e->request, k->dsa->pub_key);
466 			buffer_get_bignum2(&e->request, k->dsa->priv_key);
467 			break;
468 		case KEY_RSA:
469 			k = key_new_private(type);
470 			buffer_get_bignum2(&e->request, k->rsa->n);
471 			buffer_get_bignum2(&e->request, k->rsa->e);
472 			buffer_get_bignum2(&e->request, k->rsa->d);
473 			buffer_get_bignum2(&e->request, k->rsa->iqmp);
474 			buffer_get_bignum2(&e->request, k->rsa->p);
475 			buffer_get_bignum2(&e->request, k->rsa->q);
476 
477 			/* Generate additional parameters */
478 			rsa_generate_additional_parameters(k->rsa);
479 			break;
480 		default:
481 			buffer_clear(&e->request);
482 			goto send;
483 		}
484 		break;
485 	}
486 	/* enable blinding */
487 	switch (k->type) {
488 	case KEY_RSA:
489 	case KEY_RSA1:
490 		if (RSA_blinding_on(k->rsa, NULL) != 1) {
491 			error("process_add_identity: RSA_blinding_on failed");
492 			key_free(k);
493 			goto send;
494 		}
495 		break;
496 	}
497 	comment = buffer_get_string(&e->request, NULL);
498 	if (k == NULL) {
499 		xfree(comment);
500 		goto send;
501 	}
502 	success = 1;
503 	while (buffer_len(&e->request)) {
504 		switch (buffer_get_char(&e->request)) {
505 		case SSH_AGENT_CONSTRAIN_LIFETIME:
506 			death = time(NULL) + buffer_get_int(&e->request);
507 			break;
508 		case SSH_AGENT_CONSTRAIN_CONFIRM:
509 			confirm = 1;
510 			break;
511 		default:
512 			break;
513 		}
514 	}
515 	if (lifetime && !death)
516 		death = time(NULL) + lifetime;
517 	if (lookup_identity(k, version) == NULL) {
518 		Identity *id = xmalloc(sizeof(Identity));
519 		id->key = k;
520 		id->comment = comment;
521 		id->death = death;
522 		id->confirm = confirm;
523 		TAILQ_INSERT_TAIL(&tab->idlist, id, next);
524 		/* Increment the number of identities. */
525 		tab->nentries++;
526 	} else {
527 		key_free(k);
528 		xfree(comment);
529 	}
530 send:
531 	buffer_put_int(&e->output, 1);
532 	buffer_put_char(&e->output,
533 	    success ? SSH_AGENT_SUCCESS : SSH_AGENT_FAILURE);
534 }
535 
536 /* XXX todo: encrypt sensitive data with passphrase */
537 static void
538 process_lock_agent(SocketEntry *e, int lock)
539 {
540 	int success = 0;
541 	char *passwd;
542 
543 	passwd = buffer_get_string(&e->request, NULL);
544 	if (locked && !lock && strcmp(passwd, lock_passwd) == 0) {
545 		locked = 0;
546 		memset(lock_passwd, 0, strlen(lock_passwd));
547 		xfree(lock_passwd);
548 		lock_passwd = NULL;
549 		success = 1;
550 	} else if (!locked && lock) {
551 		locked = 1;
552 		lock_passwd = xstrdup(passwd);
553 		success = 1;
554 	}
555 	memset(passwd, 0, strlen(passwd));
556 	xfree(passwd);
557 
558 	buffer_put_int(&e->output, 1);
559 	buffer_put_char(&e->output,
560 	    success ? SSH_AGENT_SUCCESS : SSH_AGENT_FAILURE);
561 }
562 
563 static void
564 no_identities(SocketEntry *e, u_int type)
565 {
566 	Buffer msg;
567 
568 	buffer_init(&msg);
569 	buffer_put_char(&msg,
570 	    (type == SSH_AGENTC_REQUEST_RSA_IDENTITIES) ?
571 	    SSH_AGENT_RSA_IDENTITIES_ANSWER : SSH2_AGENT_IDENTITIES_ANSWER);
572 	buffer_put_int(&msg, 0);
573 	buffer_put_int(&e->output, buffer_len(&msg));
574 	buffer_append(&e->output, buffer_ptr(&msg), buffer_len(&msg));
575 	buffer_free(&msg);
576 }
577 
578 #ifdef SMARTCARD
579 static void
580 process_add_smartcard_key (SocketEntry *e)
581 {
582 	char *sc_reader_id = NULL, *pin;
583 	int i, version, success = 0, death = 0, confirm = 0;
584 	Key **keys, *k;
585 	Identity *id;
586 	Idtab *tab;
587 
588 	sc_reader_id = buffer_get_string(&e->request, NULL);
589 	pin = buffer_get_string(&e->request, NULL);
590 
591 	while (buffer_len(&e->request)) {
592 		switch (buffer_get_char(&e->request)) {
593 		case SSH_AGENT_CONSTRAIN_LIFETIME:
594 			death = time(NULL) + buffer_get_int(&e->request);
595 			break;
596 		case SSH_AGENT_CONSTRAIN_CONFIRM:
597 			confirm = 1;
598 			break;
599 		default:
600 			break;
601 		}
602 	}
603 	if (lifetime && !death)
604 		death = time(NULL) + lifetime;
605 
606 	keys = sc_get_keys(sc_reader_id, pin);
607 	xfree(sc_reader_id);
608 	xfree(pin);
609 
610 	if (keys == NULL || keys[0] == NULL) {
611 		error("sc_get_keys failed");
612 		goto send;
613 	}
614 	for (i = 0; keys[i] != NULL; i++) {
615 		k = keys[i];
616 		version = k->type == KEY_RSA1 ? 1 : 2;
617 		tab = idtab_lookup(version);
618 		if (lookup_identity(k, version) == NULL) {
619 			id = xmalloc(sizeof(Identity));
620 			id->key = k;
621 			id->comment = sc_get_key_label(k);
622 			id->death = death;
623 			id->confirm = confirm;
624 			TAILQ_INSERT_TAIL(&tab->idlist, id, next);
625 			tab->nentries++;
626 			success = 1;
627 		} else {
628 			key_free(k);
629 		}
630 		keys[i] = NULL;
631 	}
632 	xfree(keys);
633 send:
634 	buffer_put_int(&e->output, 1);
635 	buffer_put_char(&e->output,
636 	    success ? SSH_AGENT_SUCCESS : SSH_AGENT_FAILURE);
637 }
638 
639 static void
640 process_remove_smartcard_key(SocketEntry *e)
641 {
642 	char *sc_reader_id = NULL, *pin;
643 	int i, version, success = 0;
644 	Key **keys, *k = NULL;
645 	Identity *id;
646 	Idtab *tab;
647 
648 	sc_reader_id = buffer_get_string(&e->request, NULL);
649 	pin = buffer_get_string(&e->request, NULL);
650 	keys = sc_get_keys(sc_reader_id, pin);
651 	xfree(sc_reader_id);
652 	xfree(pin);
653 
654 	if (keys == NULL || keys[0] == NULL) {
655 		error("sc_get_keys failed");
656 		goto send;
657 	}
658 	for (i = 0; keys[i] != NULL; i++) {
659 		k = keys[i];
660 		version = k->type == KEY_RSA1 ? 1 : 2;
661 		if ((id = lookup_identity(k, version)) != NULL) {
662 			tab = idtab_lookup(version);
663 			TAILQ_REMOVE(&tab->idlist, id, next);
664 			tab->nentries--;
665 			free_identity(id);
666 			success = 1;
667 		}
668 		key_free(k);
669 		keys[i] = NULL;
670 	}
671 	xfree(keys);
672 send:
673 	buffer_put_int(&e->output, 1);
674 	buffer_put_char(&e->output,
675 	    success ? SSH_AGENT_SUCCESS : SSH_AGENT_FAILURE);
676 }
677 #endif /* SMARTCARD */
678 
679 /* dispatch incoming messages */
680 
681 static void
682 process_message(SocketEntry *e)
683 {
684 	u_int msg_len, type;
685 	u_char *cp;
686 
687 	/* kill dead keys */
688 	reaper();
689 
690 	if (buffer_len(&e->input) < 5)
691 		return;		/* Incomplete message. */
692 	cp = buffer_ptr(&e->input);
693 	msg_len = GET_32BIT(cp);
694 	if (msg_len > 256 * 1024) {
695 		close_socket(e);
696 		return;
697 	}
698 	if (buffer_len(&e->input) < msg_len + 4)
699 		return;
700 
701 	/* move the current input to e->request */
702 	buffer_consume(&e->input, 4);
703 	buffer_clear(&e->request);
704 	buffer_append(&e->request, buffer_ptr(&e->input), msg_len);
705 	buffer_consume(&e->input, msg_len);
706 	type = buffer_get_char(&e->request);
707 
708 	/* check wheter agent is locked */
709 	if (locked && type != SSH_AGENTC_UNLOCK) {
710 		buffer_clear(&e->request);
711 		switch (type) {
712 		case SSH_AGENTC_REQUEST_RSA_IDENTITIES:
713 		case SSH2_AGENTC_REQUEST_IDENTITIES:
714 			/* send empty lists */
715 			no_identities(e, type);
716 			break;
717 		default:
718 			/* send a fail message for all other request types */
719 			buffer_put_int(&e->output, 1);
720 			buffer_put_char(&e->output, SSH_AGENT_FAILURE);
721 		}
722 		return;
723 	}
724 
725 	debug("type %d", type);
726 	switch (type) {
727 	case SSH_AGENTC_LOCK:
728 	case SSH_AGENTC_UNLOCK:
729 		process_lock_agent(e, type == SSH_AGENTC_LOCK);
730 		break;
731 	/* ssh1 */
732 	case SSH_AGENTC_RSA_CHALLENGE:
733 		process_authentication_challenge1(e);
734 		break;
735 	case SSH_AGENTC_REQUEST_RSA_IDENTITIES:
736 		process_request_identities(e, 1);
737 		break;
738 	case SSH_AGENTC_ADD_RSA_IDENTITY:
739 	case SSH_AGENTC_ADD_RSA_ID_CONSTRAINED:
740 		process_add_identity(e, 1);
741 		break;
742 	case SSH_AGENTC_REMOVE_RSA_IDENTITY:
743 		process_remove_identity(e, 1);
744 		break;
745 	case SSH_AGENTC_REMOVE_ALL_RSA_IDENTITIES:
746 		process_remove_all_identities(e, 1);
747 		break;
748 	/* ssh2 */
749 	case SSH2_AGENTC_SIGN_REQUEST:
750 		process_sign_request2(e);
751 		break;
752 	case SSH2_AGENTC_REQUEST_IDENTITIES:
753 		process_request_identities(e, 2);
754 		break;
755 	case SSH2_AGENTC_ADD_IDENTITY:
756 	case SSH2_AGENTC_ADD_ID_CONSTRAINED:
757 		process_add_identity(e, 2);
758 		break;
759 	case SSH2_AGENTC_REMOVE_IDENTITY:
760 		process_remove_identity(e, 2);
761 		break;
762 	case SSH2_AGENTC_REMOVE_ALL_IDENTITIES:
763 		process_remove_all_identities(e, 2);
764 		break;
765 #ifdef SMARTCARD
766 	case SSH_AGENTC_ADD_SMARTCARD_KEY:
767 	case SSH_AGENTC_ADD_SMARTCARD_KEY_CONSTRAINED:
768 		process_add_smartcard_key(e);
769 		break;
770 	case SSH_AGENTC_REMOVE_SMARTCARD_KEY:
771 		process_remove_smartcard_key(e);
772 		break;
773 #endif /* SMARTCARD */
774 	default:
775 		/* Unknown message.  Respond with failure. */
776 		error("Unknown message %d", type);
777 		buffer_clear(&e->request);
778 		buffer_put_int(&e->output, 1);
779 		buffer_put_char(&e->output, SSH_AGENT_FAILURE);
780 		break;
781 	}
782 }
783 
784 static void
785 new_socket(sock_type type, int fd)
786 {
787 	u_int i, old_alloc, new_alloc;
788 
789 	set_nonblock(fd);
790 
791 	if (fd > max_fd)
792 		max_fd = fd;
793 
794 	for (i = 0; i < sockets_alloc; i++)
795 		if (sockets[i].type == AUTH_UNUSED) {
796 			sockets[i].fd = fd;
797 			buffer_init(&sockets[i].input);
798 			buffer_init(&sockets[i].output);
799 			buffer_init(&sockets[i].request);
800 			sockets[i].type = type;
801 			return;
802 		}
803 	old_alloc = sockets_alloc;
804 	new_alloc = sockets_alloc + 10;
805 	if (sockets)
806 		sockets = xrealloc(sockets, new_alloc * sizeof(sockets[0]));
807 	else
808 		sockets = xmalloc(new_alloc * sizeof(sockets[0]));
809 	for (i = old_alloc; i < new_alloc; i++)
810 		sockets[i].type = AUTH_UNUSED;
811 	sockets_alloc = new_alloc;
812 	sockets[old_alloc].fd = fd;
813 	buffer_init(&sockets[old_alloc].input);
814 	buffer_init(&sockets[old_alloc].output);
815 	buffer_init(&sockets[old_alloc].request);
816 	sockets[old_alloc].type = type;
817 }
818 
819 static int
820 prepare_select(fd_set **fdrp, fd_set **fdwp, int *fdl, u_int *nallocp)
821 {
822 	u_int i, sz;
823 	int n = 0;
824 
825 	for (i = 0; i < sockets_alloc; i++) {
826 		switch (sockets[i].type) {
827 		case AUTH_SOCKET:
828 		case AUTH_CONNECTION:
829 			n = MAX(n, sockets[i].fd);
830 			break;
831 		case AUTH_UNUSED:
832 			break;
833 		default:
834 			fatal("Unknown socket type %d", sockets[i].type);
835 			break;
836 		}
837 	}
838 
839 	sz = howmany(n+1, NFDBITS) * sizeof(fd_mask);
840 	if (*fdrp == NULL || sz > *nallocp) {
841 		if (*fdrp)
842 			xfree(*fdrp);
843 		if (*fdwp)
844 			xfree(*fdwp);
845 		*fdrp = xmalloc(sz);
846 		*fdwp = xmalloc(sz);
847 		*nallocp = sz;
848 	}
849 	if (n < *fdl)
850 		debug("XXX shrink: %d < %d", n, *fdl);
851 	*fdl = n;
852 	memset(*fdrp, 0, sz);
853 	memset(*fdwp, 0, sz);
854 
855 	for (i = 0; i < sockets_alloc; i++) {
856 		switch (sockets[i].type) {
857 		case AUTH_SOCKET:
858 		case AUTH_CONNECTION:
859 			FD_SET(sockets[i].fd, *fdrp);
860 			if (buffer_len(&sockets[i].output) > 0)
861 				FD_SET(sockets[i].fd, *fdwp);
862 			break;
863 		default:
864 			break;
865 		}
866 	}
867 	return (1);
868 }
869 
870 static void
871 after_select(fd_set *readset, fd_set *writeset)
872 {
873 	struct sockaddr_un sunaddr;
874 	socklen_t slen;
875 	char buf[1024];
876 	int len, sock;
877 	u_int i;
878 	uid_t euid;
879 	gid_t egid;
880 
881 	for (i = 0; i < sockets_alloc; i++)
882 		switch (sockets[i].type) {
883 		case AUTH_UNUSED:
884 			break;
885 		case AUTH_SOCKET:
886 			if (FD_ISSET(sockets[i].fd, readset)) {
887 				slen = sizeof(sunaddr);
888 				sock = accept(sockets[i].fd,
889 				    (struct sockaddr *) &sunaddr, &slen);
890 				if (sock < 0) {
891 					error("accept from AUTH_SOCKET: %s",
892 					    strerror(errno));
893 					break;
894 				}
895 				if (getpeereid(sock, &euid, &egid) < 0) {
896 					error("getpeereid %d failed: %s",
897 					    sock, strerror(errno));
898 					close(sock);
899 					break;
900 				}
901 				if ((euid != 0) && (getuid() != euid)) {
902 					error("uid mismatch: "
903 					    "peer euid %u != uid %u",
904 					    (u_int) euid, (u_int) getuid());
905 					close(sock);
906 					break;
907 				}
908 				new_socket(AUTH_CONNECTION, sock);
909 			}
910 			break;
911 		case AUTH_CONNECTION:
912 			if (buffer_len(&sockets[i].output) > 0 &&
913 			    FD_ISSET(sockets[i].fd, writeset)) {
914 				do {
915 					len = write(sockets[i].fd,
916 					    buffer_ptr(&sockets[i].output),
917 					    buffer_len(&sockets[i].output));
918 					if (len == -1 && (errno == EAGAIN ||
919 					    errno == EINTR))
920 						continue;
921 					break;
922 				} while (1);
923 				if (len <= 0) {
924 					close_socket(&sockets[i]);
925 					break;
926 				}
927 				buffer_consume(&sockets[i].output, len);
928 			}
929 			if (FD_ISSET(sockets[i].fd, readset)) {
930 				do {
931 					len = read(sockets[i].fd, buf, sizeof(buf));
932 					if (len == -1 && (errno == EAGAIN ||
933 					    errno == EINTR))
934 						continue;
935 					break;
936 				} while (1);
937 				if (len <= 0) {
938 					close_socket(&sockets[i]);
939 					break;
940 				}
941 				buffer_append(&sockets[i].input, buf, len);
942 				process_message(&sockets[i]);
943 			}
944 			break;
945 		default:
946 			fatal("Unknown type %d", sockets[i].type);
947 		}
948 }
949 
950 static void
951 cleanup_socket(void)
952 {
953 	if (socket_name[0])
954 		unlink(socket_name);
955 	if (socket_dir[0])
956 		rmdir(socket_dir);
957 }
958 
959 void
960 cleanup_exit(int i)
961 {
962 	cleanup_socket();
963 	_exit(i);
964 }
965 
966 static void
967 cleanup_handler(int sig)
968 {
969 	cleanup_socket();
970 	_exit(2);
971 }
972 
973 static void
974 check_parent_exists(int sig)
975 {
976 	int save_errno = errno;
977 
978 	if (parent_pid != -1 && kill(parent_pid, 0) < 0) {
979 		/* printf("Parent has died - Authentication agent exiting.\n"); */
980 		cleanup_handler(sig); /* safe */
981 	}
982 	mysignal(SIGALRM, check_parent_exists);
983 	alarm(10);
984 	errno = save_errno;
985 }
986 
987 static void
988 usage(void)
989 {
990 	fprintf(stderr, "Usage: %s [options] [command [args ...]]\n",
991 	    __progname);
992 	fprintf(stderr, "Options:\n");
993 	fprintf(stderr, "  -c          Generate C-shell commands on stdout.\n");
994 	fprintf(stderr, "  -s          Generate Bourne shell commands on stdout.\n");
995 	fprintf(stderr, "  -k          Kill the current agent.\n");
996 	fprintf(stderr, "  -d          Debug mode.\n");
997 	fprintf(stderr, "  -a socket   Bind agent socket to given name.\n");
998 	fprintf(stderr, "  -t life     Default identity lifetime (seconds).\n");
999 	exit(1);
1000 }
1001 
1002 int
1003 main(int ac, char **av)
1004 {
1005 	int c_flag = 0, d_flag = 0, k_flag = 0, s_flag = 0;
1006 	int sock, fd,  ch;
1007 	u_int nalloc;
1008 	char *shell, *format, *pidstr, *agentsocket = NULL;
1009 	fd_set *readsetp = NULL, *writesetp = NULL;
1010 	struct sockaddr_un sunaddr;
1011 #ifdef HAVE_SETRLIMIT
1012 	struct rlimit rlim;
1013 #endif
1014 #ifdef HAVE_CYGWIN
1015 	int prev_mask;
1016 #endif
1017 	extern int optind;
1018 	extern char *optarg;
1019 	pid_t pid;
1020 	char pidstrbuf[1 + 3 * sizeof pid];
1021 
1022 	/* drop */
1023 	setegid(getgid());
1024 	setgid(getgid());
1025 	setuid(geteuid());
1026 
1027 #if defined(HAVE_PRCTL) && defined(PR_SET_DUMPABLE)
1028 	/* Disable ptrace on Linux without sgid bit */
1029 	prctl(PR_SET_DUMPABLE, 0);
1030 #endif
1031 
1032 	SSLeay_add_all_algorithms();
1033 
1034 	__progname = ssh_get_progname(av[0]);
1035 	init_rng();
1036 	seed_rng();
1037 
1038 	while ((ch = getopt(ac, av, "cdksa:t:")) != -1) {
1039 		switch (ch) {
1040 		case 'c':
1041 			if (s_flag)
1042 				usage();
1043 			c_flag++;
1044 			break;
1045 		case 'k':
1046 			k_flag++;
1047 			break;
1048 		case 's':
1049 			if (c_flag)
1050 				usage();
1051 			s_flag++;
1052 			break;
1053 		case 'd':
1054 			if (d_flag)
1055 				usage();
1056 			d_flag++;
1057 			break;
1058 		case 'a':
1059 			agentsocket = optarg;
1060 			break;
1061 		case 't':
1062 			if ((lifetime = convtime(optarg)) == -1) {
1063 				fprintf(stderr, "Invalid lifetime\n");
1064 				usage();
1065 			}
1066 			break;
1067 		default:
1068 			usage();
1069 		}
1070 	}
1071 	ac -= optind;
1072 	av += optind;
1073 
1074 	if (ac > 0 && (c_flag || k_flag || s_flag || d_flag))
1075 		usage();
1076 
1077 	if (ac == 0 && !c_flag && !s_flag) {
1078 		shell = getenv("SHELL");
1079 		if (shell != NULL && strncmp(shell + strlen(shell) - 3, "csh", 3) == 0)
1080 			c_flag = 1;
1081 	}
1082 	if (k_flag) {
1083 		pidstr = getenv(SSH_AGENTPID_ENV_NAME);
1084 		if (pidstr == NULL) {
1085 			fprintf(stderr, "%s not set, cannot kill agent\n",
1086 			    SSH_AGENTPID_ENV_NAME);
1087 			exit(1);
1088 		}
1089 		pid = atoi(pidstr);
1090 		if (pid < 1) {
1091 			fprintf(stderr, "%s=\"%s\", which is not a good PID\n",
1092 			    SSH_AGENTPID_ENV_NAME, pidstr);
1093 			exit(1);
1094 		}
1095 		if (kill(pid, SIGTERM) == -1) {
1096 			perror("kill");
1097 			exit(1);
1098 		}
1099 		format = c_flag ? "unsetenv %s;\n" : "unset %s;\n";
1100 		printf(format, SSH_AUTHSOCKET_ENV_NAME);
1101 		printf(format, SSH_AGENTPID_ENV_NAME);
1102 		printf("echo Agent pid %ld killed;\n", (long)pid);
1103 		exit(0);
1104 	}
1105 	parent_pid = getpid();
1106 
1107 	if (agentsocket == NULL) {
1108 		/* Create private directory for agent socket */
1109 		strlcpy(socket_dir, "/tmp/ssh-XXXXXXXXXX", sizeof socket_dir);
1110 		if (mkdtemp(socket_dir) == NULL) {
1111 			perror("mkdtemp: private socket dir");
1112 			exit(1);
1113 		}
1114 		snprintf(socket_name, sizeof socket_name, "%s/agent.%ld", socket_dir,
1115 		    (long)parent_pid);
1116 	} else {
1117 		/* Try to use specified agent socket */
1118 		socket_dir[0] = '\0';
1119 		strlcpy(socket_name, agentsocket, sizeof socket_name);
1120 	}
1121 
1122 	/*
1123 	 * Create socket early so it will exist before command gets run from
1124 	 * the parent.
1125 	 */
1126 	sock = socket(AF_UNIX, SOCK_STREAM, 0);
1127 	if (sock < 0) {
1128 		perror("socket");
1129 		cleanup_exit(1);
1130 	}
1131 	memset(&sunaddr, 0, sizeof(sunaddr));
1132 	sunaddr.sun_family = AF_UNIX;
1133 	strlcpy(sunaddr.sun_path, socket_name, sizeof(sunaddr.sun_path));
1134 #ifdef HAVE_CYGWIN
1135 	prev_mask = umask(0177);
1136 #endif
1137 	if (bind(sock, (struct sockaddr *) & sunaddr, sizeof(sunaddr)) < 0) {
1138 		perror("bind");
1139 #ifdef HAVE_CYGWIN
1140 		umask(prev_mask);
1141 #endif
1142 		cleanup_exit(1);
1143 	}
1144 #ifdef HAVE_CYGWIN
1145 	umask(prev_mask);
1146 #endif
1147 	if (listen(sock, SSH_LISTEN_BACKLOG) < 0) {
1148 		perror("listen");
1149 		cleanup_exit(1);
1150 	}
1151 
1152 	/*
1153 	 * Fork, and have the parent execute the command, if any, or present
1154 	 * the socket data.  The child continues as the authentication agent.
1155 	 */
1156 	if (d_flag) {
1157 		log_init(__progname, SYSLOG_LEVEL_DEBUG1, SYSLOG_FACILITY_AUTH, 1);
1158 		format = c_flag ? "setenv %s %s;\n" : "%s=%s; export %s;\n";
1159 		printf(format, SSH_AUTHSOCKET_ENV_NAME, socket_name,
1160 		    SSH_AUTHSOCKET_ENV_NAME);
1161 		printf("echo Agent pid %ld;\n", (long)parent_pid);
1162 		goto skip;
1163 	}
1164 	pid = fork();
1165 	if (pid == -1) {
1166 		perror("fork");
1167 		cleanup_exit(1);
1168 	}
1169 	if (pid != 0) {		/* Parent - execute the given command. */
1170 		close(sock);
1171 		snprintf(pidstrbuf, sizeof pidstrbuf, "%ld", (long)pid);
1172 		if (ac == 0) {
1173 			format = c_flag ? "setenv %s %s;\n" : "%s=%s; export %s;\n";
1174 			printf(format, SSH_AUTHSOCKET_ENV_NAME, socket_name,
1175 			    SSH_AUTHSOCKET_ENV_NAME);
1176 			printf(format, SSH_AGENTPID_ENV_NAME, pidstrbuf,
1177 			    SSH_AGENTPID_ENV_NAME);
1178 			printf("echo Agent pid %ld;\n", (long)pid);
1179 			exit(0);
1180 		}
1181 		if (setenv(SSH_AUTHSOCKET_ENV_NAME, socket_name, 1) == -1 ||
1182 		    setenv(SSH_AGENTPID_ENV_NAME, pidstrbuf, 1) == -1) {
1183 			perror("setenv");
1184 			exit(1);
1185 		}
1186 		execvp(av[0], av);
1187 		perror(av[0]);
1188 		exit(1);
1189 	}
1190 	/* child */
1191 	log_init(__progname, SYSLOG_LEVEL_INFO, SYSLOG_FACILITY_AUTH, 0);
1192 
1193 	if (setsid() == -1) {
1194 		error("setsid: %s", strerror(errno));
1195 		cleanup_exit(1);
1196 	}
1197 
1198 	(void)chdir("/");
1199 	if ((fd = open(_PATH_DEVNULL, O_RDWR, 0)) != -1) {
1200 		/* XXX might close listen socket */
1201 		(void)dup2(fd, STDIN_FILENO);
1202 		(void)dup2(fd, STDOUT_FILENO);
1203 		(void)dup2(fd, STDERR_FILENO);
1204 		if (fd > 2)
1205 			close(fd);
1206 	}
1207 
1208 #ifdef HAVE_SETRLIMIT
1209 	/* deny core dumps, since memory contains unencrypted private keys */
1210 	rlim.rlim_cur = rlim.rlim_max = 0;
1211 	if (setrlimit(RLIMIT_CORE, &rlim) < 0) {
1212 		error("setrlimit RLIMIT_CORE: %s", strerror(errno));
1213 		cleanup_exit(1);
1214 	}
1215 #endif
1216 
1217 skip:
1218 	new_socket(AUTH_SOCKET, sock);
1219 	if (ac > 0) {
1220 		mysignal(SIGALRM, check_parent_exists);
1221 		alarm(10);
1222 	}
1223 	idtab_init();
1224 	if (!d_flag)
1225 		signal(SIGINT, SIG_IGN);
1226 	signal(SIGPIPE, SIG_IGN);
1227 	signal(SIGHUP, cleanup_handler);
1228 	signal(SIGTERM, cleanup_handler);
1229 	nalloc = 0;
1230 
1231 	while (1) {
1232 		prepare_select(&readsetp, &writesetp, &max_fd, &nalloc);
1233 		if (select(max_fd + 1, readsetp, writesetp, NULL, NULL) < 0) {
1234 			if (errno == EINTR)
1235 				continue;
1236 			fatal("select: %s", strerror(errno));
1237 		}
1238 		after_select(readsetp, writesetp);
1239 	}
1240 	/* NOTREACHED */
1241 }
1242