/***************************************************************************/ /* Module: $Id: authenticate.c,v 1.5 1999/05/09 02:30:27 maf Exp $ /* Description: KarlBridge authentication system, user authorization /* Author: maf /* Notes: /***************************************************************************/ /* $Log: */ #include #include #include #include #include #include #include #include "kbauth.h" #define AUTH 0 /* user passed authentication check */ #define NOAUTH 1 /* user did Not pass authentication check */ #ifdef SIMP_AUTH2 #include "../simpauth2/s2.h" #include "../simpauth2/report.h" char *progname = "kbauth"; int detach; #endif /* SIMP_AUTH2 */ int AuthenticateUser(userName, maxLen) char *userName; int maxLen; { int c; char *p; char pass[17]; struct passwd *pwd; char *salt; int isNotOk; int loginFailures; #ifdef SIMP_AUTH2 struct s2_client s2_client; int i, ok, index; u_char id[16], rcode; #endif /* SIMP_AUTH2 */ loginFailures = 0; for (;;) { /* Get Username */ for (;;) { printf("Username: "); for (p = userName; (c = getchar()) != '\n';) { /* ^d exits */ if (c == EOF) return NOAUTH; /* copy without overflowing */ if (p < userName + (maxLen - 1)) *p++ = c; } /* don't allow blank input, else exit loop */ if (p > userName) { *p = 0; break; } } /* for ;; */ /* Get Password */ if (MyGetPass("Password: ", pass, sizeof(pass))) return NOAUTH; #ifdef SIMP_AUTH /* /* This block will either return NOAUTH, AUTH, or fall through which /* is NOAUTH /**/ if (!simpauthcheck(userName, pass)) return AUTH; #endif /* SIMP_AUTH */ #ifdef SIMP_AUTH2 if (s2_client_init(&s2_client, S2_CLIENT_SERVERLIST)) { fprintf(stderr, "s2_client_init(): failed"); return NOAUTH; } if (s2_client_load_config(&s2_client)) { fprintf(stderr, "s2_load_client_config(): failed"); return NOAUTH; } s2_pick_server(&s2_client, 0); for (i = 0,ok = 0; i < s2_client.servers; ++i) { index = s2_client.pick[i]; if (s2_client_connect(&s2_client, index, 10)) { fprintf(stderr, "s2_connect(): failed\n"); continue; } /* generate random ID */ s2_generate_id(&id); /* send the request */ if (s2_client_request(&s2_client, userName, pass, "kbauth", index, id)) { fprintf(stderr, "s2_client_request(): failed\n"); continue; } /* read reply header */ if (s2_client_decode_reply(&s2_client, index, id, &rcode)) { fprintf(stderr, "s2_client_decode_reply(): failed\n"); continue; } s2_client_cleanup(&s2_client); ok = 1; break; } if (!ok) { fprintf(stderr, "No working s2 servers\n"); return NOAUTH; } if (rcode == S2_AUTH_GOOD) return AUTH; #endif /* SIMP_AUTH2 */ #ifdef UNIX_PASSWD /* /* This block will either return NOAUTH, AUTH, or fall through which /* is NOAUTH /**/ /* setup getpw* library routines */ setpwent(); /* if userName exists, get their encrypted password, else use xx which could never be a valid hash */ if (pwd = getpwnam(userName)) salt = pwd->pw_passwd; else salt = "xx"; /* Test Password */ if (pwd) { isNotOk = strcmp(crypt(pass, salt), pwd->pw_passwd); } /* 0 out the unencrypted passwd */ /* which, ofcourse doesn't mean it's not in a swapfile, a tty buffer, etc */ bzero(pass, sizeof(pass)); /* was this a valid login? */ if (pwd && !isNotOk) return AUTH; /* yes */ #endif /* UNIX_PASSWD */ #ifdef MANSON_AUTH /* /* This block will either return NOAUTH, AUTH, or fall through which /* is NOAUTH /**/ if (!authenticate_user(userName, pass, "SLIP", "truth.magnus.acs.ohio-state.edu")) return AUTH; /* yes */ #endif /* MANSON_AUTH */ /* no */ loginFailures ++; printf("Login incorrect\n"); if (loginFailures > 3) sleep(1); if (loginFailures > 5) sleep(3); if (loginFailures > 6) return NOAUTH; /* they lose */ } /* for ;; */ } /* AuthenticateUser */ /*********************************************************************/ /* Function: MyGetPass /* /* Description: /* /* Get a password without echoing to the screen /* /* Returns: 0 for good /* !0 for error. /* /*********************************************************************/ MyGetPass(message, pass, mlen) char *pass, *message; int mlen; { int x, len; char *c; struct termios newmode, oldmode; printf("%s", message); fflush(stdout); /* get old mode */ if (tcgetattr(STDIN_FILENO, &oldmode) < 0) return 1; /* new mode = old mode without ECHO */ newmode = oldmode; newmode.c_lflag &= ~ECHO; /* set new mode */ if (tcsetattr(STDIN_FILENO, TCSANOW, &newmode) < 0) return 1; /* get the password */ len = 0; x = 0; while (x != 10) { x = getc(stdin); if ((len+1) < mlen) pass[len++] = x; } if (!len) len = 1; pass[len - 1] = 0; printf("\n"); /* reset to old mode */ if (tcsetattr(STDIN_FILENO, TCSANOW, &oldmode) < 0) return 1; } /* MyGetPass */