diff options
author | Damien Miller <djm@mindrot.org> | 2002-01-22 23:26:13 +1100 |
---|---|---|
committer | Damien Miller <djm@mindrot.org> | 2002-01-22 23:26:13 +1100 |
commit | 1a534ae97fc1d9e75384d8df44fef7f788c3629d (patch) | |
tree | 2f82a4462004110661ad34a9e36fb761ada78bc5 | |
parent | df224031ca59175e021c9b0084060fb9a909f31e (diff) |
- provos@cvs.openbsd.org 2002/01/13 17:27:07
[ssh-agent.c]
change to use queue.h macros; okay markus@
-rw-r--r-- | ChangeLog | 5 | ||||
-rw-r--r-- | ssh-agent.c | 151 |
2 files changed, 73 insertions, 83 deletions
@@ -152,6 +152,9 @@ | |||
152 | - markus@cvs.openbsd.org 2002/01/12 13:10:29 | 152 | - markus@cvs.openbsd.org 2002/01/12 13:10:29 |
153 | [auth-skey.c] | 153 | [auth-skey.c] |
154 | undo local change | 154 | undo local change |
155 | - provos@cvs.openbsd.org 2002/01/13 17:27:07 | ||
156 | [ssh-agent.c] | ||
157 | change to use queue.h macros; okay markus@ | ||
155 | 158 | ||
156 | 159 | ||
157 | 20020121 | 160 | 20020121 |
@@ -7300,4 +7303,4 @@ | |||
7300 | - Wrote replacements for strlcpy and mkdtemp | 7303 | - Wrote replacements for strlcpy and mkdtemp |
7301 | - Released 1.0pre1 | 7304 | - Released 1.0pre1 |
7302 | 7305 | ||
7303 | $Id: ChangeLog,v 1.1766 2002/01/22 12:25:46 djm Exp $ | 7306 | $Id: ChangeLog,v 1.1767 2002/01/22 12:26:13 djm Exp $ |
diff --git a/ssh-agent.c b/ssh-agent.c index f5849cee4..84cff1282 100644 --- a/ssh-agent.c +++ b/ssh-agent.c | |||
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: ssh-agent.c,v 1.77 2001/12/29 21:56:01 stevesk Exp $ */ | 1 | /* $OpenBSD: ssh-agent.c,v 1.78 2002/01/13 17:27:07 provos Exp $ */ |
2 | 2 | ||
3 | /* | 3 | /* |
4 | * Author: Tatu Ylonen <ylo@cs.hut.fi> | 4 | * Author: Tatu Ylonen <ylo@cs.hut.fi> |
@@ -36,7 +36,8 @@ | |||
36 | */ | 36 | */ |
37 | 37 | ||
38 | #include "includes.h" | 38 | #include "includes.h" |
39 | RCSID("$OpenBSD: ssh-agent.c,v 1.77 2001/12/29 21:56:01 stevesk Exp $"); | 39 | #include <sys/queue.h> |
40 | RCSID("$OpenBSD: ssh-agent.c,v 1.78 2002/01/13 17:27:07 provos Exp $"); | ||
40 | 41 | ||
41 | #include <openssl/evp.h> | 42 | #include <openssl/evp.h> |
42 | #include <openssl/md5.h> | 43 | #include <openssl/md5.h> |
@@ -77,14 +78,15 @@ typedef struct { | |||
77 | u_int sockets_alloc = 0; | 78 | u_int sockets_alloc = 0; |
78 | SocketEntry *sockets = NULL; | 79 | SocketEntry *sockets = NULL; |
79 | 80 | ||
80 | typedef struct { | 81 | typedef struct identity { |
82 | TAILQ_ENTRY(identity) next; | ||
81 | Key *key; | 83 | Key *key; |
82 | char *comment; | 84 | char *comment; |
83 | } Identity; | 85 | } Identity; |
84 | 86 | ||
85 | typedef struct { | 87 | typedef struct { |
86 | int nentries; | 88 | int nentries; |
87 | Identity *identities; | 89 | TAILQ_HEAD(idqueue, identity) idlist; |
88 | } Idtab; | 90 | } Idtab; |
89 | 91 | ||
90 | /* private key table, one per protocol version */ | 92 | /* private key table, one per protocol version */ |
@@ -110,7 +112,7 @@ idtab_init(void) | |||
110 | { | 112 | { |
111 | int i; | 113 | int i; |
112 | for (i = 0; i <=2; i++) { | 114 | for (i = 0; i <=2; i++) { |
113 | idtable[i].identities = NULL; | 115 | TAILQ_INIT(&idtable[i].idlist); |
114 | idtable[i].nentries = 0; | 116 | idtable[i].nentries = 0; |
115 | } | 117 | } |
116 | } | 118 | } |
@@ -125,19 +127,25 @@ idtab_lookup(int version) | |||
125 | } | 127 | } |
126 | 128 | ||
127 | /* return matching private key for given public key */ | 129 | /* return matching private key for given public key */ |
128 | static Key * | 130 | static Identity * |
129 | lookup_private_key(Key *key, int *idx, int version) | 131 | lookup_identity(Key *key, int version) |
130 | { | 132 | { |
131 | int i; | 133 | Identity *id; |
134 | |||
132 | Idtab *tab = idtab_lookup(version); | 135 | Idtab *tab = idtab_lookup(version); |
133 | for (i = 0; i < tab->nentries; i++) { | 136 | TAILQ_FOREACH(id, &tab->idlist, next) { |
134 | if (key_equal(key, tab->identities[i].key)) { | 137 | if (key_equal(key, id->key)) |
135 | if (idx != NULL) | 138 | return (id); |
136 | *idx = i; | ||
137 | return tab->identities[i].key; | ||
138 | } | ||
139 | } | 139 | } |
140 | return NULL; | 140 | return (NULL); |
141 | } | ||
142 | |||
143 | static void | ||
144 | free_identity(Identity *id) | ||
145 | { | ||
146 | key_free(id->key); | ||
147 | xfree(id->comment); | ||
148 | xfree(id); | ||
141 | } | 149 | } |
142 | 150 | ||
143 | /* send list of supported public keys to 'client' */ | 151 | /* send list of supported public keys to 'client' */ |
@@ -146,14 +154,13 @@ process_request_identities(SocketEntry *e, int version) | |||
146 | { | 154 | { |
147 | Idtab *tab = idtab_lookup(version); | 155 | Idtab *tab = idtab_lookup(version); |
148 | Buffer msg; | 156 | Buffer msg; |
149 | int i; | 157 | Identity *id; |
150 | 158 | ||
151 | buffer_init(&msg); | 159 | buffer_init(&msg); |
152 | buffer_put_char(&msg, (version == 1) ? | 160 | buffer_put_char(&msg, (version == 1) ? |
153 | SSH_AGENT_RSA_IDENTITIES_ANSWER : SSH2_AGENT_IDENTITIES_ANSWER); | 161 | SSH_AGENT_RSA_IDENTITIES_ANSWER : SSH2_AGENT_IDENTITIES_ANSWER); |
154 | buffer_put_int(&msg, tab->nentries); | 162 | buffer_put_int(&msg, tab->nentries); |
155 | for (i = 0; i < tab->nentries; i++) { | 163 | TAILQ_FOREACH(id, &tab->idlist, next) { |
156 | Identity *id = &tab->identities[i]; | ||
157 | if (id->key->type == KEY_RSA1) { | 164 | if (id->key->type == KEY_RSA1) { |
158 | buffer_put_int(&msg, BN_num_bits(id->key->rsa->n)); | 165 | buffer_put_int(&msg, BN_num_bits(id->key->rsa->n)); |
159 | buffer_put_bignum(&msg, id->key->rsa->e); | 166 | buffer_put_bignum(&msg, id->key->rsa->e); |
@@ -176,7 +183,8 @@ process_request_identities(SocketEntry *e, int version) | |||
176 | static void | 183 | static void |
177 | process_authentication_challenge1(SocketEntry *e) | 184 | process_authentication_challenge1(SocketEntry *e) |
178 | { | 185 | { |
179 | Key *key, *private; | 186 | Identity *id; |
187 | Key *key; | ||
180 | BIGNUM *challenge; | 188 | BIGNUM *challenge; |
181 | int i, len; | 189 | int i, len; |
182 | Buffer msg; | 190 | Buffer msg; |
@@ -202,8 +210,9 @@ process_authentication_challenge1(SocketEntry *e) | |||
202 | if (response_type != 1) | 210 | if (response_type != 1) |
203 | goto failure; | 211 | goto failure; |
204 | 212 | ||
205 | private = lookup_private_key(key, NULL, 1); | 213 | id = lookup_identity(key, 1); |
206 | if (private != NULL) { | 214 | if (id != NULL) { |
215 | Key *private = id->key; | ||
207 | /* Decrypt the challenge using the private key. */ | 216 | /* Decrypt the challenge using the private key. */ |
208 | if (rsa_private_decrypt(challenge, challenge, private->rsa) <= 0) | 217 | if (rsa_private_decrypt(challenge, challenge, private->rsa) <= 0) |
209 | goto failure; | 218 | goto failure; |
@@ -244,7 +253,7 @@ static void | |||
244 | process_sign_request2(SocketEntry *e) | 253 | process_sign_request2(SocketEntry *e) |
245 | { | 254 | { |
246 | extern int datafellows; | 255 | extern int datafellows; |
247 | Key *key, *private; | 256 | Key *key; |
248 | u_char *blob, *data, *signature = NULL; | 257 | u_char *blob, *data, *signature = NULL; |
249 | u_int blen, dlen, slen = 0; | 258 | u_int blen, dlen, slen = 0; |
250 | int flags; | 259 | int flags; |
@@ -262,9 +271,9 @@ process_sign_request2(SocketEntry *e) | |||
262 | 271 | ||
263 | key = key_from_blob(blob, blen); | 272 | key = key_from_blob(blob, blen); |
264 | if (key != NULL) { | 273 | if (key != NULL) { |
265 | private = lookup_private_key(key, NULL, 2); | 274 | Identity *id = lookup_identity(key, 2); |
266 | if (private != NULL) | 275 | if (id != NULL) |
267 | ok = key_sign(private, &signature, &slen, data, dlen); | 276 | ok = key_sign(id->key, &signature, &slen, data, dlen); |
268 | } | 277 | } |
269 | key_free(key); | 278 | key_free(key); |
270 | buffer_init(&msg); | 279 | buffer_init(&msg); |
@@ -288,7 +297,7 @@ process_sign_request2(SocketEntry *e) | |||
288 | static void | 297 | static void |
289 | process_remove_identity(SocketEntry *e, int version) | 298 | process_remove_identity(SocketEntry *e, int version) |
290 | { | 299 | { |
291 | Key *key = NULL, *private; | 300 | Key *key = NULL; |
292 | u_char *blob; | 301 | u_char *blob; |
293 | u_int blen; | 302 | u_int blen; |
294 | u_int bits; | 303 | u_int bits; |
@@ -312,9 +321,8 @@ process_remove_identity(SocketEntry *e, int version) | |||
312 | break; | 321 | break; |
313 | } | 322 | } |
314 | if (key != NULL) { | 323 | if (key != NULL) { |
315 | int idx; | 324 | Identity *id = lookup_identity(key, version); |
316 | private = lookup_private_key(key, &idx, version); | 325 | if (id != NULL) { |
317 | if (private != NULL) { | ||
318 | /* | 326 | /* |
319 | * We have this key. Free the old key. Since we | 327 | * We have this key. Free the old key. Since we |
320 | * don\'t want to leave empty slots in the middle of | 328 | * don\'t want to leave empty slots in the middle of |
@@ -323,19 +331,12 @@ process_remove_identity(SocketEntry *e, int version) | |||
323 | * of the array. | 331 | * of the array. |
324 | */ | 332 | */ |
325 | Idtab *tab = idtab_lookup(version); | 333 | Idtab *tab = idtab_lookup(version); |
326 | key_free(tab->identities[idx].key); | ||
327 | xfree(tab->identities[idx].comment); | ||
328 | if (tab->nentries < 1) | 334 | if (tab->nentries < 1) |
329 | fatal("process_remove_identity: " | 335 | fatal("process_remove_identity: " |
330 | "internal error: tab->nentries %d", | 336 | "internal error: tab->nentries %d", |
331 | tab->nentries); | 337 | tab->nentries); |
332 | if (idx != tab->nentries - 1) { | 338 | TAILQ_REMOVE(&tab->idlist, id, next); |
333 | int i; | 339 | free_identity(id); |
334 | for (i = idx; i < tab->nentries - 1; i++) | ||
335 | tab->identities[i] = tab->identities[i+1]; | ||
336 | } | ||
337 | tab->identities[tab->nentries - 1].key = NULL; | ||
338 | tab->identities[tab->nentries - 1].comment = NULL; | ||
339 | tab->nentries--; | 340 | tab->nentries--; |
340 | success = 1; | 341 | success = 1; |
341 | } | 342 | } |
@@ -349,13 +350,14 @@ process_remove_identity(SocketEntry *e, int version) | |||
349 | static void | 350 | static void |
350 | process_remove_all_identities(SocketEntry *e, int version) | 351 | process_remove_all_identities(SocketEntry *e, int version) |
351 | { | 352 | { |
352 | u_int i; | ||
353 | Idtab *tab = idtab_lookup(version); | 353 | Idtab *tab = idtab_lookup(version); |
354 | Identity *id; | ||
354 | 355 | ||
355 | /* Loop over all identities and clear the keys. */ | 356 | /* Loop over all identities and clear the keys. */ |
356 | for (i = 0; i < tab->nentries; i++) { | 357 | for (id = TAILQ_FIRST(&tab->idlist); id; |
357 | key_free(tab->identities[i].key); | 358 | id = TAILQ_FIRST(&tab->idlist)) { |
358 | xfree(tab->identities[i].comment); | 359 | TAILQ_REMOVE(&tab->idlist, id, next); |
360 | free_identity(id); | ||
359 | } | 361 | } |
360 | 362 | ||
361 | /* Mark that there are no identities. */ | 363 | /* Mark that there are no identities. */ |
@@ -429,14 +431,11 @@ process_add_identity(SocketEntry *e, int version) | |||
429 | goto send; | 431 | goto send; |
430 | } | 432 | } |
431 | success = 1; | 433 | success = 1; |
432 | if (lookup_private_key(k, NULL, version) == NULL) { | 434 | if (lookup_identity(k, version) == NULL) { |
433 | if (tab->nentries == 0) | 435 | Identity *id = xmalloc(sizeof(Identity)); |
434 | tab->identities = xmalloc(sizeof(Identity)); | 436 | id->key = k; |
435 | else | 437 | id->comment = comment; |
436 | tab->identities = xrealloc(tab->identities, | 438 | TAILQ_INSERT_TAIL(&tab->idlist, id, next); |
437 | (tab->nentries + 1) * sizeof(Identity)); | ||
438 | tab->identities[tab->nentries].key = k; | ||
439 | tab->identities[tab->nentries].comment = comment; | ||
440 | /* Increment the number of identities. */ | 439 | /* Increment the number of identities. */ |
441 | tab->nentries++; | 440 | tab->nentries++; |
442 | } else { | 441 | } else { |
@@ -471,36 +470,28 @@ process_add_smartcard_key (SocketEntry *e) | |||
471 | 470 | ||
472 | tab = idtab_lookup(1); | 471 | tab = idtab_lookup(1); |
473 | k->type = KEY_RSA1; | 472 | k->type = KEY_RSA1; |
474 | if (lookup_private_key(k, NULL, 1) == NULL) { | 473 | if (lookup_identity(k, 1) == NULL) { |
475 | if (tab->nentries == 0) | 474 | Identity *id = xmalloc(sizeof(Identity)); |
476 | tab->identities = xmalloc(sizeof(Identity)); | ||
477 | else | ||
478 | tab->identities = xrealloc(tab->identities, | ||
479 | (tab->nentries + 1) * sizeof(Identity)); | ||
480 | n = key_new(KEY_RSA1); | 475 | n = key_new(KEY_RSA1); |
481 | BN_copy(n->rsa->n, k->rsa->n); | 476 | BN_copy(n->rsa->n, k->rsa->n); |
482 | BN_copy(n->rsa->e, k->rsa->e); | 477 | BN_copy(n->rsa->e, k->rsa->e); |
483 | RSA_set_method(n->rsa, sc_get_engine()); | 478 | RSA_set_method(n->rsa, sc_get_engine()); |
484 | tab->identities[tab->nentries].key = n; | 479 | id->key = n; |
485 | tab->identities[tab->nentries].comment = | 480 | id->comment = xstrdup("rsa1 smartcard"); |
486 | xstrdup("rsa1 smartcard"); | 481 | TAILQ_INSERT_TAIL(&tab->idlist, id, next); |
487 | tab->nentries++; | 482 | tab->nentries++; |
488 | } | 483 | } |
489 | k->type = KEY_RSA; | 484 | k->type = KEY_RSA; |
490 | tab = idtab_lookup(2); | 485 | tab = idtab_lookup(2); |
491 | if (lookup_private_key(k, NULL, 2) == NULL) { | 486 | if (lookup_identity(k, 2) == NULL) { |
492 | if (tab->nentries == 0) | 487 | Identity *id = xmalloc(sizeof(Identity)); |
493 | tab->identities = xmalloc(sizeof(Identity)); | ||
494 | else | ||
495 | tab->identities = xrealloc(tab->identities, | ||
496 | (tab->nentries + 1) * sizeof(Identity)); | ||
497 | n = key_new(KEY_RSA); | 488 | n = key_new(KEY_RSA); |
498 | BN_copy(n->rsa->n, k->rsa->n); | 489 | BN_copy(n->rsa->n, k->rsa->n); |
499 | BN_copy(n->rsa->e, k->rsa->e); | 490 | BN_copy(n->rsa->e, k->rsa->e); |
500 | RSA_set_method(n->rsa, sc_get_engine()); | 491 | RSA_set_method(n->rsa, sc_get_engine()); |
501 | tab->identities[tab->nentries].key = n; | 492 | id->key = n; |
502 | tab->identities[tab->nentries].comment = | 493 | id->comment = xstrdup("rsa smartcard"); |
503 | xstrdup("rsa smartcard"); | 494 | TAILQ_INSERT_TAIL(&tab->idlist, id, next); |
504 | tab->nentries++; | 495 | tab->nentries++; |
505 | } | 496 | } |
506 | key_free(k); | 497 | key_free(k); |
@@ -513,8 +504,7 @@ send: | |||
513 | static void | 504 | static void |
514 | process_remove_smartcard_key(SocketEntry *e) | 505 | process_remove_smartcard_key(SocketEntry *e) |
515 | { | 506 | { |
516 | Key *k = NULL, *private; | 507 | Key *k = NULL; |
517 | int idx; | ||
518 | int success = 0; | 508 | int success = 0; |
519 | char *sc_reader_id = NULL; | 509 | char *sc_reader_id = NULL; |
520 | 510 | ||
@@ -525,25 +515,22 @@ process_remove_smartcard_key(SocketEntry *e) | |||
525 | if (k == NULL) { | 515 | if (k == NULL) { |
526 | error("sc_get_pubkey failed"); | 516 | error("sc_get_pubkey failed"); |
527 | } else { | 517 | } else { |
518 | Identity *id; | ||
528 | k->type = KEY_RSA1; | 519 | k->type = KEY_RSA1; |
529 | private = lookup_private_key(k, &idx, 1); | 520 | id = lookup_identity(k, 1); |
530 | if (private != NULL) { | 521 | if (id != NULL) { |
531 | Idtab *tab = idtab_lookup(1); | 522 | Idtab *tab = idtab_lookup(1); |
532 | key_free(tab->identities[idx].key); | 523 | TAILQ_REMOVE(&tab->idlist, id, next); |
533 | xfree(tab->identities[idx].comment); | 524 | free_identity(id); |
534 | if (idx != tab->nentries) | ||
535 | tab->identities[idx] = tab->identities[tab->nentries]; | ||
536 | tab->nentries--; | 525 | tab->nentries--; |
537 | success = 1; | 526 | success = 1; |
538 | } | 527 | } |
539 | k->type = KEY_RSA; | 528 | k->type = KEY_RSA; |
540 | private = lookup_private_key(k, &idx, 2); | 529 | id = lookup_identity(k, 2); |
541 | if (private != NULL) { | 530 | if (id != NULL) { |
542 | Idtab *tab = idtab_lookup(2); | 531 | Idtab *tab = idtab_lookup(2); |
543 | key_free(tab->identities[idx].key); | 532 | TAILQ_REMOVE(&tab->idlist, id, next); |
544 | xfree(tab->identities[idx].comment); | 533 | free_identity(id); |
545 | if (idx != tab->nentries) | ||
546 | tab->identities[idx] = tab->identities[tab->nentries]; | ||
547 | tab->nentries--; | 534 | tab->nentries--; |
548 | success = 1; | 535 | success = 1; |
549 | } | 536 | } |