aboutsummaryrefslogtreecommitdiff
path: root/contrib/opie/libopie/verify.c
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/opie/libopie/verify.c')
-rw-r--r--contrib/opie/libopie/verify.c255
1 files changed, 255 insertions, 0 deletions
diff --git a/contrib/opie/libopie/verify.c b/contrib/opie/libopie/verify.c
new file mode 100644
index 000000000000..7388a8ab6fc5
--- /dev/null
+++ b/contrib/opie/libopie/verify.c
@@ -0,0 +1,255 @@
+/* verify.c: The opieverify() library function.
+
+%%% copyright-cmetz
+This software is Copyright 1996 by Craig Metz, All Rights Reserved.
+The Inner Net License Version 2 applies to this software.
+You should have received a copy of the license with this software. If
+you didn't get a copy, you may request one from <license@inner.net>.
+
+ History:
+
+ Created by cmetz for OPIE 2.3 using the old verify.c as a guide.
+*/
+
+#include "opie_cfg.h"
+#ifdef HAVE_STRING_H
+#include <string.h>
+#endif /* HAVE_STRING_H */
+#include "opie.h"
+
+#define RESPONSE_STANDARD 0
+#define RESPONSE_WORD 1
+#define RESPONSE_HEX 2
+#define RESPONSE_INIT 3
+#define RESPONSE_INIT_WORD 4
+#define RESPONSE_UNKNOWN 5
+
+struct _rtrans {
+ int type;
+ char *name;
+};
+
+static struct _rtrans rtrans[] = {
+ { RESPONSE_WORD, "word" },
+ { RESPONSE_HEX, "hex" },
+ { RESPONSE_INIT, "init" },
+ { RESPONSE_INIT_WORD, "init-word" },
+ { RESPONSE_STANDARD, "" },
+ { RESPONSE_UNKNOWN, NULL }
+};
+
+static char *algids[] = { NULL, NULL, NULL, "sha1", "md4", "md5" };
+
+static int changed FUNCTION((opie), struct opie *opie)
+{
+ struct opie opie2;
+
+ memset(&opie2, 0, sizeof(struct opie));
+ opie2.opie_principal = opie->opie_principal;
+ if (__opiereadrec(&opie2))
+ return 1;
+
+ if ((opie2.opie_n != opie->opie_n) || strcmp(opie2.opie_val, opie->opie_val) || strcmp(opie2.opie_seed, opie->opie_seed))
+ return 1;
+
+ memset(&opie2, 0, sizeof(struct opie));
+ return 0;
+}
+
+int opieverify FUNCTION((opie, response), struct opie *opie AND char *response)
+{
+ int i, rval = -1;
+ char *c;
+ char key[8], fkey[8], lastkey[8];
+ struct opie nopie;
+
+ if (!opie || !response)
+ goto verret;
+
+ if (!opie->opie_principal)
+#if DEBUG
+ abort();
+#else /* DEBUG */
+ goto verret;
+#endif /* DEBUG */
+
+ if (!opieatob8(lastkey, opie->opie_val))
+ goto verret;
+
+ if (c = strchr(response, ':')) {
+ *(c++) = 0;
+ {
+ struct _rtrans *r;
+ for (r = rtrans; r->name && strcmp(r->name, response); r++);
+ i = r->type;
+ }
+ } else
+ i = RESPONSE_STANDARD;
+
+ switch(i) {
+ case RESPONSE_STANDARD:
+ i = 1;
+
+ if (opieetob(key, response) == 1) {
+ memcpy(fkey, key, sizeof(key));
+ opiehash(fkey, MDX);
+ i = memcmp(fkey, lastkey, sizeof(key));
+ }
+ if (i && opieatob8(key, response)) {
+ memcpy(fkey, key, sizeof(key));
+ opiehash(fkey, MDX);
+ i = memcmp(fkey, lastkey, sizeof(key));
+ }
+ break;
+ case RESPONSE_WORD:
+ i = 1;
+
+ if (opieetob(key, c) == 1) {
+ memcpy(fkey, key, sizeof(key));
+ opiehash(fkey, MDX);
+ i = memcmp(fkey, lastkey, sizeof(key));
+ }
+ break;
+ case RESPONSE_HEX:
+ i = 1;
+
+ if (opieatob8(key, c)) {
+ memcpy(fkey, key, sizeof(key));
+ opiehash(fkey, MDX);
+ i = memcmp(fkey, lastkey, sizeof(key));
+ }
+ break;
+ case RESPONSE_INIT:
+ case RESPONSE_INIT_WORD:
+ {
+ char *c2;
+ char newkey[8], ckxor[8], ck[8], cv[8], cvc[8];
+ char buf[OPIE_SEED_MAX + 48 + 1];
+
+ if (!(c2 = strchr(c, ':')))
+ goto verret;
+
+ *(c2++) = 0;
+
+ if (i == RESPONSE_INIT) {
+ if (!opieatob8(key, c))
+ goto verret;
+ } else {
+ if (opieetob(key, c) != 1)
+ goto verret;
+ }
+
+ memcpy(fkey, key, sizeof(key));
+ opiehash(fkey, MDX);
+
+ if (memcmp(fkey, lastkey, sizeof(key)))
+ goto verret;
+
+ if (changed(opie))
+ goto verret;
+
+ opie->opie_n--;
+
+ if (!opiebtoa8(opie->opie_val, key))
+ goto verret;
+
+ if (__opiewriterec(opie))
+ goto verret;
+
+ if (!(c2 = strchr(c = c2, ':')))
+ goto verret;
+
+ *(c2++) = 0;
+
+ {
+ int j;
+
+ if (_opieparsechallenge(c, &j, &(opie->opie_n), &(opie->opie_seed)) || (j != MDX))
+ goto verret;
+ }
+
+ if (!(c2 = strchr(c = c2, ':')))
+ goto verret;
+
+ *(c2++) = 0;
+
+ if (i == RESPONSE_INIT) {
+ if (!opieatob8(newkey, c))
+ goto verret;
+ } else {
+ if (opieetob(newkey, c) != 1)
+ goto verret;
+ }
+
+ if (!opie->opie_reinitkey || (opie->opie_reinitkey[0] == '*'))
+ goto verwrt;
+
+ if (!(c2 = strchr(c = c2, ':')))
+ goto verret;
+
+ *(c2++) = 0;
+
+ if (i == RESPONSE_INIT) {
+ if (!opieatob8(ckxor, c))
+ goto verret;
+ if (!opieatob8(cv, c2))
+ goto verret;
+ } else {
+ if (opieetob(ckxor, c) != 1)
+ goto verret;
+ if (opieetob(cv, c2) != 1)
+ goto verret;
+ }
+
+ if (!opieatob8(ck, opie->opie_reinitkey))
+ goto verret;
+
+ c = buf;
+ memcpy(c, ck, sizeof(ck)); c += sizeof(ck);
+ memcpy(c, key, sizeof(key)); c += sizeof(key);
+ c += sprintf(c, "%s 499 %s", algids[MDX], opie->opie_seed);
+ memcpy(c, newkey, sizeof(newkey)); c += sizeof(newkey);
+ memcpy(c, ckxor, sizeof(ckxor)); c += sizeof(ckxor);
+ memcpy(c, ck, sizeof(ck)); c += sizeof(ck);
+ opiehashlen(MDX, buf, cvc, (unsigned int)c - (unsigned int)buf);
+
+ if (memcmp(cv, cvc, sizeof(cv)))
+ goto verret;
+
+ for (i = 0; i < 8; i++)
+ ck[i] ^= ckxor[i];
+
+ if (!opiebtoa8(opie->opie_reinitkey, ck))
+ goto verret;
+
+ memcpy(key, newkey, sizeof(key));
+ }
+ goto verwrt;
+ case RESPONSE_UNKNOWN:
+ rval = 1;
+ goto verret;
+ default:
+ rval = -1;
+ goto verret;
+ }
+
+ if (i) {
+ rval = 1;
+ goto verret;
+ }
+
+ if (changed(opie))
+ goto verret;
+
+ opie->opie_n--;
+
+verwrt:
+ if (!opiebtoa8(opie->opie_val, key))
+ goto verret;
+ rval = __opiewriterec(opie);
+
+verret:
+ opieunlock();
+ memset(opie, 0, sizeof(struct opie));
+ return rval;
+}