]> andersk Git - gssapi-openssh.git/blob - openssh/sshconnect2.c
openssh-4.4p1-gsskex-20061002.patch
[gssapi-openssh.git] / openssh / sshconnect2.c
1 /* $OpenBSD: sshconnect2.c,v 1.162 2006/08/30 00:06:51 dtucker Exp $ */
2 /*
3  * Copyright (c) 2000 Markus Friedl.  All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  *
14  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
15  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
16  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
17  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
18  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
19  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
20  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
21  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
23  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24  */
25
26 #include "includes.h"
27
28 #include <sys/types.h>
29 #include <sys/socket.h>
30 #include <sys/wait.h>
31 #include <sys/stat.h>
32
33 #include <errno.h>
34 #include <pwd.h>
35 #include <signal.h>
36 #include <stdarg.h>
37 #include <stdio.h>
38 #include <string.h>
39 #include <unistd.h>
40
41 #include "openbsd-compat/sys-queue.h"
42
43 #include "xmalloc.h"
44 #include "ssh.h"
45 #include "ssh2.h"
46 #include "buffer.h"
47 #include "packet.h"
48 #include "compat.h"
49 #include "cipher.h"
50 #include "key.h"
51 #include "kex.h"
52 #include "myproposal.h"
53 #include "sshconnect.h"
54 #include "authfile.h"
55 #include "dh.h"
56 #include "authfd.h"
57 #include "log.h"
58 #include "readconf.h"
59 #include "misc.h"
60 #include "match.h"
61 #include "dispatch.h"
62 #include "canohost.h"
63 #include "msg.h"
64 #include "pathnames.h"
65 #include "uidswap.h"
66
67 #ifdef GSSAPI
68 #include "ssh-gss.h"
69 #endif
70
71 /* import */
72 extern char *client_version_string;
73 extern char *server_version_string;
74 extern Options options;
75
76 /*
77  * SSH2 key exchange
78  */
79
80 u_char *session_id2 = NULL;
81 u_int session_id2_len = 0;
82
83 char *xxx_host;
84 struct sockaddr *xxx_hostaddr;
85
86 Kex *xxx_kex = NULL;
87
88 static int
89 verify_host_key_callback(Key *hostkey)
90 {
91         if (verify_host_key(xxx_host, xxx_hostaddr, hostkey) == -1)
92                 fatal("Host key verification failed.");
93         return 0;
94 }
95
96 void
97 ssh_kex2(char *host, struct sockaddr *hostaddr)
98 {
99         Kex *kex;
100
101 #ifdef GSSAPI
102         char *orig = NULL, *gss = NULL;
103         char *gss_host = NULL;
104 #endif
105
106         xxx_host = host;
107         xxx_hostaddr = hostaddr;
108
109 #ifdef GSSAPI
110         if (options.gss_keyex) {
111                 /* Add the GSSAPI mechanisms currently supported on this 
112                  * client to the key exchange algorithm proposal */
113                 orig = myproposal[PROPOSAL_KEX_ALGS];
114
115                 if (options.gss_trust_dns)
116                         gss_host = (char *)get_canonical_hostname(1);
117                 else
118                         gss_host = host;
119
120                 gss = ssh_gssapi_client_mechanisms(gss_host);
121                 if (gss) {
122                         debug("Offering GSSAPI proposal: %s", gss);
123                         xasprintf(&myproposal[PROPOSAL_KEX_ALGS],
124                             "%s,%s", gss, orig);
125                 }
126         }
127 #endif
128
129         if (options.ciphers == (char *)-1) {
130                 logit("No valid ciphers for protocol version 2 given, using defaults.");
131                 options.ciphers = NULL;
132         }
133         if (options.ciphers != NULL) {
134                 myproposal[PROPOSAL_ENC_ALGS_CTOS] =
135                 myproposal[PROPOSAL_ENC_ALGS_STOC] = options.ciphers;
136         }
137         myproposal[PROPOSAL_ENC_ALGS_CTOS] =
138             compat_cipher_proposal(myproposal[PROPOSAL_ENC_ALGS_CTOS]);
139         myproposal[PROPOSAL_ENC_ALGS_STOC] =
140             compat_cipher_proposal(myproposal[PROPOSAL_ENC_ALGS_STOC]);
141         if (options.compression) {
142                 myproposal[PROPOSAL_COMP_ALGS_CTOS] =
143                 myproposal[PROPOSAL_COMP_ALGS_STOC] = "zlib@openssh.com,zlib,none";
144         } else {
145                 myproposal[PROPOSAL_COMP_ALGS_CTOS] =
146                 myproposal[PROPOSAL_COMP_ALGS_STOC] = "none,zlib@openssh.com,zlib";
147         }
148         if (options.macs != NULL) {
149                 myproposal[PROPOSAL_MAC_ALGS_CTOS] =
150                 myproposal[PROPOSAL_MAC_ALGS_STOC] = options.macs;
151         }
152         if (options.hostkeyalgorithms != NULL)
153                 myproposal[PROPOSAL_SERVER_HOST_KEY_ALGS] =
154                     options.hostkeyalgorithms;
155
156 #ifdef GSSAPI
157         /* If we've got GSSAPI algorithms, then we also support the
158          * 'null' hostkey, as a last resort */
159         if (options.gss_keyex && gss) {
160                 orig = myproposal[PROPOSAL_SERVER_HOST_KEY_ALGS];
161                 xasprintf(&myproposal[PROPOSAL_SERVER_HOST_KEY_ALGS], 
162                     "%s,null", orig);
163         }
164 #endif
165
166         if (options.rekey_limit)
167                 packet_set_rekey_limit(options.rekey_limit);
168
169         /* start key exchange */
170         kex = kex_setup(myproposal);
171         kex->kex[KEX_DH_GRP1_SHA1] = kexdh_client;
172         kex->kex[KEX_DH_GRP14_SHA1] = kexdh_client;
173         kex->kex[KEX_DH_GEX_SHA1] = kexgex_client;
174         kex->kex[KEX_DH_GEX_SHA256] = kexgex_client;
175 #ifdef GSSAPI
176         kex->kex[KEX_GSS_GRP1_SHA1] = kexgss_client;
177         kex->kex[KEX_GSS_GRP14_SHA1] = kexgss_client;
178         kex->kex[KEX_GSS_GEX_SHA1] = kexgss_client;
179 #endif
180         kex->client_version_string=client_version_string;
181         kex->server_version_string=server_version_string;
182         kex->verify_host_key=&verify_host_key_callback;
183
184 #ifdef GSSAPI
185         kex->gss_deleg_creds = options.gss_deleg_creds;
186         kex->gss_trust_dns = options.gss_trust_dns;
187         kex->gss_host = gss_host;
188 #endif
189
190         xxx_kex = kex;
191
192         dispatch_run(DISPATCH_BLOCK, &kex->done, kex);
193
194         session_id2 = kex->session_id;
195         session_id2_len = kex->session_id_len;
196
197 #ifdef DEBUG_KEXDH
198         /* send 1st encrypted/maced/compressed message */
199         packet_start(SSH2_MSG_IGNORE);
200         packet_put_cstring("markus");
201         packet_send();
202         packet_write_wait();
203 #endif
204 }
205
206 /*
207  * Authenticate user
208  */
209
210 typedef struct Authctxt Authctxt;
211 typedef struct Authmethod Authmethod;
212 typedef struct identity Identity;
213 typedef struct idlist Idlist;
214
215 struct identity {
216         TAILQ_ENTRY(identity) next;
217         AuthenticationConnection *ac;   /* set if agent supports key */
218         Key     *key;                   /* public/private key */
219         char    *filename;              /* comment for agent-only keys */
220         int     tried;
221         int     isprivate;              /* key points to the private key */
222 };
223 TAILQ_HEAD(idlist, identity);
224
225 struct Authctxt {
226         const char *server_user;
227         const char *local_user;
228         const char *host;
229         const char *service;
230         Authmethod *method;
231         int success;
232         char *authlist;
233         /* pubkey */
234         Idlist keys;
235         AuthenticationConnection *agent;
236         /* hostbased */
237         Sensitive *sensitive;
238         /* kbd-interactive */
239         int info_req_seen;
240         /* generic */
241         void *methoddata;
242 };
243 struct Authmethod {
244         char    *name;          /* string to compare against server's list */
245         int     (*userauth)(Authctxt *authctxt);
246         int     *enabled;       /* flag in option struct that enables method */
247         int     *batch_flag;    /* flag in option struct that disables method */
248 };
249
250 void    input_userauth_success(int, u_int32_t, void *);
251 void    input_userauth_failure(int, u_int32_t, void *);
252 void    input_userauth_banner(int, u_int32_t, void *);
253 void    input_userauth_error(int, u_int32_t, void *);
254 void    input_userauth_info_req(int, u_int32_t, void *);
255 void    input_userauth_pk_ok(int, u_int32_t, void *);
256 void    input_userauth_passwd_changereq(int, u_int32_t, void *);
257
258 int     userauth_none(Authctxt *);
259 int     userauth_pubkey(Authctxt *);
260 int     userauth_passwd(Authctxt *);
261 int     userauth_kbdint(Authctxt *);
262 int     userauth_hostbased(Authctxt *);
263 int     userauth_kerberos(Authctxt *);
264
265 #ifdef GSSAPI
266 int     userauth_gssapi(Authctxt *authctxt);
267 void    input_gssapi_response(int type, u_int32_t, void *);
268 void    input_gssapi_token(int type, u_int32_t, void *);
269 void    input_gssapi_hash(int type, u_int32_t, void *);
270 void    input_gssapi_error(int, u_int32_t, void *);
271 void    input_gssapi_errtok(int, u_int32_t, void *);
272 int     userauth_gsskeyex(Authctxt *authctxt);
273 #endif
274
275 void    userauth(Authctxt *, char *);
276
277 static int sign_and_send_pubkey(Authctxt *, Identity *);
278 static void pubkey_prepare(Authctxt *);
279 static void pubkey_cleanup(Authctxt *);
280 static Key *load_identity_file(char *);
281
282 static Authmethod *authmethod_get(char *authlist);
283 static Authmethod *authmethod_lookup(const char *name);
284 static char *authmethods_get(void);
285
286 Authmethod authmethods[] = {
287 #ifdef GSSAPI
288         {"gssapi-keyex",
289                 userauth_gsskeyex,
290                 &options.gss_authentication,
291                 NULL},
292         {"gssapi-with-mic",
293                 userauth_gssapi,
294                 &options.gss_authentication,
295                 NULL},
296 #endif
297         {"hostbased",
298                 userauth_hostbased,
299                 &options.hostbased_authentication,
300                 NULL},
301         {"publickey",
302                 userauth_pubkey,
303                 &options.pubkey_authentication,
304                 NULL},
305         {"keyboard-interactive",
306                 userauth_kbdint,
307                 &options.kbd_interactive_authentication,
308                 &options.batch_mode},
309         {"password",
310                 userauth_passwd,
311                 &options.password_authentication,
312                 &options.batch_mode},
313         {"none",
314                 userauth_none,
315                 NULL,
316                 NULL},
317         {NULL, NULL, NULL, NULL}
318 };
319
320 void
321 ssh_userauth2(const char *local_user, const char *server_user, char *host,
322     Sensitive *sensitive)
323 {
324         Authctxt authctxt;
325         int type;
326
327         if (options.challenge_response_authentication)
328                 options.kbd_interactive_authentication = 1;
329
330         packet_start(SSH2_MSG_SERVICE_REQUEST);
331         packet_put_cstring("ssh-userauth");
332         packet_send();
333         debug("SSH2_MSG_SERVICE_REQUEST sent");
334         packet_write_wait();
335         type = packet_read();
336         if (type != SSH2_MSG_SERVICE_ACCEPT)
337                 fatal("Server denied authentication request: %d", type);
338         if (packet_remaining() > 0) {
339                 char *reply = packet_get_string(NULL);
340                 debug2("service_accept: %s", reply);
341                 xfree(reply);
342         } else {
343                 debug2("buggy server: service_accept w/o service");
344         }
345         packet_check_eom();
346         debug("SSH2_MSG_SERVICE_ACCEPT received");
347
348         if (options.preferred_authentications == NULL)
349                 options.preferred_authentications = authmethods_get();
350
351         /* setup authentication context */
352         memset(&authctxt, 0, sizeof(authctxt));
353         pubkey_prepare(&authctxt);
354         authctxt.server_user = server_user;
355         authctxt.local_user = local_user;
356         authctxt.host = host;
357         authctxt.service = "ssh-connection";            /* service name */
358         authctxt.success = 0;
359         authctxt.method = authmethod_lookup("none");
360         authctxt.authlist = NULL;
361         authctxt.methoddata = NULL;
362         authctxt.sensitive = sensitive;
363         authctxt.info_req_seen = 0;
364         if (authctxt.method == NULL)
365                 fatal("ssh_userauth2: internal error: cannot send userauth none request");
366
367         /* initial userauth request */
368         userauth_none(&authctxt);
369
370         dispatch_init(&input_userauth_error);
371         dispatch_set(SSH2_MSG_USERAUTH_SUCCESS, &input_userauth_success);
372         dispatch_set(SSH2_MSG_USERAUTH_FAILURE, &input_userauth_failure);
373         dispatch_set(SSH2_MSG_USERAUTH_BANNER, &input_userauth_banner);
374         dispatch_run(DISPATCH_BLOCK, &authctxt.success, &authctxt);     /* loop until success */
375
376         pubkey_cleanup(&authctxt);
377         dispatch_range(SSH2_MSG_USERAUTH_MIN, SSH2_MSG_USERAUTH_MAX, NULL);
378
379         debug("Authentication succeeded (%s).", authctxt.method->name);
380 }
381
382 void
383 userauth(Authctxt *authctxt, char *authlist)
384 {
385         if (authctxt->methoddata) {
386                 xfree(authctxt->methoddata);
387                 authctxt->methoddata = NULL;
388         }
389         if (authlist == NULL) {
390                 authlist = authctxt->authlist;
391         } else {
392                 if (authctxt->authlist)
393                         xfree(authctxt->authlist);
394                 authctxt->authlist = authlist;
395         }
396         for (;;) {
397                 Authmethod *method = authmethod_get(authlist);
398                 if (method == NULL)
399                         fatal("Permission denied (%s).", authlist);
400                 authctxt->method = method;
401
402                 /* reset the per method handler */
403                 dispatch_range(SSH2_MSG_USERAUTH_PER_METHOD_MIN,
404                     SSH2_MSG_USERAUTH_PER_METHOD_MAX, NULL);
405
406                 /* and try new method */
407                 if (method->userauth(authctxt) != 0) {
408                         debug2("we sent a %s packet, wait for reply", method->name);
409                         break;
410                 } else {
411                         debug2("we did not send a packet, disable method");
412                         method->enabled = NULL;
413                 }
414         }
415 }
416
417 void
418 input_userauth_error(int type, u_int32_t seq, void *ctxt)
419 {
420         fatal("input_userauth_error: bad message during authentication: "
421             "type %d", type);
422 }
423
424 void
425 input_userauth_banner(int type, u_int32_t seq, void *ctxt)
426 {
427         char *msg, *lang;
428
429         debug3("input_userauth_banner");
430         msg = packet_get_string(NULL);
431         lang = packet_get_string(NULL);
432         if (options.log_level >= SYSLOG_LEVEL_INFO)
433                 fprintf(stderr, "%s", msg);
434         xfree(msg);
435         xfree(lang);
436 }
437
438 void
439 input_userauth_success(int type, u_int32_t seq, void *ctxt)
440 {
441         Authctxt *authctxt = ctxt;
442         if (authctxt == NULL)
443                 fatal("input_userauth_success: no authentication context");
444         if (authctxt->authlist) {
445                 xfree(authctxt->authlist);
446                 authctxt->authlist = NULL;
447         }
448         if (authctxt->methoddata) {
449                 xfree(authctxt->methoddata);
450                 authctxt->methoddata = NULL;
451         }
452         authctxt->success = 1;                  /* break out */
453 }
454
455 void
456 input_userauth_failure(int type, u_int32_t seq, void *ctxt)
457 {
458         Authctxt *authctxt = ctxt;
459         char *authlist = NULL;
460         int partial;
461
462         if (authctxt == NULL)
463                 fatal("input_userauth_failure: no authentication context");
464
465         authlist = packet_get_string(NULL);
466         partial = packet_get_char();
467         packet_check_eom();
468
469         if (partial != 0)
470                 logit("Authenticated with partial success.");
471         debug("Authentications that can continue: %s", authlist);
472
473         userauth(authctxt, authlist);
474 }
475 void
476 input_userauth_pk_ok(int type, u_int32_t seq, void *ctxt)
477 {
478         Authctxt *authctxt = ctxt;
479         Key *key = NULL;
480         Identity *id = NULL;
481         Buffer b;
482         int pktype, sent = 0;
483         u_int alen, blen;
484         char *pkalg, *fp;
485         u_char *pkblob;
486
487         if (authctxt == NULL)
488                 fatal("input_userauth_pk_ok: no authentication context");
489         if (datafellows & SSH_BUG_PKOK) {
490                 /* this is similar to SSH_BUG_PKAUTH */
491                 debug2("input_userauth_pk_ok: SSH_BUG_PKOK");
492                 pkblob = packet_get_string(&blen);
493                 buffer_init(&b);
494                 buffer_append(&b, pkblob, blen);
495                 pkalg = buffer_get_string(&b, &alen);
496                 buffer_free(&b);
497         } else {
498                 pkalg = packet_get_string(&alen);
499                 pkblob = packet_get_string(&blen);
500         }
501         packet_check_eom();
502
503         debug("Server accepts key: pkalg %s blen %u", pkalg, blen);
504
505         if ((pktype = key_type_from_name(pkalg)) == KEY_UNSPEC) {
506                 debug("unknown pkalg %s", pkalg);
507                 goto done;
508         }
509         if ((key = key_from_blob(pkblob, blen)) == NULL) {
510                 debug("no key from blob. pkalg %s", pkalg);
511                 goto done;
512         }
513         if (key->type != pktype) {
514                 error("input_userauth_pk_ok: type mismatch "
515                     "for decoded key (received %d, expected %d)",
516                     key->type, pktype);
517                 goto done;
518         }
519         fp = key_fingerprint(key, SSH_FP_MD5, SSH_FP_HEX);
520         debug2("input_userauth_pk_ok: fp %s", fp);
521         xfree(fp);
522
523         /*
524          * search keys in the reverse order, because last candidate has been
525          * moved to the end of the queue.  this also avoids confusion by
526          * duplicate keys
527          */
528         TAILQ_FOREACH_REVERSE(id, &authctxt->keys, idlist, next) {
529                 if (key_equal(key, id->key)) {
530                         sent = sign_and_send_pubkey(authctxt, id);
531                         break;
532                 }
533         }
534 done:
535         if (key != NULL)
536                 key_free(key);
537         xfree(pkalg);
538         xfree(pkblob);
539
540         /* try another method if we did not send a packet */
541         if (sent == 0)
542                 userauth(authctxt, NULL);
543 }
544
545 #ifdef GSSAPI
546 int
547 userauth_gssapi(Authctxt *authctxt)
548 {
549         Gssctxt *gssctxt = NULL;
550         static gss_OID_set gss_supported = NULL;
551         static u_int mech = 0;
552         OM_uint32 min;
553         int ok = 0;
554         char *gss_host = NULL;
555
556         if (options.gss_trust_dns)
557                 gss_host = (char *)get_canonical_hostname(1);
558         else
559                 gss_host = (char *)authctxt->host;
560
561         /* Try one GSSAPI method at a time, rather than sending them all at
562          * once. */
563
564         if (gss_supported == NULL)
565                 gss_indicate_mechs(&min, &gss_supported);
566
567         /* Check to see if the mechanism is usable before we offer it */
568         while (mech < gss_supported->count && !ok) {
569                 /* My DER encoding requires length<128 */
570                 if (gss_supported->elements[mech].length < 128 &&
571                     ssh_gssapi_check_mechanism(&gssctxt, 
572                     &gss_supported->elements[mech], gss_host)) {
573                         ok = 1; /* Mechanism works */
574                 } else {
575                         mech++;
576                 }
577         }
578
579         if (!ok)
580                 return 0;
581
582         authctxt->methoddata=(void *)gssctxt;
583
584         packet_start(SSH2_MSG_USERAUTH_REQUEST);
585         packet_put_cstring(authctxt->server_user);
586         packet_put_cstring(authctxt->service);
587         packet_put_cstring(authctxt->method->name);
588
589         packet_put_int(1);
590
591         packet_put_int((gss_supported->elements[mech].length) + 2);
592         packet_put_char(SSH_GSS_OIDTYPE);
593         packet_put_char(gss_supported->elements[mech].length);
594         packet_put_raw(gss_supported->elements[mech].elements,
595             gss_supported->elements[mech].length);
596
597         packet_send();
598
599         dispatch_set(SSH2_MSG_USERAUTH_GSSAPI_RESPONSE, &input_gssapi_response);
600         dispatch_set(SSH2_MSG_USERAUTH_GSSAPI_TOKEN, &input_gssapi_token);
601         dispatch_set(SSH2_MSG_USERAUTH_GSSAPI_ERROR, &input_gssapi_error);
602         dispatch_set(SSH2_MSG_USERAUTH_GSSAPI_ERRTOK, &input_gssapi_errtok);
603
604         mech++; /* Move along to next candidate */
605
606         return 1;
607 }
608
609 static OM_uint32
610 process_gssapi_token(void *ctxt, gss_buffer_t recv_tok)
611 {
612         Authctxt *authctxt = ctxt;
613         Gssctxt *gssctxt = authctxt->methoddata;
614         gss_buffer_desc send_tok = GSS_C_EMPTY_BUFFER;
615         gss_buffer_desc mic = GSS_C_EMPTY_BUFFER;
616         gss_buffer_desc gssbuf;
617         OM_uint32 status, ms, flags;
618         Buffer b;
619
620         status = ssh_gssapi_init_ctx(gssctxt, options.gss_deleg_creds,
621             recv_tok, &send_tok, &flags);
622
623         if (send_tok.length > 0) {
624                 if (GSS_ERROR(status))
625                         packet_start(SSH2_MSG_USERAUTH_GSSAPI_ERRTOK);
626                 else
627                         packet_start(SSH2_MSG_USERAUTH_GSSAPI_TOKEN);
628
629                 packet_put_string(send_tok.value, send_tok.length);
630                 packet_send();
631                 gss_release_buffer(&ms, &send_tok);
632         }
633
634         if (status == GSS_S_COMPLETE) {
635                 /* send either complete or MIC, depending on mechanism */
636                 if (!(flags & GSS_C_INTEG_FLAG)) {
637                         packet_start(SSH2_MSG_USERAUTH_GSSAPI_EXCHANGE_COMPLETE);
638                         packet_send();
639                 } else {
640                         ssh_gssapi_buildmic(&b, authctxt->server_user,
641                             authctxt->service, "gssapi-with-mic");
642
643                         gssbuf.value = buffer_ptr(&b);
644                         gssbuf.length = buffer_len(&b);
645
646                         status = ssh_gssapi_sign(gssctxt, &gssbuf, &mic);
647
648                         if (!GSS_ERROR(status)) {
649                                 packet_start(SSH2_MSG_USERAUTH_GSSAPI_MIC);
650                                 packet_put_string(mic.value, mic.length);
651
652                                 packet_send();
653                         }
654
655                         buffer_free(&b);
656                         gss_release_buffer(&ms, &mic);
657                 }
658         }
659
660         return status;
661 }
662
663 void
664 input_gssapi_response(int type, u_int32_t plen, void *ctxt)
665 {
666         Authctxt *authctxt = ctxt;
667         Gssctxt *gssctxt;
668         u_int oidlen;
669         u_char *oidv;
670
671         if (authctxt == NULL)
672                 fatal("input_gssapi_response: no authentication context");
673         gssctxt = authctxt->methoddata;
674
675         /* Setup our OID */
676         oidv = packet_get_string(&oidlen);
677
678         if (oidlen <= 2 ||
679             oidv[0] != SSH_GSS_OIDTYPE ||
680             oidv[1] != oidlen - 2) {
681                 xfree(oidv);
682                 debug("Badly encoded mechanism OID received");
683                 userauth(authctxt, NULL);
684                 return;
685         }
686
687         if (!ssh_gssapi_check_oid(gssctxt, oidv + 2, oidlen - 2))
688                 fatal("Server returned different OID than expected");
689
690         packet_check_eom();
691
692         xfree(oidv);
693
694         if (GSS_ERROR(process_gssapi_token(ctxt, GSS_C_NO_BUFFER))) {
695                 /* Start again with next method on list */
696                 debug("Trying to start again");
697                 userauth(authctxt, NULL);
698                 return;
699         }
700 }
701
702 void
703 input_gssapi_token(int type, u_int32_t plen, void *ctxt)
704 {
705         Authctxt *authctxt = ctxt;
706         gss_buffer_desc recv_tok;
707         OM_uint32 status;
708         u_int slen;
709
710         if (authctxt == NULL)
711                 fatal("input_gssapi_response: no authentication context");
712
713         recv_tok.value = packet_get_string(&slen);
714         recv_tok.length = slen; /* safe typecast */
715
716         packet_check_eom();
717
718         status = process_gssapi_token(ctxt, &recv_tok);
719
720         xfree(recv_tok.value);
721
722         if (GSS_ERROR(status)) {
723                 /* Start again with the next method in the list */
724                 userauth(authctxt, NULL);
725                 return;
726         }
727 }
728
729 void
730 input_gssapi_errtok(int type, u_int32_t plen, void *ctxt)
731 {
732         Authctxt *authctxt = ctxt;
733         Gssctxt *gssctxt;
734         gss_buffer_desc send_tok = GSS_C_EMPTY_BUFFER;
735         gss_buffer_desc recv_tok;
736         OM_uint32 status, ms;
737         u_int len;
738
739         if (authctxt == NULL)
740                 fatal("input_gssapi_response: no authentication context");
741         gssctxt = authctxt->methoddata;
742
743         recv_tok.value = packet_get_string(&len);
744         recv_tok.length = len;
745
746         packet_check_eom();
747
748         /* Stick it into GSSAPI and see what it says */
749         status = ssh_gssapi_init_ctx(gssctxt, options.gss_deleg_creds,
750             &recv_tok, &send_tok, NULL);
751
752         xfree(recv_tok.value);
753         gss_release_buffer(&ms, &send_tok);
754
755         /* Server will be returning a failed packet after this one */
756 }
757
758 void
759 input_gssapi_error(int type, u_int32_t plen, void *ctxt)
760 {
761         OM_uint32 maj, min;
762         char *msg;
763         char *lang;
764
765         maj=packet_get_int();
766         min=packet_get_int();
767         msg=packet_get_string(NULL);
768         lang=packet_get_string(NULL);
769
770         packet_check_eom();
771
772         debug("Server GSSAPI Error:\n%s", msg);
773         xfree(msg);
774         xfree(lang);
775 }
776
777 int
778 userauth_gsskeyex(Authctxt *authctxt)
779 {
780         Buffer b;
781         gss_buffer_desc gssbuf;
782         gss_buffer_desc mic = GSS_C_EMPTY_BUFFER;
783         OM_uint32 ms;
784
785         static int attempt = 0;
786         if (attempt++ >= 1)
787                 return (0);
788
789         if (gss_kex_context == NULL) {
790                 debug("No valid Key exchange context"); 
791                 return (0);
792         }
793
794         ssh_gssapi_buildmic(&b, authctxt->server_user, authctxt->service,
795             "gssapi-keyex");
796
797         gssbuf.value = buffer_ptr(&b);
798         gssbuf.length = buffer_len(&b);
799
800         if (GSS_ERROR(ssh_gssapi_sign(gss_kex_context, &gssbuf, &mic))) {
801                 buffer_free(&b);
802                 return (0);
803         }
804
805         packet_start(SSH2_MSG_USERAUTH_REQUEST);
806         packet_put_cstring(authctxt->server_user);
807         packet_put_cstring(authctxt->service);
808         packet_put_cstring(authctxt->method->name);
809         packet_put_string(mic.value, mic.length);
810         packet_send();
811
812         buffer_free(&b);
813         gss_release_buffer(&ms, &mic);
814
815         return (1);
816 }
817
818 #endif /* GSSAPI */
819
820 int
821 userauth_none(Authctxt *authctxt)
822 {
823         /* initial userauth request */
824         packet_start(SSH2_MSG_USERAUTH_REQUEST);
825         packet_put_cstring(authctxt->server_user);
826         packet_put_cstring(authctxt->service);
827         packet_put_cstring(authctxt->method->name);
828         packet_send();
829         return 1;
830 }
831
832 int
833 userauth_passwd(Authctxt *authctxt)
834 {
835         static int attempt = 0;
836         char prompt[150];
837         char *password;
838
839         if (attempt++ >= options.number_of_password_prompts)
840                 return 0;
841
842         if (attempt != 1)
843                 error("Permission denied, please try again.");
844
845         snprintf(prompt, sizeof(prompt), "%.30s@%.128s's password: ",
846             authctxt->server_user, authctxt->host);
847         password = read_passphrase(prompt, 0);
848         packet_start(SSH2_MSG_USERAUTH_REQUEST);
849         packet_put_cstring(authctxt->server_user);
850         packet_put_cstring(authctxt->service);
851         packet_put_cstring(authctxt->method->name);
852         packet_put_char(0);
853         packet_put_cstring(password);
854         memset(password, 0, strlen(password));
855         xfree(password);
856         packet_add_padding(64);
857         packet_send();
858
859         dispatch_set(SSH2_MSG_USERAUTH_PASSWD_CHANGEREQ,
860             &input_userauth_passwd_changereq);
861
862         return 1;
863 }
864 /*
865  * parse PASSWD_CHANGEREQ, prompt user and send SSH2_MSG_USERAUTH_REQUEST
866  */
867 void
868 input_userauth_passwd_changereq(int type, u_int32_t seqnr, void *ctxt)
869 {
870         Authctxt *authctxt = ctxt;
871         char *info, *lang, *password = NULL, *retype = NULL;
872         char prompt[150];
873
874         debug2("input_userauth_passwd_changereq");
875
876         if (authctxt == NULL)
877                 fatal("input_userauth_passwd_changereq: "
878                     "no authentication context");
879
880         info = packet_get_string(NULL);
881         lang = packet_get_string(NULL);
882         if (strlen(info) > 0)
883                 logit("%s", info);
884         xfree(info);
885         xfree(lang);
886         packet_start(SSH2_MSG_USERAUTH_REQUEST);
887         packet_put_cstring(authctxt->server_user);
888         packet_put_cstring(authctxt->service);
889         packet_put_cstring(authctxt->method->name);
890         packet_put_char(1);                     /* additional info */
891         snprintf(prompt, sizeof(prompt),
892             "Enter %.30s@%.128s's old password: ",
893             authctxt->server_user, authctxt->host);
894         password = read_passphrase(prompt, 0);
895         packet_put_cstring(password);
896         memset(password, 0, strlen(password));
897         xfree(password);
898         password = NULL;
899         while (password == NULL) {
900                 snprintf(prompt, sizeof(prompt),
901                     "Enter %.30s@%.128s's new password: ",
902                     authctxt->server_user, authctxt->host);
903                 password = read_passphrase(prompt, RP_ALLOW_EOF);
904                 if (password == NULL) {
905                         /* bail out */
906                         return;
907                 }
908                 snprintf(prompt, sizeof(prompt),
909                     "Retype %.30s@%.128s's new password: ",
910                     authctxt->server_user, authctxt->host);
911                 retype = read_passphrase(prompt, 0);
912                 if (strcmp(password, retype) != 0) {
913                         memset(password, 0, strlen(password));
914                         xfree(password);
915                         logit("Mismatch; try again, EOF to quit.");
916                         password = NULL;
917                 }
918                 memset(retype, 0, strlen(retype));
919                 xfree(retype);
920         }
921         packet_put_cstring(password);
922         memset(password, 0, strlen(password));
923         xfree(password);
924         packet_add_padding(64);
925         packet_send();
926
927         dispatch_set(SSH2_MSG_USERAUTH_PASSWD_CHANGEREQ,
928             &input_userauth_passwd_changereq);
929 }
930
931 static int
932 identity_sign(Identity *id, u_char **sigp, u_int *lenp,
933     u_char *data, u_int datalen)
934 {
935         Key *prv;
936         int ret;
937
938         /* the agent supports this key */
939         if (id->ac)
940                 return (ssh_agent_sign(id->ac, id->key, sigp, lenp,
941                     data, datalen));
942         /*
943          * we have already loaded the private key or
944          * the private key is stored in external hardware
945          */
946         if (id->isprivate || (id->key->flags & KEY_FLAG_EXT))
947                 return (key_sign(id->key, sigp, lenp, data, datalen));
948         /* load the private key from the file */
949         if ((prv = load_identity_file(id->filename)) == NULL)
950                 return (-1);
951         ret = key_sign(prv, sigp, lenp, data, datalen);
952         key_free(prv);
953         return (ret);
954 }
955
956 static int
957 sign_and_send_pubkey(Authctxt *authctxt, Identity *id)
958 {
959         Buffer b;
960         u_char *blob, *signature;
961         u_int bloblen, slen;
962         u_int skip = 0;
963         int ret = -1;
964         int have_sig = 1;
965
966         debug3("sign_and_send_pubkey");
967
968         if (key_to_blob(id->key, &blob, &bloblen) == 0) {
969                 /* we cannot handle this key */
970                 debug3("sign_and_send_pubkey: cannot handle key");
971                 return 0;
972         }
973         /* data to be signed */
974         buffer_init(&b);
975         if (datafellows & SSH_OLD_SESSIONID) {
976                 buffer_append(&b, session_id2, session_id2_len);
977                 skip = session_id2_len;
978         } else {
979                 buffer_put_string(&b, session_id2, session_id2_len);
980                 skip = buffer_len(&b);
981         }
982         buffer_put_char(&b, SSH2_MSG_USERAUTH_REQUEST);
983         buffer_put_cstring(&b, authctxt->server_user);
984         buffer_put_cstring(&b,
985             datafellows & SSH_BUG_PKSERVICE ?
986             "ssh-userauth" :
987             authctxt->service);
988         if (datafellows & SSH_BUG_PKAUTH) {
989                 buffer_put_char(&b, have_sig);
990         } else {
991                 buffer_put_cstring(&b, authctxt->method->name);
992                 buffer_put_char(&b, have_sig);
993                 buffer_put_cstring(&b, key_ssh_name(id->key));
994         }
995         buffer_put_string(&b, blob, bloblen);
996
997         /* generate signature */
998         ret = identity_sign(id, &signature, &slen,
999             buffer_ptr(&b), buffer_len(&b));
1000         if (ret == -1) {
1001                 xfree(blob);
1002                 buffer_free(&b);
1003                 return 0;
1004         }
1005 #ifdef DEBUG_PK
1006         buffer_dump(&b);
1007 #endif
1008         if (datafellows & SSH_BUG_PKSERVICE) {
1009                 buffer_clear(&b);
1010                 buffer_append(&b, session_id2, session_id2_len);
1011                 skip = session_id2_len;
1012                 buffer_put_char(&b, SSH2_MSG_USERAUTH_REQUEST);
1013                 buffer_put_cstring(&b, authctxt->server_user);
1014                 buffer_put_cstring(&b, authctxt->service);
1015                 buffer_put_cstring(&b, authctxt->method->name);
1016                 buffer_put_char(&b, have_sig);
1017                 if (!(datafellows & SSH_BUG_PKAUTH))
1018                         buffer_put_cstring(&b, key_ssh_name(id->key));
1019                 buffer_put_string(&b, blob, bloblen);
1020         }
1021         xfree(blob);
1022
1023         /* append signature */
1024         buffer_put_string(&b, signature, slen);
1025         xfree(signature);
1026
1027         /* skip session id and packet type */
1028         if (buffer_len(&b) < skip + 1)
1029                 fatal("userauth_pubkey: internal error");
1030         buffer_consume(&b, skip + 1);
1031
1032         /* put remaining data from buffer into packet */
1033         packet_start(SSH2_MSG_USERAUTH_REQUEST);
1034         packet_put_raw(buffer_ptr(&b), buffer_len(&b));
1035         buffer_free(&b);
1036         packet_send();
1037
1038         return 1;
1039 }
1040
1041 static int
1042 send_pubkey_test(Authctxt *authctxt, Identity *id)
1043 {
1044         u_char *blob;
1045         u_int bloblen, have_sig = 0;
1046
1047         debug3("send_pubkey_test");
1048
1049         if (key_to_blob(id->key, &blob, &bloblen) == 0) {
1050                 /* we cannot handle this key */
1051                 debug3("send_pubkey_test: cannot handle key");
1052                 return 0;
1053         }
1054         /* register callback for USERAUTH_PK_OK message */
1055         dispatch_set(SSH2_MSG_USERAUTH_PK_OK, &input_userauth_pk_ok);
1056
1057         packet_start(SSH2_MSG_USERAUTH_REQUEST);
1058         packet_put_cstring(authctxt->server_user);
1059         packet_put_cstring(authctxt->service);
1060         packet_put_cstring(authctxt->method->name);
1061         packet_put_char(have_sig);
1062         if (!(datafellows & SSH_BUG_PKAUTH))
1063                 packet_put_cstring(key_ssh_name(id->key));
1064         packet_put_string(blob, bloblen);
1065         xfree(blob);
1066         packet_send();
1067         return 1;
1068 }
1069
1070 static Key *
1071 load_identity_file(char *filename)
1072 {
1073         Key *private;
1074         char prompt[300], *passphrase;
1075         int perm_ok, quit, i;
1076         struct stat st;
1077
1078         if (stat(filename, &st) < 0) {
1079                 debug3("no such identity: %s", filename);
1080                 return NULL;
1081         }
1082         private = key_load_private_type(KEY_UNSPEC, filename, "", NULL, &perm_ok);
1083         if (!perm_ok)
1084                 return NULL;
1085         if (private == NULL) {
1086                 if (options.batch_mode)
1087                         return NULL;
1088                 snprintf(prompt, sizeof prompt,
1089                     "Enter passphrase for key '%.100s': ", filename);
1090                 for (i = 0; i < options.number_of_password_prompts; i++) {
1091                         passphrase = read_passphrase(prompt, 0);
1092                         if (strcmp(passphrase, "") != 0) {
1093                                 private = key_load_private_type(KEY_UNSPEC,
1094                                     filename, passphrase, NULL, NULL);
1095                                 quit = 0;
1096                         } else {
1097                                 debug2("no passphrase given, try next key");
1098                                 quit = 1;
1099                         }
1100                         memset(passphrase, 0, strlen(passphrase));
1101                         xfree(passphrase);
1102                         if (private != NULL || quit)
1103                                 break;
1104                         debug2("bad passphrase given, try again...");
1105                 }
1106         }
1107         return private;
1108 }
1109
1110 /*
1111  * try keys in the following order:
1112  *      1. agent keys that are found in the config file
1113  *      2. other agent keys
1114  *      3. keys that are only listed in the config file
1115  */
1116 static void
1117 pubkey_prepare(Authctxt *authctxt)
1118 {
1119         Identity *id;
1120         Idlist agent, files, *preferred;
1121         Key *key;
1122         AuthenticationConnection *ac;
1123         char *comment;
1124         int i, found;
1125
1126         TAILQ_INIT(&agent);     /* keys from the agent */
1127         TAILQ_INIT(&files);     /* keys from the config file */
1128         preferred = &authctxt->keys;
1129         TAILQ_INIT(preferred);  /* preferred order of keys */
1130
1131         /* list of keys stored in the filesystem */
1132         for (i = 0; i < options.num_identity_files; i++) {
1133                 key = options.identity_keys[i];
1134                 if (key && key->type == KEY_RSA1)
1135                         continue;
1136                 options.identity_keys[i] = NULL;
1137                 id = xcalloc(1, sizeof(*id));
1138                 id->key = key;
1139                 id->filename = xstrdup(options.identity_files[i]);
1140                 TAILQ_INSERT_TAIL(&files, id, next);
1141         }
1142         /* list of keys supported by the agent */
1143         if ((ac = ssh_get_authentication_connection())) {
1144                 for (key = ssh_get_first_identity(ac, &comment, 2);
1145                     key != NULL;
1146                     key = ssh_get_next_identity(ac, &comment, 2)) {
1147                         found = 0;
1148                         TAILQ_FOREACH(id, &files, next) {
1149                                 /* agent keys from the config file are preferred */
1150                                 if (key_equal(key, id->key)) {
1151                                         key_free(key);
1152                                         xfree(comment);
1153                                         TAILQ_REMOVE(&files, id, next);
1154                                         TAILQ_INSERT_TAIL(preferred, id, next);
1155                                         id->ac = ac;
1156                                         found = 1;
1157                                         break;
1158                                 }
1159                         }
1160                         if (!found && !options.identities_only) {
1161                                 id = xcalloc(1, sizeof(*id));
1162                                 id->key = key;
1163                                 id->filename = comment;
1164                                 id->ac = ac;
1165                                 TAILQ_INSERT_TAIL(&agent, id, next);
1166                         }
1167                 }
1168                 /* append remaining agent keys */
1169                 for (id = TAILQ_FIRST(&agent); id; id = TAILQ_FIRST(&agent)) {
1170                         TAILQ_REMOVE(&agent, id, next);
1171                         TAILQ_INSERT_TAIL(preferred, id, next);
1172                 }
1173                 authctxt->agent = ac;
1174         }
1175         /* append remaining keys from the config file */
1176         for (id = TAILQ_FIRST(&files); id; id = TAILQ_FIRST(&files)) {
1177                 TAILQ_REMOVE(&files, id, next);
1178                 TAILQ_INSERT_TAIL(preferred, id, next);
1179         }
1180         TAILQ_FOREACH(id, preferred, next) {
1181                 debug2("key: %s (%p)", id->filename, id->key);
1182         }
1183 }
1184
1185 static void
1186 pubkey_cleanup(Authctxt *authctxt)
1187 {
1188         Identity *id;
1189
1190         if (authctxt->agent != NULL)
1191                 ssh_close_authentication_connection(authctxt->agent);
1192         for (id = TAILQ_FIRST(&authctxt->keys); id;
1193             id = TAILQ_FIRST(&authctxt->keys)) {
1194                 TAILQ_REMOVE(&authctxt->keys, id, next);
1195                 if (id->key)
1196                         key_free(id->key);
1197                 if (id->filename)
1198                         xfree(id->filename);
1199                 xfree(id);
1200         }
1201 }
1202
1203 int
1204 userauth_pubkey(Authctxt *authctxt)
1205 {
1206         Identity *id;
1207         int sent = 0;
1208
1209         while ((id = TAILQ_FIRST(&authctxt->keys))) {
1210                 if (id->tried++)
1211                         return (0);
1212                 /* move key to the end of the queue */
1213                 TAILQ_REMOVE(&authctxt->keys, id, next);
1214                 TAILQ_INSERT_TAIL(&authctxt->keys, id, next);
1215                 /*
1216                  * send a test message if we have the public key. for
1217                  * encrypted keys we cannot do this and have to load the
1218                  * private key instead
1219                  */
1220                 if (id->key && id->key->type != KEY_RSA1) {
1221                         debug("Offering public key: %s", id->filename);
1222                         sent = send_pubkey_test(authctxt, id);
1223                 } else if (id->key == NULL) {
1224                         debug("Trying private key: %s", id->filename);
1225                         id->key = load_identity_file(id->filename);
1226                         if (id->key != NULL) {
1227                                 id->isprivate = 1;
1228                                 sent = sign_and_send_pubkey(authctxt, id);
1229                                 key_free(id->key);
1230                                 id->key = NULL;
1231                         }
1232                 }
1233                 if (sent)
1234                         return (sent);
1235         }
1236         return (0);
1237 }
1238
1239 /*
1240  * Send userauth request message specifying keyboard-interactive method.
1241  */
1242 int
1243 userauth_kbdint(Authctxt *authctxt)
1244 {
1245         static int attempt = 0;
1246
1247         if (attempt++ >= options.number_of_password_prompts)
1248                 return 0;
1249         /* disable if no SSH2_MSG_USERAUTH_INFO_REQUEST has been seen */
1250         if (attempt > 1 && !authctxt->info_req_seen) {
1251                 debug3("userauth_kbdint: disable: no info_req_seen");
1252                 dispatch_set(SSH2_MSG_USERAUTH_INFO_REQUEST, NULL);
1253                 return 0;
1254         }
1255
1256         debug2("userauth_kbdint");
1257         packet_start(SSH2_MSG_USERAUTH_REQUEST);
1258         packet_put_cstring(authctxt->server_user);
1259         packet_put_cstring(authctxt->service);
1260         packet_put_cstring(authctxt->method->name);
1261         packet_put_cstring("");                                 /* lang */
1262         packet_put_cstring(options.kbd_interactive_devices ?
1263             options.kbd_interactive_devices : "");
1264         packet_send();
1265
1266         dispatch_set(SSH2_MSG_USERAUTH_INFO_REQUEST, &input_userauth_info_req);
1267         return 1;
1268 }
1269
1270 /*
1271  * parse INFO_REQUEST, prompt user and send INFO_RESPONSE
1272  */
1273 void
1274 input_userauth_info_req(int type, u_int32_t seq, void *ctxt)
1275 {
1276         Authctxt *authctxt = ctxt;
1277         char *name, *inst, *lang, *prompt, *response;
1278         u_int num_prompts, i;
1279         int echo = 0;
1280
1281         debug2("input_userauth_info_req");
1282
1283         if (authctxt == NULL)
1284                 fatal("input_userauth_info_req: no authentication context");
1285
1286         authctxt->info_req_seen = 1;
1287
1288         name = packet_get_string(NULL);
1289         inst = packet_get_string(NULL);
1290         lang = packet_get_string(NULL);
1291         if (strlen(name) > 0)
1292                 logit("%s", name);
1293         if (strlen(inst) > 0)
1294                 logit("%s", inst);
1295         xfree(name);
1296         xfree(inst);
1297         xfree(lang);
1298
1299         num_prompts = packet_get_int();
1300         /*
1301          * Begin to build info response packet based on prompts requested.
1302          * We commit to providing the correct number of responses, so if
1303          * further on we run into a problem that prevents this, we have to
1304          * be sure and clean this up and send a correct error response.
1305          */
1306         packet_start(SSH2_MSG_USERAUTH_INFO_RESPONSE);
1307         packet_put_int(num_prompts);
1308
1309         debug2("input_userauth_info_req: num_prompts %d", num_prompts);
1310         for (i = 0; i < num_prompts; i++) {
1311                 prompt = packet_get_string(NULL);
1312                 echo = packet_get_char();
1313
1314                 response = read_passphrase(prompt, echo ? RP_ECHO : 0);
1315
1316                 packet_put_cstring(response);
1317                 memset(response, 0, strlen(response));
1318                 xfree(response);
1319                 xfree(prompt);
1320         }
1321         packet_check_eom(); /* done with parsing incoming message. */
1322
1323         packet_add_padding(64);
1324         packet_send();
1325 }
1326
1327 static int
1328 ssh_keysign(Key *key, u_char **sigp, u_int *lenp,
1329     u_char *data, u_int datalen)
1330 {
1331         Buffer b;
1332         struct stat st;
1333         pid_t pid;
1334         int to[2], from[2], status, version = 2;
1335
1336         debug2("ssh_keysign called");
1337
1338         if (stat(_PATH_SSH_KEY_SIGN, &st) < 0) {
1339                 error("ssh_keysign: no installed: %s", strerror(errno));
1340                 return -1;
1341         }
1342         if (fflush(stdout) != 0)
1343                 error("ssh_keysign: fflush: %s", strerror(errno));
1344         if (pipe(to) < 0) {
1345                 error("ssh_keysign: pipe: %s", strerror(errno));
1346                 return -1;
1347         }
1348         if (pipe(from) < 0) {
1349                 error("ssh_keysign: pipe: %s", strerror(errno));
1350                 return -1;
1351         }
1352         if ((pid = fork()) < 0) {
1353                 error("ssh_keysign: fork: %s", strerror(errno));
1354                 return -1;
1355         }
1356         if (pid == 0) {
1357                 permanently_drop_suid(getuid());
1358                 close(from[0]);
1359                 if (dup2(from[1], STDOUT_FILENO) < 0)
1360                         fatal("ssh_keysign: dup2: %s", strerror(errno));
1361                 close(to[1]);
1362                 if (dup2(to[0], STDIN_FILENO) < 0)
1363                         fatal("ssh_keysign: dup2: %s", strerror(errno));
1364                 close(from[1]);
1365                 close(to[0]);
1366                 execl(_PATH_SSH_KEY_SIGN, _PATH_SSH_KEY_SIGN, (char *) 0);
1367                 fatal("ssh_keysign: exec(%s): %s", _PATH_SSH_KEY_SIGN,
1368                     strerror(errno));
1369         }
1370         close(from[1]);
1371         close(to[0]);
1372
1373         buffer_init(&b);
1374         buffer_put_int(&b, packet_get_connection_in()); /* send # of socket */
1375         buffer_put_string(&b, data, datalen);
1376         if (ssh_msg_send(to[1], version, &b) == -1)
1377                 fatal("ssh_keysign: couldn't send request");
1378
1379         if (ssh_msg_recv(from[0], &b) < 0) {
1380                 error("ssh_keysign: no reply");
1381                 buffer_free(&b);
1382                 return -1;
1383         }
1384         close(from[0]);
1385         close(to[1]);
1386
1387         while (waitpid(pid, &status, 0) < 0)
1388                 if (errno != EINTR)
1389                         break;
1390
1391         if (buffer_get_char(&b) != version) {
1392                 error("ssh_keysign: bad version");
1393                 buffer_free(&b);
1394                 return -1;
1395         }
1396         *sigp = buffer_get_string(&b, lenp);
1397         buffer_free(&b);
1398
1399         return 0;
1400 }
1401
1402 int
1403 userauth_hostbased(Authctxt *authctxt)
1404 {
1405         Key *private = NULL;
1406         Sensitive *sensitive = authctxt->sensitive;
1407         Buffer b;
1408         u_char *signature, *blob;
1409         char *chost, *pkalg, *p;
1410         const char *service;
1411         u_int blen, slen;
1412         int ok, i, len, found = 0;
1413
1414         /* check for a useful key */
1415         for (i = 0; i < sensitive->nkeys; i++) {
1416                 private = sensitive->keys[i];
1417                 if (private && private->type != KEY_RSA1) {
1418                         found = 1;
1419                         /* we take and free the key */
1420                         sensitive->keys[i] = NULL;
1421                         break;
1422                 }
1423         }
1424         if (!found) {
1425                 debug("No more client hostkeys for hostbased authentication.");
1426                 return 0;
1427         }
1428         if (key_to_blob(private, &blob, &blen) == 0) {
1429                 key_free(private);
1430                 return 0;
1431         }
1432         /* figure out a name for the client host */
1433         p = get_local_name(packet_get_connection_in());
1434         if (p == NULL) {
1435                 error("userauth_hostbased: cannot get local ipaddr/name");
1436                 key_free(private);
1437                 xfree(blob);
1438                 return 0;
1439         }
1440         len = strlen(p) + 2;
1441         xasprintf(&chost, "%s.", p);
1442         debug2("userauth_hostbased: chost %s", chost);
1443         xfree(p);
1444
1445         service = datafellows & SSH_BUG_HBSERVICE ? "ssh-userauth" :
1446             authctxt->service;
1447         pkalg = xstrdup(key_ssh_name(private));
1448         buffer_init(&b);
1449         /* construct data */
1450         buffer_put_string(&b, session_id2, session_id2_len);
1451         buffer_put_char(&b, SSH2_MSG_USERAUTH_REQUEST);
1452         buffer_put_cstring(&b, authctxt->server_user);
1453         buffer_put_cstring(&b, service);
1454         buffer_put_cstring(&b, authctxt->method->name);
1455         buffer_put_cstring(&b, pkalg);
1456         buffer_put_string(&b, blob, blen);
1457         buffer_put_cstring(&b, chost);
1458         buffer_put_cstring(&b, authctxt->local_user);
1459 #ifdef DEBUG_PK
1460         buffer_dump(&b);
1461 #endif
1462         if (sensitive->external_keysign)
1463                 ok = ssh_keysign(private, &signature, &slen,
1464                     buffer_ptr(&b), buffer_len(&b));
1465         else
1466                 ok = key_sign(private, &signature, &slen,
1467                     buffer_ptr(&b), buffer_len(&b));
1468         key_free(private);
1469         buffer_free(&b);
1470         if (ok != 0) {
1471                 error("key_sign failed");
1472                 xfree(chost);
1473                 xfree(pkalg);
1474                 xfree(blob);
1475                 return 0;
1476         }
1477         packet_start(SSH2_MSG_USERAUTH_REQUEST);
1478         packet_put_cstring(authctxt->server_user);
1479         packet_put_cstring(authctxt->service);
1480         packet_put_cstring(authctxt->method->name);
1481         packet_put_cstring(pkalg);
1482         packet_put_string(blob, blen);
1483         packet_put_cstring(chost);
1484         packet_put_cstring(authctxt->local_user);
1485         packet_put_string(signature, slen);
1486         memset(signature, 's', slen);
1487         xfree(signature);
1488         xfree(chost);
1489         xfree(pkalg);
1490         xfree(blob);
1491
1492         packet_send();
1493         return 1;
1494 }
1495
1496 /* find auth method */
1497
1498 /*
1499  * given auth method name, if configurable options permit this method fill
1500  * in auth_ident field and return true, otherwise return false.
1501  */
1502 static int
1503 authmethod_is_enabled(Authmethod *method)
1504 {
1505         if (method == NULL)
1506                 return 0;
1507         /* return false if options indicate this method is disabled */
1508         if  (method->enabled == NULL || *method->enabled == 0)
1509                 return 0;
1510         /* return false if batch mode is enabled but method needs interactive mode */
1511         if  (method->batch_flag != NULL && *method->batch_flag != 0)
1512                 return 0;
1513         return 1;
1514 }
1515
1516 static Authmethod *
1517 authmethod_lookup(const char *name)
1518 {
1519         Authmethod *method = NULL;
1520         if (name != NULL)
1521                 for (method = authmethods; method->name != NULL; method++)
1522                         if (strcmp(name, method->name) == 0)
1523                                 return method;
1524         debug2("Unrecognized authentication method name: %s", name ? name : "NULL");
1525         return NULL;
1526 }
1527
1528 /* XXX internal state */
1529 static Authmethod *current = NULL;
1530 static char *supported = NULL;
1531 static char *preferred = NULL;
1532
1533 /*
1534  * Given the authentication method list sent by the server, return the
1535  * next method we should try.  If the server initially sends a nil list,
1536  * use a built-in default list.
1537  */
1538 static Authmethod *
1539 authmethod_get(char *authlist)
1540 {
1541         char *name = NULL;
1542         u_int next;
1543
1544         /* Use a suitable default if we're passed a nil list.  */
1545         if (authlist == NULL || strlen(authlist) == 0)
1546                 authlist = options.preferred_authentications;
1547
1548         if (supported == NULL || strcmp(authlist, supported) != 0) {
1549                 debug3("start over, passed a different list %s", authlist);
1550                 if (supported != NULL)
1551                         xfree(supported);
1552                 supported = xstrdup(authlist);
1553                 preferred = options.preferred_authentications;
1554                 debug3("preferred %s", preferred);
1555                 current = NULL;
1556         } else if (current != NULL && authmethod_is_enabled(current))
1557                 return current;
1558
1559         for (;;) {
1560                 if ((name = match_list(preferred, supported, &next)) == NULL) {
1561                         debug("No more authentication methods to try.");
1562                         current = NULL;
1563                         return NULL;
1564                 }
1565                 preferred += next;
1566                 debug3("authmethod_lookup %s", name);
1567                 debug3("remaining preferred: %s", preferred);
1568                 if ((current = authmethod_lookup(name)) != NULL &&
1569                     authmethod_is_enabled(current)) {
1570                         debug3("authmethod_is_enabled %s", name);
1571                         debug("Next authentication method: %s", name);
1572                         return current;
1573                 }
1574         }
1575 }
1576
1577 static char *
1578 authmethods_get(void)
1579 {
1580         Authmethod *method = NULL;
1581         Buffer b;
1582         char *list;
1583
1584         buffer_init(&b);
1585         for (method = authmethods; method->name != NULL; method++) {
1586                 if (authmethod_is_enabled(method)) {
1587                         if (buffer_len(&b) > 0)
1588                                 buffer_append(&b, ",", 1);
1589                         buffer_append(&b, method->name, strlen(method->name));
1590                 }
1591         }
1592         buffer_append(&b, "\0", 1);
1593         list = xstrdup(buffer_ptr(&b));
1594         buffer_free(&b);
1595         return list;
1596 }
This page took 0.241243 seconds and 5 git commands to generate.