prepare for multiple names for authmethods
authordjm <djm@openbsd.org>
Sun, 19 Dec 2021 22:12:07 +0000 (22:12 +0000)
committerdjm <djm@openbsd.org>
Sun, 19 Dec 2021 22:12:07 +0000 (22:12 +0000)
allow authentication methods to have one additional name beyond their
primary name.

allow lookup by this synonym

Use primary name for authentication decisions, e.g. for
PermitRootLogin=publickey

Pass actual invoked name to the authmethods, so they can tell whether they
were requested via the their primary name or synonym.

ok markus@

usr.bin/ssh/auth.h
usr.bin/ssh/auth2-gss.c
usr.bin/ssh/auth2-hostbased.c
usr.bin/ssh/auth2-kbdint.c
usr.bin/ssh/auth2-none.c
usr.bin/ssh/auth2-passwd.c
usr.bin/ssh/auth2-pubkey.c
usr.bin/ssh/auth2.c

index d1d9c8f..d9f1295 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: auth.h,v 1.101 2020/12/22 00:12:22 djm Exp $ */
+/* $OpenBSD: auth.h,v 1.102 2021/12/19 22:12:07 djm Exp $ */
 
 /*
  * Copyright (c) 2000 Markus Friedl.  All rights reserved.
@@ -95,7 +95,8 @@ struct Authctxt {
 
 struct Authmethod {
        char    *name;
-       int     (*userauth)(struct ssh *);
+       char    *synonym;
+       int     (*userauth)(struct ssh *, const char *);
        int     *enabled;
 };
 
index 245c5d9..6501a26 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: auth2-gss.c,v 1.32 2021/01/27 10:15:08 djm Exp $ */
+/* $OpenBSD: auth2-gss.c,v 1.33 2021/12/19 22:12:07 djm Exp $ */
 
 /*
  * Copyright (c) 2001-2003 Simon Wilkinson. All rights reserved.
@@ -55,7 +55,7 @@ static int input_gssapi_errtok(int, u_int32_t, struct ssh *);
  * how to check local user kuserok and the like)
  */
 static int
-userauth_gssapi(struct ssh *ssh)
+userauth_gssapi(struct ssh *ssh, const char *method)
 {
        Authctxt *authctxt = ssh->authctxt;
        gss_OID_desc goid = {0, NULL};
@@ -324,6 +324,7 @@ input_gssapi_mic(int type, u_int32_t plen, struct ssh *ssh)
 
 Authmethod method_gssapi = {
        "gssapi-with-mic",
+       NULL,
        userauth_gssapi,
        &options.gss_authentication
 };
index cd95239..f99f93e 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: auth2-hostbased.c,v 1.47 2021/07/23 03:37:52 djm Exp $ */
+/* $OpenBSD: auth2-hostbased.c,v 1.48 2021/12/19 22:12:07 djm Exp $ */
 /*
  * Copyright (c) 2000 Markus Friedl.  All rights reserved.
  *
@@ -56,7 +56,7 @@
 extern ServerOptions options;
 
 static int
-userauth_hostbased(struct ssh *ssh)
+userauth_hostbased(struct ssh *ssh, const char *method)
 {
        Authctxt *authctxt = ssh->authctxt;
        struct sshbuf *b;
@@ -131,7 +131,7 @@ userauth_hostbased(struct ssh *ssh)
            (r = sshbuf_put_u8(b, SSH2_MSG_USERAUTH_REQUEST)) != 0 ||
            (r = sshbuf_put_cstring(b, authctxt->user)) != 0 ||
            (r = sshbuf_put_cstring(b, authctxt->service)) != 0 ||
-           (r = sshbuf_put_cstring(b, "hostbased")) != 0 ||
+           (r = sshbuf_put_cstring(b, method)) != 0 ||
            (r = sshbuf_put_string(b, pkalg, alen)) != 0 ||
            (r = sshbuf_put_string(b, pkblob, blen)) != 0 ||
            (r = sshbuf_put_cstring(b, chost)) != 0 ||
@@ -254,6 +254,7 @@ hostbased_key_allowed(struct ssh *ssh, struct passwd *pw,
 
 Authmethod method_hostbased = {
        "hostbased",
+       NULL,
        userauth_hostbased,
        &options.hostbased_authentication
 };
index 1bd12cd..034b6ea 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: auth2-kbdint.c,v 1.13 2021/07/02 05:11:20 dtucker Exp $ */
+/* $OpenBSD: auth2-kbdint.c,v 1.14 2021/12/19 22:12:07 djm Exp $ */
 /*
  * Copyright (c) 2000 Markus Friedl.  All rights reserved.
  *
@@ -42,7 +42,7 @@
 extern ServerOptions options;
 
 static int
-userauth_kbdint(struct ssh *ssh)
+userauth_kbdint(struct ssh *ssh, const char *method)
 {
        int r, authenticated = 0;
        char *lang, *devs;
@@ -64,6 +64,7 @@ userauth_kbdint(struct ssh *ssh)
 
 Authmethod method_kbdint = {
        "keyboard-interactive",
+       NULL,
        userauth_kbdint,
        &options.kbd_interactive_authentication
 };
index 6e00b11..7763203 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: auth2-none.c,v 1.23 2020/10/18 11:32:01 djm Exp $ */
+/* $OpenBSD: auth2-none.c,v 1.24 2021/12/19 22:12:07 djm Exp $ */
 /*
  * Copyright (c) 2000 Markus Friedl.  All rights reserved.
  *
@@ -50,7 +50,7 @@ extern ServerOptions options;
 static int none_enabled = 1;
 
 static int
-userauth_none(struct ssh *ssh)
+userauth_none(struct ssh *ssh, const char *method)
 {
        int r;
 
@@ -64,6 +64,7 @@ userauth_none(struct ssh *ssh)
 
 Authmethod method_none = {
        "none",
+       NULL,
        userauth_none,
        &none_enabled
 };
index 9ff2b20..9c62de1 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: auth2-passwd.c,v 1.19 2020/10/18 11:32:01 djm Exp $ */
+/* $OpenBSD: auth2-passwd.c,v 1.20 2021/12/19 22:12:07 djm Exp $ */
 /*
  * Copyright (c) 2000 Markus Friedl.  All rights reserved.
  *
@@ -47,7 +47,7 @@
 extern ServerOptions options;
 
 static int
-userauth_passwd(struct ssh *ssh)
+userauth_passwd(struct ssh *ssh, const char *method)
 {
        char *password;
        int authenticated = 0, r;
@@ -70,6 +70,7 @@ userauth_passwd(struct ssh *ssh)
 
 Authmethod method_passwd = {
        "password",
+       NULL,
        userauth_passwd,
        &options.password_authentication
 };
index 0575ae6..54f6f04 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: auth2-pubkey.c,v 1.110 2021/09/29 01:33:32 djm Exp $ */
+/* $OpenBSD: auth2-pubkey.c,v 1.111 2021/12/19 22:12:07 djm Exp $ */
 /*
  * Copyright (c) 2000 Markus Friedl.  All rights reserved.
  *
@@ -83,7 +83,7 @@ format_key(const struct sshkey *key)
 }
 
 static int
-userauth_pubkey(struct ssh *ssh)
+userauth_pubkey(struct ssh *ssh, const char *method)
 {
        Authctxt *authctxt = ssh->authctxt;
        struct passwd *pw = authctxt->pw;
@@ -189,7 +189,7 @@ userauth_pubkey(struct ssh *ssh)
                if ((r = sshbuf_put_u8(b, SSH2_MSG_USERAUTH_REQUEST)) != 0 ||
                    (r = sshbuf_put_cstring(b, userstyle)) != 0 ||
                    (r = sshbuf_put_cstring(b, authctxt->service)) != 0 ||
-                   (r = sshbuf_put_cstring(b, "publickey")) != 0 ||
+                   (r = sshbuf_put_cstring(b, method)) != 0 ||
                    (r = sshbuf_put_u8(b, have_sig)) != 0 ||
                    (r = sshbuf_put_cstring(b, pkalg)) != 0 ||
                    (r = sshbuf_put_string(b, pkblob, blen)) != 0)
@@ -1064,6 +1064,7 @@ user_key_allowed(struct ssh *ssh, struct passwd *pw, struct sshkey *key,
 
 Authmethod method_pubkey = {
        "publickey",
+       NULL,
        userauth_pubkey,
        &options.pubkey_authentication
 };
index c21c2e1..d6cc3d7 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: auth2.c,v 1.161 2021/04/03 06:18:40 djm Exp $ */
+/* $OpenBSD: auth2.c,v 1.162 2021/12/19 22:12:07 djm Exp $ */
 /*
  * Copyright (c) 2000 Markus Friedl.  All rights reserved.
  *
@@ -314,7 +314,7 @@ input_userauth_request(int type, u_int32_t seq, struct ssh *ssh)
        m = authmethod_lookup(authctxt, method);
        if (m != NULL && authctxt->failures < options.max_authtries) {
                debug2("input_userauth_request: try method %s", method);
-               authenticated = m->userauth(ssh);
+               authenticated = m->userauth(ssh, method);
        }
        if (!authctxt->authenticated)
                ensure_minimum_time_since(tstart,
@@ -329,18 +329,26 @@ input_userauth_request(int type, u_int32_t seq, struct ssh *ssh)
 }
 
 void
-userauth_finish(struct ssh *ssh, int authenticated, const char *method,
+userauth_finish(struct ssh *ssh, int authenticated, const char *packet_method,
     const char *submethod)
 {
        Authctxt *authctxt = ssh->authctxt;
+       Authmethod *m = NULL;
+       const char *method = packet_method;
        char *methods;
        int r, partial = 0;
 
-       if (!authctxt->valid && authenticated)
-               fatal("INTERNAL ERROR: authenticated invalid user %s",
-                   authctxt->user);
-       if (authenticated && authctxt->postponed)
-               fatal("INTERNAL ERROR: authenticated and postponed");
+       if (authenticated) {
+               if (!authctxt->valid) {
+                       fatal("INTERNAL ERROR: authenticated invalid user %s",
+                           authctxt->user);
+               }
+               if (authctxt->postponed)
+                       fatal("INTERNAL ERROR: authenticated and postponed");
+               if ((m = authmethod_lookup(authctxt, method)) == NULL)
+                       fatal("INTERNAL ERROR: bad method %s", method);
+               method = m->name; /* prefer primary name to possible synonym */
+       }
 
        /* Special handling for root */
        if (authenticated && authctxt->pw->pw_uid == 0 &&
@@ -457,7 +465,9 @@ authmethod_lookup(Authctxt *authctxt, const char *name)
                for (i = 0; authmethods[i] != NULL; i++)
                        if (authmethods[i]->enabled != NULL &&
                            *(authmethods[i]->enabled) != 0 &&
-                           strcmp(name, authmethods[i]->name) == 0 &&
+                           (strcmp(name, authmethods[i]->name) == 0 ||
+                           (authmethods[i]->synonym != NULL &&
+                           strcmp(name, authmethods[i]->synonym) == 0)) &&
                            auth2_method_allowed(authctxt,
                            authmethods[i]->name, NULL))
                                return authmethods[i];