summaryrefslogtreecommitdiffstats
path: root/crypto/openssh/auth-skey.c
diff options
context:
space:
mode:
authordes <des@FreeBSD.org>2002-03-18 09:55:03 +0000
committerdes <des@FreeBSD.org>2002-03-18 09:55:03 +0000
commit2fc4a488978a03338ecc65403597582c77dabeea (patch)
tree068818e7abaca45008ac24af9fb4de22815cc0eb /crypto/openssh/auth-skey.c
parent8acd87ac472a182ef2d717212f2c0faba81143a5 (diff)
downloadFreeBSD-src-2fc4a488978a03338ecc65403597582c77dabeea.zip
FreeBSD-src-2fc4a488978a03338ecc65403597582c77dabeea.tar.gz
Vendor import of OpenSSH 3.1
Diffstat (limited to 'crypto/openssh/auth-skey.c')
-rw-r--r--crypto/openssh/auth-skey.c227
1 files changed, 59 insertions, 168 deletions
diff --git a/crypto/openssh/auth-skey.c b/crypto/openssh/auth-skey.c
index 95ff6e4..df19f75 100644
--- a/crypto/openssh/auth-skey.c
+++ b/crypto/openssh/auth-skey.c
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 1999,2000 Markus Friedl. All rights reserved.
+ * Copyright (c) 2001 Markus Friedl. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
@@ -21,185 +21,76 @@
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-
#include "includes.h"
-RCSID("$OpenBSD: auth-skey.c,v 1.9 2000/10/19 16:41:13 deraadt Exp $");
+RCSID("$OpenBSD: auth-skey.c,v 1.16 2002/01/12 13:10:29 markus Exp $");
-#include "ssh.h"
-#include "packet.h"
-#include <sha1.h>
+#ifdef SKEY
-/*
- * try skey authentication,
- * return 1 on success, 0 on failure, -1 if skey is not available
- */
+#include <skey.h>
-int
-auth_skey_password(struct passwd * pw, const char *password)
+#include "xmalloc.h"
+#include "auth.h"
+
+static void *
+skey_init_ctx(Authctxt *authctxt)
{
- if (strncasecmp(password, "s/key", 5) == 0) {
- char *skeyinfo = skey_keyinfo(pw->pw_name);
- if (skeyinfo == NULL) {
- debug("generating fake skeyinfo for %.100s.",
- pw->pw_name);
- skeyinfo = skey_fake_keyinfo(pw->pw_name);
- }
- if (skeyinfo != NULL)
- packet_send_debug("%s", skeyinfo);
- /* Try again. */
- return 0;
- } else if (skey_haskey(pw->pw_name) == 0 &&
- skey_passcheck(pw->pw_name, (char *) password) != -1) {
- /* Authentication succeeded. */
- return 1;
- }
- /* Fall back to ordinary passwd authentication. */
- return -1;
+ return authctxt;
}
-/* from %OpenBSD: skeylogin.c,v 1.32 1999/08/16 14:46:56 millert Exp % */
-
-#define ROUND(x) (((x)[0] << 24) + (((x)[1]) << 16) + (((x)[2]) << 8) + \
- ((x)[3]))
+#define PROMPT "\nS/Key Password: "
-/*
- * hash_collapse()
- */
-static u_int32_t
-hash_collapse(s)
- u_char *s;
+static int
+skey_query(void *ctx, char **name, char **infotxt,
+ u_int* numprompts, char ***prompts, u_int **echo_on)
{
- int len, target;
- u_int32_t i;
-
- if ((strlen(s) % sizeof(u_int32_t)) == 0)
- target = strlen(s); /* Multiple of 4 */
- else
- target = strlen(s) - (strlen(s) % sizeof(u_int32_t));
-
- for (i = 0, len = 0; len < target; len += 4)
- i ^= ROUND(s + len);
-
- return i;
+ Authctxt *authctxt = ctx;
+ char challenge[1024], *p;
+ int len;
+ struct skey skey;
+
+ if (skeychallenge(&skey, authctxt->user, challenge) == -1)
+ return -1;
+
+ *name = xstrdup("");
+ *infotxt = xstrdup("");
+ *numprompts = 1;
+ *prompts = xmalloc(*numprompts * sizeof(char*));
+ *echo_on = xmalloc(*numprompts * sizeof(u_int));
+ (*echo_on)[0] = 0;
+
+ len = strlen(challenge) + strlen(PROMPT) + 1;
+ p = xmalloc(len);
+ strlcpy(p, challenge, len);
+ strlcat(p, PROMPT, len);
+ (*prompts)[0] = p;
+
+ return 0;
}
-char *
-skey_fake_keyinfo(char *username)
+static int
+skey_respond(void *ctx, u_int numresponses, char **responses)
{
- int i;
- u_int ptr;
- u_char hseed[SKEY_MAX_SEED_LEN], flg = 1, *up;
- char pbuf[SKEY_MAX_PW_LEN+1];
- static char skeyprompt[SKEY_MAX_CHALLENGE+1];
- char *secret = NULL;
- size_t secretlen = 0;
- SHA1_CTX ctx;
- char *p, *u;
-
- /*
- * Base first 4 chars of seed on hostname.
- * Add some filler for short hostnames if necessary.
- */
- if (gethostname(pbuf, sizeof(pbuf)) == -1)
- *(p = pbuf) = '.';
- else
- for (p = pbuf; *p && isalnum(*p); p++)
- if (isalpha(*p) && isupper(*p))
- *p = tolower(*p);
- if (*p && pbuf - p < 4)
- (void)strncpy(p, "asjd", 4 - (pbuf - p));
- pbuf[4] = '\0';
-
- /* Hash the username if possible */
- if ((up = SHA1Data(username, strlen(username), NULL)) != NULL) {
- struct stat sb;
- time_t t;
- int fd;
+ Authctxt *authctxt = ctx;
- /* Collapse the hash */
- ptr = hash_collapse(up);
- memset(up, 0, strlen(up));
-
- /* See if the random file's there, else use ctime */
- if ((fd = open(_SKEY_RAND_FILE_PATH_, O_RDONLY)) != -1
- && fstat(fd, &sb) == 0 &&
- sb.st_size > (off_t)SKEY_MAX_SEED_LEN &&
- lseek(fd, ptr % (sb.st_size - SKEY_MAX_SEED_LEN),
- SEEK_SET) != -1 && read(fd, hseed,
- SKEY_MAX_SEED_LEN) == SKEY_MAX_SEED_LEN) {
- close(fd);
- fd = -1;
- secret = hseed;
- secretlen = SKEY_MAX_SEED_LEN;
- flg = 0;
- } else if (!stat(_PATH_MEM, &sb) || !stat("/", &sb)) {
- t = sb.st_ctime;
- secret = ctime(&t);
- secretlen = strlen(secret);
- flg = 0;
- }
- if (fd != -1)
- close(fd);
- }
-
- /* Put that in your pipe and smoke it */
- if (flg == 0) {
- /* Hash secret value with username */
- SHA1Init(&ctx);
- SHA1Update(&ctx, secret, secretlen);
- SHA1Update(&ctx, username, strlen(username));
- SHA1End(&ctx, up);
-
- /* Zero out */
- memset(secret, 0, secretlen);
-
- /* Now hash the hash */
- SHA1Init(&ctx);
- SHA1Update(&ctx, up, strlen(up));
- SHA1End(&ctx, up);
-
- ptr = hash_collapse(up + 4);
-
- for (i = 4; i < 9; i++) {
- pbuf[i] = (ptr % 10) + '0';
- ptr /= 10;
- }
- pbuf[i] = '\0';
-
- /* Sequence number */
- ptr = ((up[2] + up[3]) % 99) + 1;
-
- memset(up, 0, 20); /* SHA1 specific */
- free(up);
-
- (void)snprintf(skeyprompt, sizeof skeyprompt,
- "otp-%.*s %d %.*s",
- SKEY_MAX_HASHNAME_LEN,
- skey_get_algorithm(),
- ptr, SKEY_MAX_SEED_LEN,
- pbuf);
- } else {
- /* Base last 8 chars of seed on username */
- u = username;
- i = 8;
- p = &pbuf[4];
- do {
- if (*u == 0) {
- /* Pad remainder with zeros */
- while (--i >= 0)
- *p++ = '0';
- break;
- }
-
- *p++ = (*u++ % 10) + '0';
- } while (--i != 0);
- pbuf[12] = '\0';
+ if (authctxt->valid &&
+ numresponses == 1 &&
+ skey_haskey(authctxt->pw->pw_name) == 0 &&
+ skey_passcheck(authctxt->pw->pw_name, responses[0]) != -1)
+ return 0;
+ return -1;
+}
- (void)snprintf(skeyprompt, sizeof skeyprompt,
- "otp-%.*s %d %.*s",
- SKEY_MAX_HASHNAME_LEN,
- skey_get_algorithm(),
- 99, SKEY_MAX_SEED_LEN, pbuf);
- }
- return skeyprompt;
+static void
+skey_free_ctx(void *ctx)
+{
+ /* we don't have a special context */
}
+
+KbdintDevice skey_device = {
+ "skey",
+ skey_init_ctx,
+ skey_query,
+ skey_respond,
+ skey_free_ctx
+};
+#endif /* SKEY */
OpenPOWER on IntegriCloud