diff options
author | Luke Leighton <lkcl@samba.org> | 2000-02-04 05:16:57 +0000 |
---|---|---|
committer | Luke Leighton <lkcl@samba.org> | 2000-02-04 05:16:57 +0000 |
commit | 1cc42831d37417035188cedf9b36a638cc754160 (patch) | |
tree | f84b900aa9639b9250cee23b3552dcc400042c71 /source/smbd | |
parent | cbac99425b0b230788ea71ca716806b1332b5006 (diff) | |
download | samba-1cc42831d37417035188cedf9b36a638cc754160.tar.gz |
ok, this _is_ as big as it looks, conceptually, and i haven't even
done what i wanted to: this is only preparation!!!!
i started off in smbd/lanman.c, and noticed that api_NetUserGetInfo
takes all its info from user_struct *vuser. i thought, that's odd,
that doesn't look right.
then i realised that the info there is exactly what is contained in
the NET_USER_INFO_3 structure: the return result from an NT Domain
User Logon.
various lights went on, and i realised that when an SMBsesssetupX
is carried out, internally, NT must do an NT Domain User Logon
with the SMB user's challenge/response password, and then store the
return result associated with the SMB session.
in this way, when an api_NetUserGetInfo call comes in, the CORRECT
info can be returned, not some faked-up information.
anyway, this commit is all the consequences of putting NET_USER_INFO_3
into user_struct, which feeds up through _several_ layers of function
calls. i sort-of understood that i needed to do this, but not quite.
the upshot of this is that user_struct now contains the REAL nt
domain username (in NET_USER_INFO_3) so the confusion between nt
user names and unix usernames now can be removed from samba code.
if you want a unix user name, you use vuser->unix_name.
if you want an NT user name, you use (UNISTR2*)vuser->usr.uni_user_name.
p.s it's in UNICODE :)
p.p.s if you want the RID of the user, it's vuser->usr.user_rid.
p.p.p.s there's over 25 NT-specific other bits of info in NET_USER_INFO_3
too!
Diffstat (limited to 'source/smbd')
-rw-r--r-- | source/smbd/chgpasswd.c | 2 | ||||
-rw-r--r-- | source/smbd/lanman.c | 12 | ||||
-rw-r--r-- | source/smbd/negprot.c | 27 | ||||
-rw-r--r-- | source/smbd/password.c | 173 | ||||
-rw-r--r-- | source/smbd/process.c | 5 | ||||
-rw-r--r-- | source/smbd/reply.c | 9 |
6 files changed, 28 insertions, 200 deletions
diff --git a/source/smbd/chgpasswd.c b/source/smbd/chgpasswd.c index a07723f937c..9ebc4ed2f9a 100644 --- a/source/smbd/chgpasswd.c +++ b/source/smbd/chgpasswd.c @@ -829,7 +829,7 @@ BOOL change_oem_password(struct smb_passwd *smbpw, UNISTR2 *new_passwd, /**************************************************************************** update the encrypted smbpasswd file from the plaintext username and password *****************************************************************************/ -BOOL update_smbpassword_file(char *user, char *password) +BOOL update_smbpassword_file(const char *user, const char *password) { struct smb_passwd *smbpw; UNISTR2 newpw; diff --git a/source/smbd/lanman.c b/source/smbd/lanman.c index 3a15e90e8fa..49f4563b34c 100644 --- a/source/smbd/lanman.c +++ b/source/smbd/lanman.c @@ -1630,18 +1630,6 @@ static BOOL api_SamOEMChangePassword(connection_struct *conn,uint16 vuid, char * DEBUG(3,("api_SamOEMChangePassword: Change password for <%s>\n",user)); - /* - * Pass the user through the NT -> unix user mapping - * function. - */ - - (void)map_username(user); - - /* - * Do any UNIX username case mangling. - */ - (void)Get_Pwnam( user, True); - if (msrpc_sam_ntpasswd_set("\\\\.", user, NULL, (uchar*) data, (uchar *)&data[516], /* lm pw */ NULL, NULL)) /* nt pw */ diff --git a/source/smbd/negprot.c b/source/smbd/negprot.c index 0b48b0e2b25..4498e42950b 100644 --- a/source/smbd/negprot.c +++ b/source/smbd/negprot.c @@ -111,15 +111,6 @@ static int reply_lanman2(char *outbuf) char cryptkey[8]; char crypt_len = 0; - if (lp_security() == SEC_SERVER) { - cli = server_cryptkey(); - } - - if (cli) { - DEBUG(3,("using password server validation\n")); - doencrypt = ((cli->sec_mode & 2) != 0); - } - if (lp_security()>=SEC_USER) secword |= 1; if (doencrypt) secword |= 2; @@ -164,7 +155,6 @@ static int reply_nt1(char *outbuf) BOOL doencrypt = SMBENCRYPT(); time_t t = time(NULL); int data_len; - struct cli_state *cli = NULL; char cryptkey[8]; char crypt_len = 0; @@ -190,24 +180,9 @@ static int reply_nt1(char *outbuf) CAP_LARGE_READX|CAP_STATUS32|CAP_LEVEL_II_OPLOCKS; */ - if (lp_security() == SEC_SERVER) - { - cli = server_cryptkey(); - } - - if (cli) { - DEBUG(3,("using password server validation\n")); - doencrypt = ((cli->sec_mode & 2) != 0); - } - if (doencrypt) { crypt_len = 8; - if (!cli) { - generate_next_challenge(cryptkey); - } else { - memcpy(cryptkey, cli->cryptkey, 8); - set_challenge(cli->cryptkey); - } + generate_next_challenge(cryptkey); } if (lp_readraw() && lp_writeraw()) { diff --git a/source/smbd/password.c b/source/smbd/password.c index 7b6668c04d9..2141525bc09 100644 --- a/source/smbd/password.c +++ b/source/smbd/password.c @@ -55,129 +55,27 @@ void add_session_user(char *user) } /**************************************************************************** -validate a password with the password server -****************************************************************************/ -static BOOL check_server_security(char *user, char *domain, - char *pass, int passlen, - char *ntpass, int ntpasslen) -{ - struct cli_state *cli; - static unsigned char badpass[24]; - static BOOL tested_password_server = False; - static BOOL bad_password_server = False; - - if(lp_security() != SEC_SERVER) - return False; - - DEBUG(10,("check_server_security\n")); - - cli = server_client(); - - if (!cli->initialised) - { - DEBUG(1,("password server %s is not connected\n", cli->desthost)); - return False; - } - - if(badpass[0] == 0) - memset(badpass, 0x1f, sizeof(badpass)); - - if((passlen == sizeof(badpass)) && !memcmp(badpass, pass, passlen)) { - /* - * Very unlikely, our random bad password is the same as the users - * password. */ - memset(badpass, badpass[0]+1, sizeof(badpass)); - } - - /* - * Attempt a session setup with a totally incorrect password. - * If this succeeds with the guest bit *NOT* set then the password - * server is broken and is not correctly setting the guest bit. We - * need to detect this as some versions of NT4.x are broken. JRA. - */ - - if(!tested_password_server) { - if (cli_session_setup(cli, global_myname, - user, (char *)badpass, sizeof(badpass), - (char *)badpass, sizeof(badpass), domain)) { - - /* - * We connected to the password server so we - * can say we've tested it. - */ - tested_password_server = True; - - if ((SVAL(cli->inbuf,smb_vwv2) & 1) == 0) { - DEBUG(0,("server_validate: password server %s allows users as non-guest \ -with a bad password.\n", cli->desthost)); - DEBUG(0,("server_validate: This is broken (and insecure) behaviour. Please do not \ -use this machine as the password server.\n")); - cli_ulogoff(cli); - - /* - * Password server has the bug. - */ - bad_password_server = True; - return False; - } - cli_ulogoff(cli); - } - } else { - - /* - * We have already tested the password server. - * Fail immediately if it has the bug. - */ - - if(bad_password_server) { - DEBUG(0,("server_validate: [1] password server %s allows users as non-guest \ -with a bad password.\n", cli->desthost)); - DEBUG(0,("server_validate: [1] This is broken (and insecure) behaviour. Please do not \ -use this machine as the password server.\n")); - return False; - } - } - - /* - * Now we know the password server will correctly set the guest bit, or is - * not guest enabled, we can try with the real password. - */ - - if (!cli_session_setup(cli, global_myname, - user, pass, passlen, ntpass, ntpasslen, domain)) { - DEBUG(1,("password server %s rejected the password\n", cli->desthost)); - return False; - } - - /* if logged in as guest then reject */ - if ((SVAL(cli->inbuf,smb_vwv2) & 1) != 0) { - DEBUG(1,("password server %s gave us guest only\n", cli->desthost)); - cli_ulogoff(cli); - return False; - } - - - cli_ulogoff(cli); - - return(True); -} - - -/**************************************************************************** check if a username/password pair is OK either via the system password database or the encrypted SMB password database return True if the password is correct, False otherwise ****************************************************************************/ -BOOL password_ok(char *orig_user, char *domain, - char *smb_apasswd, int smb_apasslen, - char *smb_ntpasswd, int smb_ntpasslen, +BOOL password_ok(const char *orig_user, const char *domain, + const char *smb_apasswd, int smb_apasslen, + const char *smb_ntpasswd, int smb_ntpasslen, struct passwd *pwd, - uchar user_sess_key[16]) + NET_USER_INFO_3 *info3) { uchar last_chal[8]; BOOL cleartext = smb_apasslen != 24 && smb_ntpasslen == 0; uchar *chal = NULL; + if (info3 == NULL) + { + DEBUG(0,("password_ok: no NET_USER_INFO_3 parameter!\n")); + return False; + } + + ZERO_STRUCTP(info3); /* * SMB password check */ @@ -186,15 +84,7 @@ BOOL password_ok(char *orig_user, char *domain, (lp_encrypted_passwords() && smb_apasslen == 0 && lp_null_passwords())) { - /* check security = server */ - if (!cleartext && - check_server_security(orig_user, domain, - smb_apasswd, smb_apasslen, - smb_ntpasswd, smb_ntpasslen)) - { - DEBUG(10,("password_ok: server auth succeeded\n")); - return True; - } + DEBUG(10,("password_ok: check SMB auth\n")); /* check security = user / domain */ if ((!cleartext) && last_challenge(last_chal)) @@ -206,7 +96,7 @@ BOOL password_ok(char *orig_user, char *domain, chal, smb_apasswd, smb_apasslen, smb_ntpasswd, smb_ntpasslen, - user_sess_key, NULL) == 0x0) + info3) == 0x0) { DEBUG(10,("password_ok: domain auth succeeded\n")); return True; @@ -236,7 +126,7 @@ BOOL password_ok(char *orig_user, char *domain, validate a group username entry. Return the username or NULL ****************************************************************************/ static char *validate_group(char *group,char *password,int pwlen,int snum, - uchar user_sess_key[16]) + NET_USER_INFO_3 *info3) { #if defined(HAVE_NETGROUP) && defined(HAVE_GETNETGRENT) && defined(HAVE_SETNETGRENT) && defined(HAVE_ENDNETGRENT) { @@ -245,7 +135,7 @@ static char *validate_group(char *group,char *password,int pwlen,int snum, while (getnetgrent(&host, &user, &domain)) { if (user) { if (user_ok(user, snum) && - password_ok(user,NULL,password,pwlen,NULL,0,NULL,user_sess_key)) + password_ok(user,NULL,password,pwlen,NULL,0,NULL,info3)) { endnetgrent(); return(user); @@ -268,7 +158,7 @@ static char *validate_group(char *group,char *password,int pwlen,int snum, static fstring name; fstrcpy(name,*member); if (user_ok(name,snum) && - password_ok(name,NULL,password,pwlen,NULL,0,NULL, user_sess_key)) + password_ok(name,NULL,password,pwlen,NULL,0,NULL, info3)) return(&name[0]); member++; } @@ -335,14 +225,14 @@ BOOL authorise_login(int snum,char *user, char *domain, /* check the given username and password */ if (!ok && (*user) && user_ok(user,snum)) { - ok = password_ok(user,domain, password, pwlen, NULL, 0, NULL, vuser->user_sess_key); + ok = password_ok(user,domain, password, pwlen, NULL, 0, NULL, &vuser->usr); if (ok) DEBUG(3,("ACCEPTED: given username password ok\n")); } /* check for a previously registered guest username */ if (!ok && (vuser != 0) && vuser->guest) { if (user_ok(vuser->name,snum) && - password_ok(vuser->name, domain, password, pwlen, NULL, 0, NULL, vuser->user_sess_key)) { + password_ok(vuser->name, domain, password, pwlen, NULL, 0, NULL, &vuser->usr)) { fstrcpy(user, vuser->name); vuser->guest = False; DEBUG(3,("ACCEPTED: given password with registered user %s\n", user)); @@ -367,7 +257,7 @@ BOOL authorise_login(int snum,char *user, char *domain, if (!user_ok(user2,snum)) continue; if (password_ok(user2, domain, password, pwlen, NULL, 0, NULL, - vuser->user_sess_key)) + &vuser->usr)) { ok = True; fstrcpy(user,user2); @@ -407,7 +297,7 @@ BOOL authorise_login(int snum,char *user, char *domain, { if (*auser == '@') { - auser = validate_group(auser+1,password,pwlen,snum, vuser->user_sess_key); + auser = validate_group(auser+1,password,pwlen,snum, &vuser->usr); if (auser) { ok = True; @@ -421,7 +311,7 @@ BOOL authorise_login(int snum,char *user, char *domain, fstrcpy(user2,auser); if (user_ok(user2,snum) && password_ok(user2,domain,password,pwlen,NULL, 0, - NULL, vuser->user_sess_key)) + NULL, &vuser->usr)) { ok = True; fstrcpy(user,user2); @@ -598,24 +488,3 @@ BOOL check_hosts_equiv(char *user) } -/**************************************************************************** -return the client state structure -****************************************************************************/ -struct cli_state *server_client(void) -{ - static struct cli_state pw_cli; - return &pw_cli; -} - -/**************************************************************************** -support for server level security -****************************************************************************/ -struct cli_state *server_cryptkey(void) -{ - if (cli_connect_serverlist(server_client(), lp_passwordserver())) - { - return server_client(); - } - return NULL; -} - diff --git a/source/smbd/process.c b/source/smbd/process.c index 6b151bf3bc6..d391914f600 100644 --- a/source/smbd/process.c +++ b/source/smbd/process.c @@ -884,15 +884,10 @@ void smbd_process(void) if (keepalive && (counter-last_keepalive)>keepalive) { - struct cli_state *cli = server_client(); if (!send_keepalive(Client)) { DEBUG( 2, ( "Keepalive failed - exiting.\n" ) ); return; } - /* also send a keepalive to the password server if its still - connected */ - if (cli && cli->initialised) - send_keepalive(cli->fd); last_keepalive = counter; } diff --git a/source/smbd/reply.c b/source/smbd/reply.c index 8bdbec7f127..718f0cf47f8 100644 --- a/source/smbd/reply.c +++ b/source/smbd/reply.c @@ -383,11 +383,12 @@ static int session_trust_account(connection_struct *conn, if (last_challenge(last_chal)) { + NET_USER_INFO_3 info3; status = check_domain_security(user, domain, last_chal, (uchar *)smb_passwd, smb_passlen, (uchar *)smb_nt_passwd, smb_nt_passlen, - NULL, NULL); + &info3); } else { @@ -410,7 +411,7 @@ reply to a session setup command int reply_sesssetup_and_X(connection_struct *conn, char *inbuf,char *outbuf,int length,int bufsize) { uint16 sess_vuid; - uchar user_sess_key[16]; + NET_USER_INFO_3 info3; int gid; int uid; int smb_bufsize; @@ -611,7 +612,7 @@ user %s attempted down-level SMB connection\n", user)); if(!password_ok(orig_user, domain, smb_apasswd,smb_apasslen, smb_ntpasswd,smb_ntpasslen, - NULL, user_sess_key)) + NULL, &info3)) { DEBUG(0,("SMB LM/NT Password did not match!\n")); @@ -692,7 +693,7 @@ user %s attempted down-level SMB connection\n", user)); /* register the name and uid as being validated, so further connections to a uid can get through without a password, on the same VC */ - sess_vuid = register_vuid(uid,gid,user,sesssetup_user,guest,user_sess_key); + sess_vuid = register_vuid(uid,gid,user,sesssetup_user,guest,&info3); SSVAL(outbuf,smb_uid,sess_vuid); SSVAL(inbuf,smb_uid,sess_vuid); |