Main Page | Namespace List | Class List | Directories | File List | Class Members | File Members

auth2-chall.c File Reference

#include "includes.h"
#include "ssh2.h"
#include "auth.h"
#include "buffer.h"
#include "packet.h"
#include "xmalloc.h"
#include "dispatch.h"
#include "log.h"
#include "servconf.h"

Go to the source code of this file.

Classes

struct  KbdintAuthctxt

Typedefs

typedef KbdintAuthctxt KbdintAuthctxt

Functions

 RCSID ("$OpenBSD: auth2-chall.c,v 1.24 2005/07/17 07:17:54 djm Exp $")
static int auth2_challenge_start (Authctxt *)
static int send_userauth_info_request (Authctxt *)
static void input_userauth_info_response (int, u_int32_t, void *)
static KbdintAuthctxtkbdint_alloc (const char *devs)
static void kbdint_reset_device (KbdintAuthctxt *kbdintctxt)
static void kbdint_free (KbdintAuthctxt *kbdintctxt)
static int kbdint_next_device (KbdintAuthctxt *kbdintctxt)
int auth2_challenge (Authctxt *authctxt, char *devs)
void auth2_challenge_stop (Authctxt *authctxt)
void privsep_challenge_enable (void)

Variables

ServerOptions options
KbdintDevicedevices []


Typedef Documentation

typedef struct KbdintAuthctxt KbdintAuthctxt
 

Definition at line 69 of file auth2-chall.c.


Function Documentation

int auth2_challenge Authctxt authctxt,
char devs
 

Definition at line 181 of file auth2-chall.c.

References auth2_challenge_start(), debug(), kbdint_alloc(), Authctxt::kbdintctxt, and Authctxt::user.

Referenced by userauth_kbdint().

00182 {
00183         debug("auth2_challenge: user=%s devs=%s",
00184             authctxt->user ? authctxt->user : "<nouser>",
00185             devs ? devs : "<no devs>");
00186 
00187         if (authctxt->user == NULL || !devs)
00188                 return 0;
00189         if (authctxt->kbdintctxt == NULL)
00190                 authctxt->kbdintctxt = kbdint_alloc(devs);
00191         return auth2_challenge_start(authctxt);
00192 }

static int auth2_challenge_start Authctxt  )  [static]
 

Definition at line 208 of file auth2-chall.c.

References auth2_challenge_stop(), KbdintAuthctxt::ctxt, debug(), debug2(), KbdintAuthctxt::device, KbdintAuthctxt::devices, dispatch_set(), KbdintDevice::init_ctx, input_userauth_info_response(), kbdint_next_device(), Authctxt::kbdintctxt, KbdintDevice::name, Authctxt::postponed, send_userauth_info_request(), and SSH2_MSG_USERAUTH_INFO_RESPONSE.

Referenced by auth2_challenge(), and input_userauth_info_response().

00209 {
00210         KbdintAuthctxt *kbdintctxt = authctxt->kbdintctxt;
00211 
00212         debug2("auth2_challenge_start: devices %s",
00213             kbdintctxt->devices ?  kbdintctxt->devices : "<empty>");
00214 
00215         if (kbdint_next_device(kbdintctxt) == 0) {
00216                 auth2_challenge_stop(authctxt);
00217                 return 0;
00218         }
00219         debug("auth2_challenge_start: trying authentication method '%s'",
00220             kbdintctxt->device->name);
00221 
00222         if ((kbdintctxt->ctxt = kbdintctxt->device->init_ctx(authctxt)) == NULL) {
00223                 auth2_challenge_stop(authctxt);
00224                 return 0;
00225         }
00226         if (send_userauth_info_request(authctxt) == 0) {
00227                 auth2_challenge_stop(authctxt);
00228                 return 0;
00229         }
00230         dispatch_set(SSH2_MSG_USERAUTH_INFO_RESPONSE,
00231             &input_userauth_info_response);
00232 
00233         authctxt->postponed = 1;
00234         return 0;
00235 }

void auth2_challenge_stop Authctxt authctxt  ) 
 

Definition at line 196 of file auth2-chall.c.

References dispatch_set(), kbdint_free(), Authctxt::kbdintctxt, and SSH2_MSG_USERAUTH_INFO_RESPONSE.

Referenced by auth2_challenge_start(), input_userauth_info_response(), and input_userauth_request().

00197 {
00198         /* unregister callback */
00199         dispatch_set(SSH2_MSG_USERAUTH_INFO_RESPONSE, NULL);
00200         if (authctxt->kbdintctxt != NULL)  {
00201                 kbdint_free(authctxt->kbdintctxt);
00202                 authctxt->kbdintctxt = NULL;
00203         }
00204 }

static void input_userauth_info_response int  ,
u_int32_t  ,
void * 
[static]
 

Definition at line 271 of file auth2-chall.c.

References auth2_challenge_start(), auth2_challenge_stop(), authctxt, KbdintAuthctxt::ctxt, KbdintAuthctxt::device, fatal(), Authctxt::kbdintctxt, KbdintDevice::name, KbdintAuthctxt::nreq, packet_check_eom, packet_get_int(), packet_get_string(), Authctxt::postponed, KbdintDevice::respond, response(), send_userauth_info_request(), snprintf(), userauth_finish(), Authctxt::valid, xfree(), and xmalloc().

Referenced by auth2_challenge_start().

00272 {
00273         Authctxt *authctxt = ctxt;
00274         KbdintAuthctxt *kbdintctxt;
00275         int authenticated = 0, res, len;
00276         u_int i, nresp;
00277         char **response = NULL, *method;
00278 
00279         if (authctxt == NULL)
00280                 fatal("input_userauth_info_response: no authctxt");
00281         kbdintctxt = authctxt->kbdintctxt;
00282         if (kbdintctxt == NULL || kbdintctxt->ctxt == NULL)
00283                 fatal("input_userauth_info_response: no kbdintctxt");
00284         if (kbdintctxt->device == NULL)
00285                 fatal("input_userauth_info_response: no device");
00286 
00287         authctxt->postponed = 0;        /* reset */
00288         nresp = packet_get_int();
00289         if (nresp != kbdintctxt->nreq)
00290                 fatal("input_userauth_info_response: wrong number of replies");
00291         if (nresp > 100)
00292                 fatal("input_userauth_info_response: too many replies");
00293         if (nresp > 0) {
00294                 response = xmalloc(nresp * sizeof(char *));
00295                 for (i = 0; i < nresp; i++)
00296                         response[i] = packet_get_string(NULL);
00297         }
00298         packet_check_eom();
00299 
00300         res = kbdintctxt->device->respond(kbdintctxt->ctxt, nresp, response);
00301 
00302         for (i = 0; i < nresp; i++) {
00303                 memset(response[i], 'r', strlen(response[i]));
00304                 xfree(response[i]);
00305         }
00306         if (response)
00307                 xfree(response);
00308 
00309         switch (res) {
00310         case 0:
00311                 /* Success! */
00312                 authenticated = authctxt->valid ? 1 : 0;
00313                 break;
00314         case 1:
00315                 /* Authentication needs further interaction */
00316                 if (send_userauth_info_request(authctxt) == 1)
00317                         authctxt->postponed = 1;
00318                 break;
00319         default:
00320                 /* Failure! */
00321                 break;
00322         }
00323 
00324         len = strlen("keyboard-interactive") + 2 +
00325                 strlen(kbdintctxt->device->name);
00326         method = xmalloc(len);
00327         snprintf(method, len, "keyboard-interactive/%s",
00328             kbdintctxt->device->name);
00329 
00330         if (!authctxt->postponed) {
00331                 if (authenticated) {
00332                         auth2_challenge_stop(authctxt);
00333                 } else {
00334                         /* start next device */
00335                         /* may set authctxt->postponed */
00336                         auth2_challenge_start(authctxt);
00337                 }
00338         }
00339         userauth_finish(authctxt, authenticated, method);
00340         xfree(method);
00341 }

static KbdintAuthctxt* kbdint_alloc const char devs  )  [static]
 

Definition at line 94 of file auth2-chall.c.

References buffer_append(), buffer_free(), buffer_init(), buffer_len(), buffer_ptr(), KbdintAuthctxt::ctxt, debug(), KbdintAuthctxt::device, KbdintAuthctxt::devices, name, KbdintAuthctxt::nreq, remove_kbdint_device(), ServerOptions::use_pam, xmalloc(), and xstrdup().

Referenced by auth2_challenge().

00095 {
00096         KbdintAuthctxt *kbdintctxt;
00097         Buffer b;
00098         int i;
00099 
00100 #ifdef USE_PAM
00101         if (!options.use_pam)
00102                 remove_kbdint_device("pam");
00103 #endif
00104 
00105         kbdintctxt = xmalloc(sizeof(KbdintAuthctxt));
00106         if (strcmp(devs, "") == 0) {
00107                 buffer_init(&b);
00108                 for (i = 0; devices[i]; i++) {
00109                         if (buffer_len(&b) > 0)
00110                                 buffer_append(&b, ",", 1);
00111                         buffer_append(&b, devices[i]->name,
00112                             strlen(devices[i]->name));
00113                 }
00114                 buffer_append(&b, "\0", 1);
00115                 kbdintctxt->devices = xstrdup(buffer_ptr(&b));
00116                 buffer_free(&b);
00117         } else {
00118                 kbdintctxt->devices = xstrdup(devs);
00119         }
00120         debug("kbdint_alloc: devices '%s'", kbdintctxt->devices);
00121         kbdintctxt->ctxt = NULL;
00122         kbdintctxt->device = NULL;
00123         kbdintctxt->nreq = 0;
00124 
00125         return kbdintctxt;
00126 }

static void kbdint_free KbdintAuthctxt kbdintctxt  )  [static]
 

Definition at line 137 of file auth2-chall.c.

References KbdintAuthctxt::device, KbdintAuthctxt::devices, kbdint_reset_device(), and xfree().

Referenced by auth2_challenge_stop().

00138 {
00139         if (kbdintctxt->device)
00140                 kbdint_reset_device(kbdintctxt);
00141         if (kbdintctxt->devices) {
00142                 xfree(kbdintctxt->devices);
00143                 kbdintctxt->devices = NULL;
00144         }
00145         xfree(kbdintctxt);
00146 }

static int kbdint_next_device KbdintAuthctxt kbdintctxt  )  [static]
 

Definition at line 149 of file auth2-chall.c.

References debug2(), KbdintAuthctxt::device, KbdintAuthctxt::devices, kbdint_reset_device(), KbdintDevice::name, xfree(), and xstrdup().

Referenced by auth2_challenge_start().

00150 {
00151         size_t len;
00152         char *t;
00153         int i;
00154 
00155         if (kbdintctxt->device)
00156                 kbdint_reset_device(kbdintctxt);
00157         do {
00158                 len = kbdintctxt->devices ?
00159                     strcspn(kbdintctxt->devices, ",") : 0;
00160 
00161                 if (len == 0)
00162                         break;
00163                 for (i = 0; devices[i]; i++)
00164                         if (strncmp(kbdintctxt->devices, devices[i]->name, len) == 0)
00165                                 kbdintctxt->device = devices[i];
00166                 t = kbdintctxt->devices;
00167                 kbdintctxt->devices = t[len] ? xstrdup(t+len+1) : NULL;
00168                 xfree(t);
00169                 debug2("kbdint_next_device: devices %s", kbdintctxt->devices ?
00170                     kbdintctxt->devices : "<empty>");
00171         } while (kbdintctxt->devices && !kbdintctxt->device);
00172 
00173         return kbdintctxt->device ? 1 : 0;
00174 }

static void kbdint_reset_device KbdintAuthctxt kbdintctxt  )  [static]
 

Definition at line 128 of file auth2-chall.c.

References KbdintAuthctxt::ctxt, KbdintAuthctxt::device, and KbdintDevice::free_ctx.

Referenced by kbdint_free(), and kbdint_next_device().

00129 {
00130         if (kbdintctxt->ctxt) {
00131                 kbdintctxt->device->free_ctx(kbdintctxt->ctxt);
00132                 kbdintctxt->ctxt = NULL;
00133         }
00134         kbdintctxt->device = NULL;
00135 }

void privsep_challenge_enable void   ) 
 

Definition at line 344 of file auth2-chall.c.

Referenced by privsep_preauth_child().

00345 {
00346 #if defined(BSD_AUTH) || defined(USE_PAM) || defined(SKEY)
00347         int n = 0;
00348 #endif
00349 #ifdef BSD_AUTH
00350         extern KbdintDevice mm_bsdauth_device;
00351 #endif
00352 #ifdef USE_PAM
00353         extern KbdintDevice mm_sshpam_device;
00354 #endif
00355 #ifdef SKEY
00356         extern KbdintDevice mm_skey_device;
00357 #endif
00358 
00359 #ifdef BSD_AUTH
00360         devices[n++] = &mm_bsdauth_device;
00361 #else
00362 #ifdef USE_PAM
00363         devices[n++] = &mm_sshpam_device;
00364 #endif
00365 #ifdef SKEY
00366         devices[n++] = &mm_skey_device;
00367 #endif
00368 #endif
00369 }

RCSID "$OpenBSD: auth2-chall.  c,
v 1.24 2005/07/17 07:17:54 djm Exp $" 
 

static int send_userauth_info_request Authctxt  )  [static]
 

Definition at line 238 of file auth2-chall.c.

References KbdintAuthctxt::ctxt, KbdintAuthctxt::device, Authctxt::kbdintctxt, name, KbdintAuthctxt::nreq, packet_put_char(), packet_put_cstring(), packet_put_int(), packet_send(), packet_start(), packet_write_wait(), KbdintDevice::query, SSH2_MSG_USERAUTH_INFO_REQUEST, and xfree().

Referenced by auth2_challenge_start(), and input_userauth_info_response().

00239 {
00240         KbdintAuthctxt *kbdintctxt;
00241         char *name, *instr, **prompts;
00242         u_int i, *echo_on;
00243 
00244         kbdintctxt = authctxt->kbdintctxt;
00245         if (kbdintctxt->device->query(kbdintctxt->ctxt,
00246             &name, &instr, &kbdintctxt->nreq, &prompts, &echo_on))
00247                 return 0;
00248 
00249         packet_start(SSH2_MSG_USERAUTH_INFO_REQUEST);
00250         packet_put_cstring(name);
00251         packet_put_cstring(instr);
00252         packet_put_cstring("");         /* language not used */
00253         packet_put_int(kbdintctxt->nreq);
00254         for (i = 0; i < kbdintctxt->nreq; i++) {
00255                 packet_put_cstring(prompts[i]);
00256                 packet_put_char(echo_on[i]);
00257         }
00258         packet_send();
00259         packet_write_wait();
00260 
00261         for (i = 0; i < kbdintctxt->nreq; i++)
00262                 xfree(prompts[i]);
00263         xfree(prompts);
00264         xfree(echo_on);
00265         xfree(name);
00266         xfree(instr);
00267         return 1;
00268 }


Variable Documentation

KbdintDevice* devices[]
 

Initial value:

 {










        NULL
}

Definition at line 55 of file auth2-chall.c.

ServerOptions options
 

Definition at line 110 of file ssh.c.


© sourcejam.com 2005-2008