/*
- * $Id: uams_randnum.c,v 1.8 2001-10-25 20:52:55 srittau Exp $
*
* Copyright (c) 1990,1993 Regents of The University of Michigan.
* Copyright (c) 1999 Adrian Sun (asun@u.washington.edu)
#include <stdio.h>
#include <stdlib.h>
-
-/* STDC check */
-#if STDC_HEADERS
#include <string.h>
-#else /* STDC_HEADERS */
-#ifndef HAVE_STRCHR
-#define strchr index
-#define strrchr index
-#endif /* HAVE_STRCHR */
-char *strchr (), *strrchr ();
-#ifndef HAVE_MEMCPY
-#define memcpy(d,s,n) bcopy ((s), (d), (n))
-#define memmove(d,s,n) bcopy ((s), (d), (n))
-#endif /* ! HAVE_MEMCPY */
-#endif /* STDC_HEADERS */
-
-#ifdef HAVE_UNISTD_H
#include <unistd.h>
-#endif /* HAVE_UNISTD_H */
-#ifdef HAVE_FCNTL_H
#include <fcntl.h>
-#endif /* HAVE_FCNTL_H */
#include <ctype.h>
#include <pwd.h>
#include <sys/stat.h>
#include <sys/param.h>
+#include <arpa/inet.h>
-#include <syslog.h>
-
-#include <netatalk/endian.h>
-
+#include <atalk/logger.h>
#include <atalk/afp.h>
#include <atalk/uam.h>
#include <crack.h>
#endif /* USE_CRACKLIB */
-#ifndef __inline__
-#define __inline__
-#endif /* __inline__ */
-
#define PASSWDLEN 8
static C_Block seskey;
static Key_schedule seskeysched;
static struct passwd *randpwd;
-static u_int8_t randbuf[8];
+static uint8_t randbuf[8];
/* hash to a 16-bit number. this will generate completely harmless
* warnings on 64-bit machines. */
/* handle ~/.passwd. courtesy of shirsch@ibm.net. */
-static __inline__ int home_passwd(const struct passwd *pwd,
- const char *path, const int pathlen,
- char *passwd, const int len,
+static int home_passwd(const struct passwd *pwd,
+ const char *path, const int pathlen _U_,
+ unsigned char *passwd, const int len,
const int set)
{
struct stat st;
int fd, i;
if ( (fd = open(path, (set) ? O_WRONLY : O_RDONLY)) < 0 ) {
- syslog( LOG_ERR, "Failed to open %s", path);
+ LOG(log_error, logtype_uams, "Failed to open %s", path);
return AFPERR_ACCESS;
}
if (!S_ISREG(st.st_mode) || (pwd->pw_uid != st.st_uid) ||
(pwd->pw_gid != st.st_gid) ||
(st.st_mode & ( S_IRWXG | S_IRWXO )) ) {
- syslog( LOG_INFO, "Insecure permissions found for %s.", path);
+ LOG(log_info, logtype_uams, "Insecure permissions found for %s.", path);
goto home_passwd_fail;
}
/* get the password */
if (set) {
if (write(fd, passwd, len) < 0) {
- syslog( LOG_ERR, "Failed to write to %s", path );
+ LOG(log_error, logtype_uams, "Failed to write to %s", path );
goto home_passwd_fail;
}
} else {
if (read(fd, passwd, len) < 0) {
- syslog( LOG_ERR, "Failed to read from %s", path );
+ LOG(log_error, logtype_uams, "Failed to read from %s", path );
goto home_passwd_fail;
}
#define unhex(x) (isdigit(x) ? (x) - '0' : toupper(x) + 10 - 'A')
static int afppasswd(const struct passwd *pwd,
const char *path, const int pathlen,
- char *passwd, int len,
+ unsigned char *passwd, int len,
const int set)
{
- u_int8_t key[DES_KEY_SZ*2];
+ uint8_t key[DES_KEY_SZ*2];
char buf[MAXPATHLEN + 1], *p;
Key_schedule schedule;
FILE *fp;
- int i, j, keyfd = -1, err = 0;
+ unsigned int i, j;
+ int keyfd = -1, err = 0;
off_t pos;
if ((fp = fopen(path, (set) ? "r+" : "r")) == NULL) {
- syslog( LOG_ERR, "Failed to open %s", path);
+ LOG(log_error, logtype_uams, "Failed to open %s", path);
return AFPERR_ACCESS;
}
/* open the key file if it exists */
strcpy(buf, path);
- if (pathlen < sizeof(buf) - 5) {
+ if (pathlen < (int) sizeof(buf) - 5) {
strcat(buf, ".key");
keyfd = open(buf, O_RDONLY);
}
memset(buf, 0, sizeof(buf));
while (fgets(buf, sizeof(buf), fp)) {
if ((p = strchr(buf, ':'))) {
- if (strncmp(buf, pwd->pw_name, p - buf) == 0) {
+ if ( strlen(pwd->pw_name) == (p - buf) &&
+ strncmp(buf, pwd->pw_name, p - buf) == 0) {
p++;
if (*p == PASSWD_ILLEGAL) {
- syslog(LOG_INFO, "invalid password entry for %s", pwd->pw_name);
+ LOG(log_info, logtype_uams, "invalid password entry for %s", pwd->pw_name);
err = AFPERR_ACCESS;
goto afppasswd_done;
}
read(keyfd, key, sizeof(key));
/* convert to binary key */
- for (i = j = 0; i < strlen(key); i += 2, j++)
+ for (i = j = 0; i < strlen((char *) key); i += 2, j++)
key[j] = (unhex(key[i]) << 4) | unhex(key[i + 1]);
if (j <= DES_KEY_SZ)
memset(key + j, 0, sizeof(key) - j);
/* decrypt the password */
ecb_encrypt((C_Block *) p, (C_Block *) p, schedule, DES_DECRYPT);
}
- memset(schedule, 0, sizeof(schedule));
+ memset(&schedule, 0, sizeof(schedule));
}
if (set) {
* depending upon whether or not the password is in ~/.passwd
* or in a global location */
static int randpass(const struct passwd *pwd, const char *file,
- char *passwd, const int len, const int set)
+ unsigned char *passwd, const int len, const int set)
{
int i;
uid_t uid = geteuid();
return i;
}
-
/* randnum sends an 8-byte number and uses the user's password to
* check against the encrypted reply. */
-static int randnum_login(void *obj, struct passwd **uam_pwd,
- char *ibuf, int ibuflen,
- char *rbuf, int *rbuflen)
+static int rand_login(void *obj, char *username, int ulen, struct passwd **uam_pwd _U_,
+ char *ibuf _U_, size_t ibuflen _U_,
+ char *rbuf, size_t *rbuflen)
{
- char *username, *passwdfile;
- u_int16_t sessid;
- int len, ulen, err;
-
- *rbuflen = 0;
-
- if (uam_afpserver_option(obj, UAM_OPTION_USERNAME,
- (void *) &username, &ulen) < 0)
- return AFPERR_PARAM;
- len = UAM_PASSWD_FILENAME;
- if (uam_afpserver_option(obj, UAM_OPTION_PASSWDOPT,
- (void *) &passwdfile, &len) < 0)
- return AFPERR_PARAM;
-
- len = (unsigned char) *ibuf++;
- if ( len > ulen ) {
- return AFPERR_PARAM;
- }
- memcpy(username, ibuf, len );
- ibuf += len;
- username[ len ] = '\0';
- if ((unsigned long) ibuf & 1) /* padding */
- ++ibuf;
+ char *passwdfile;
+ uint16_t sessid;
+ size_t len;
+ int err;
+
+ if (( randpwd = uam_getname(obj, username, ulen)) == NULL )
+ return AFPERR_NOTAUTH; /* unknown user */
- if (( randpwd = uam_getname(username, ulen)) == NULL )
- return AFPERR_PARAM; /* unknown user */
-
- syslog( LOG_INFO, "randnum/rand2num login: %s", username);
+ LOG(log_info, logtype_uams, "randnum/rand2num login: %s", username);
if (uam_checkuser(randpwd) < 0)
return AFPERR_NOTAUTH;
+ len = UAM_PASSWD_FILENAME;
+ if (uam_afpserver_option(obj, UAM_OPTION_PASSWDOPT,
+ (void *) &passwdfile, &len) < 0)
+ return AFPERR_PARAM;
+
if ((err = randpass(randpwd, passwdfile, seskey,
sizeof(seskey), 0)) != AFP_OK)
return err;
/* check encrypted reply. we actually setup the encryption stuff
* here as the first part of randnum and rand2num are identical. */
static int randnum_logincont(void *obj, struct passwd **uam_pwd,
- char *ibuf, int ibuflen,
- char *rbuf, int *rbuflen)
+ char *ibuf, size_t ibuflen _U_,
+ char *rbuf _U_, size_t *rbuflen)
{
- u_int16_t sessid;
+ uint16_t sessid;
*rbuflen = 0;
memset(seskey, 0, sizeof(seskey));
ecb_encrypt((C_Block *) randbuf, (C_Block *) randbuf,
seskeysched, DES_ENCRYPT);
- memset(seskeysched, 0, sizeof(seskeysched));
+ memset(&seskeysched, 0, sizeof(seskeysched));
/* test against what the client sent */
if (memcmp( randbuf, ibuf, sizeof(randbuf) )) { /* != */
* and sends it back as part of the reply.
*/
static int rand2num_logincont(void *obj, struct passwd **uam_pwd,
- char *ibuf, int ibuflen,
- char *rbuf, int *rbuflen)
+ char *ibuf, size_t ibuflen _U_,
+ char *rbuf, size_t *rbuflen)
{
- u_int16_t sessid;
- int i;
+ uint16_t sessid;
+ unsigned int i;
*rbuflen = 0;
/* test against client's reply */
if (memcmp(randbuf, ibuf, sizeof(randbuf))) { /* != */
memset(randbuf, 0, sizeof(randbuf));
- memset(seskeysched, 0, sizeof(seskeysched));
+ memset(&seskeysched, 0, sizeof(seskeysched));
return AFPERR_NOTAUTH;
}
ibuf += sizeof(randbuf);
/* encrypt client's challenge and send back */
ecb_encrypt( (C_Block *) ibuf, (C_Block *) rbuf,
seskeysched, DES_ENCRYPT);
- memset(seskeysched, 0, sizeof(seskeysched));
+ memset(&seskeysched, 0, sizeof(seskeysched));
*rbuflen = sizeof(randbuf);
*uam_pwd = randpwd;
* NOTE: an FPLogin must already have completed successfully for this
* to work.
*/
-static int randnum_changepw(void *obj, const char *username,
+static int randnum_changepw(void *obj, const char *username _U_,
struct passwd *pwd, char *ibuf,
- int ibuflen, char *rbuf, int *rbuflen)
+ size_t ibuflen _U_, char *rbuf _U_, size_t *rbuflen _U_)
{
char *passwdfile;
- int err, len;
+ int err;
+ size_t len;
if (uam_checkuser(pwd) < 0)
return AFPERR_ACCESS;
#endif /* USE_CRACKLIB */
if (!err)
- err = randpass(pwd, passwdfile, ibuf + PASSWDLEN, sizeof(seskey), 1);
+ err = randpass(pwd, passwdfile, (unsigned char *)ibuf + PASSWDLEN, sizeof(seskey), 1);
/* zero out some fields */
- memset(seskeysched, 0, sizeof(seskeysched));
+ memset(&seskeysched, 0, sizeof(seskeysched));
memset(seskey, 0, sizeof(seskey));
memset(ibuf, 0, sizeof(seskey)); /* old passwd */
memset(ibuf + PASSWDLEN, 0, sizeof(seskey)); /* new passwd */
return( AFP_OK );
}
+/* randnum login */
+static int randnum_login(void *obj, struct passwd **uam_pwd,
+ char *ibuf, size_t ibuflen,
+ char *rbuf, size_t *rbuflen)
+{
+ char *username;
+ size_t len, ulen;
+
+ *rbuflen = 0;
+
+ if (uam_afpserver_option(obj, UAM_OPTION_USERNAME,
+ (void *) &username, &ulen) < 0)
+ return AFPERR_MISC;
+
+ if (ibuflen < 2) {
+ return( AFPERR_PARAM );
+ }
+
+ len = (unsigned char) *ibuf++;
+ ibuflen--;
+ if (!len || len > ibuflen || len > ulen ) {
+ return( AFPERR_PARAM );
+ }
+ memcpy(username, ibuf, len );
+ ibuf += len;
+ ibuflen -=len;
+ username[ len ] = '\0';
+
+ if ((unsigned long) ibuf & 1) { /* pad character */
+ ++ibuf;
+ ibuflen--;
+ }
+ return (rand_login(obj, username, ulen, uam_pwd, ibuf, ibuflen, rbuf, rbuflen));
+}
+
+/* randnum login ext */
+static int randnum_login_ext(void *obj, char *uname, struct passwd **uam_pwd,
+ char *ibuf, size_t ibuflen,
+ char *rbuf, size_t *rbuflen)
+{
+ char *username;
+ size_t len, ulen;
+ uint16_t temp16;
+
+ *rbuflen = 0;
+
+ if (uam_afpserver_option(obj, UAM_OPTION_USERNAME,
+ (void *) &username, &ulen) < 0)
+ return AFPERR_MISC;
+
+ if (*uname != 3)
+ return AFPERR_PARAM;
+ uname++;
+ memcpy(&temp16, uname, sizeof(temp16));
+ len = ntohs(temp16);
+ if (!len || len > ulen ) {
+ return( AFPERR_PARAM );
+ }
+ memcpy(username, uname +2, len );
+ username[ len ] = '\0';
+ return (rand_login(obj, username, ulen, uam_pwd, ibuf, ibuflen, rbuf, rbuflen));
+}
+
static int uam_setup(const char *path)
{
- if (uam_register(UAM_SERVER_LOGIN, path, "Randnum exchange",
- randnum_login, randnum_logincont, NULL) < 0)
+ if (uam_register(UAM_SERVER_LOGIN_EXT, path, "Randnum exchange",
+ randnum_login, randnum_logincont, NULL, randnum_login_ext) < 0)
return -1;
- if (uam_register(UAM_SERVER_LOGIN, path, "2-Way Randnum exchange",
- randnum_login, rand2num_logincont, NULL) < 0) {
+
+ if (uam_register(UAM_SERVER_LOGIN_EXT, path, "2-Way Randnum exchange",
+ randnum_login, rand2num_logincont, NULL, randnum_login_ext) < 0) {
uam_unregister(UAM_SERVER_LOGIN, "Randnum exchange");
return -1;
}
-
+
if (uam_register(UAM_SERVER_CHANGEPW, path, "Randnum Exchange",
randnum_changepw) < 0) {
uam_unregister(UAM_SERVER_LOGIN, "Randnum exchange");