summaryrefslogtreecommitdiff
path: root/source3/auth
diff options
context:
space:
mode:
authorAndrew Bartlett <abartlet@samba.org>2003-07-03 14:36:42 +0000
committerAndrew Bartlett <abartlet@samba.org>2003-07-03 14:36:42 +0000
commit61116049cabc292c2f2d570af4d68ddc537b91f5 (patch)
treee72d8978e409cd4664c066cc20c83e69e1ebc300 /source3/auth
parentecb86e5e88579373f3a26f744ae5cdc1a63d9d2d (diff)
downloadsamba-61116049cabc292c2f2d570af4d68ddc537b91f5.tar.gz
samba-61116049cabc292c2f2d570af4d68ddc537b91f5.tar.bz2
samba-61116049cabc292c2f2d570af4d68ddc537b91f5.zip
This patch takes the work the jerry did for beta2, and generalises it:
- The 'not implmented' checks are now done by all auth modules - the ntdomain/trustdomain/winbind modules are more presise as to what domain names they can and cannot handle - The become_root() calls are now around the winbind pipe opening only, not the entire auth call - The unix username is kept seperate from the NT username, removing the need for 'clean off the domain\' in parse_net.c - All sid->uid translations are now validated with getpwuid() to put a very basic stop to logins with 'half deleted' accounts. Andrew Bartlett (This used to be commit 85f88191b9927cc434645ef4c1eaf5ec0e8af2ec)
Diffstat (limited to 'source3/auth')
-rw-r--r--source3/auth/auth.c21
-rw-r--r--source3/auth/auth_builtin.c5
-rw-r--r--source3/auth/auth_domain.c6
-rw-r--r--source3/auth/auth_rhosts.c7
-rw-r--r--source3/auth/auth_server.c4
-rw-r--r--source3/auth/auth_util.c79
-rw-r--r--source3/auth/auth_winbind.c14
7 files changed, 92 insertions, 44 deletions
diff --git a/source3/auth/auth.c b/source3/auth/auth.c
index d99b00d4a7..9f109dc66e 100644
--- a/source3/auth/auth.c
+++ b/source3/auth/auth.c
@@ -203,8 +203,8 @@ static NTSTATUS check_ntlm_password(const struct auth_context *auth_context,
const struct auth_usersupplied_info *user_info,
struct auth_serversupplied_info **server_info)
{
-
- NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
+ /* if all the modules say 'not for me' this is reasonable */
+ NTSTATUS nt_status = NT_STATUS_NO_SUCH_USER;
const char *pdb_username;
auth_methods *auth_method;
TALLOC_CTX *mem_ctx;
@@ -269,12 +269,8 @@ static NTSTATUS check_ntlm_password(const struct auth_context *auth_context,
}
talloc_destroy(mem_ctx);
-
- /* this sucks. Somehow we have to know if an authentication module is
- authoritative for a user. Fixme!!! --jerry */
-
- if ( NT_STATUS_IS_OK(nt_status) ||
- NT_STATUS_V(nt_status) == NT_STATUS_V(NT_STATUS_WRONG_PASSWORD) )
+
+ if ( NT_STATUS_IS_OK(nt_status))
{
break;
}
@@ -463,8 +459,13 @@ NTSTATUS make_auth_context_subsystem(struct auth_context **auth_context)
break;
case SEC_USER:
if (lp_encrypted_passwords()) {
- DEBUG(5,("Making default auth method list for security=user, encrypt passwords = yes\n"));
- auth_method_list = str_list_make("guest sam", NULL);
+ if ((lp_server_role() == ROLE_DOMAIN_PDC) || (lp_server_role() == ROLE_DOMAIN_BDC)) {
+ DEBUG(5,("Making default auth method list for DC, security=user, encrypt passwords = yes\n"));
+ auth_method_list = str_list_make("guest sam winbind:trustdomain", NULL);
+ } else {
+ DEBUG(5,("Making default auth method list for standalone security=user, encrypt passwords = yes\n"));
+ auth_method_list = str_list_make("guest sam", NULL);
+ }
} else {
DEBUG(5,("Making default auth method list for security=user, encrypt passwords = no\n"));
auth_method_list = str_list_make("guest unix", NULL);
diff --git a/source3/auth/auth_builtin.c b/source3/auth/auth_builtin.c
index 5a9b5534ab..0358836793 100644
--- a/source3/auth/auth_builtin.c
+++ b/source3/auth/auth_builtin.c
@@ -38,7 +38,8 @@ static NTSTATUS check_guest_security(const struct auth_context *auth_context,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
- NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
+ /* mark this as 'not for me' */
+ NTSTATUS nt_status = NT_STATUS_NOT_IMPLEMENTED;
if (!(user_info->internal_username.str
&& *user_info->internal_username.str)) {
@@ -133,7 +134,7 @@ static NTSTATUS check_fixed_challenge_security(const struct auth_context *auth_c
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
- return NT_STATUS_UNSUCCESSFUL;
+ return NT_STATUS_NOT_IMPLEMENTED;
}
/****************************************************************************
diff --git a/source3/auth/auth_domain.c b/source3/auth/auth_domain.c
index 80320d8266..56bd6b9aca 100644
--- a/source3/auth/auth_domain.c
+++ b/source3/auth/auth_domain.c
@@ -266,7 +266,7 @@ static NTSTATUS check_ntdomain_security(const struct auth_context *auth_context,
* password file.
*/
- if(is_myname(user_info->domain.str)) {
+ if(strequal(get_global_sam_name(), user_info->domain.str)) {
DEBUG(3,("check_ntdomain_security: Requested domain was for this machine.\n"));
return NT_STATUS_NOT_IMPLEMENTED;
}
@@ -346,7 +346,7 @@ static NTSTATUS check_trustdomain_security(const struct auth_context *auth_conte
* Check that the requested domain is not our own machine name or domain name.
*/
- if( is_myname(user_info->domain.str) || strequal(lp_workgroup(), user_info->domain.str) ) {
+ if( strequal(get_global_sam_name(), user_info->domain.str)) {
DEBUG(3,("check_trustdomain_security: Requested domain [%s] was for this machine.\n",
user_info->domain.str));
return NT_STATUS_NOT_IMPLEMENTED;
@@ -358,7 +358,7 @@ static NTSTATUS check_trustdomain_security(const struct auth_context *auth_conte
user is known to us and does not exist */
if ( !is_trusted_domain( user_info->domain.str ) )
- return NT_STATUS_NO_SUCH_USER;
+ return NT_STATUS_NOT_IMPLEMENTED;
/*
* Get the trusted account password for the trusted domain
diff --git a/source3/auth/auth_rhosts.c b/source3/auth/auth_rhosts.c
index 8fec760e21..e2c6f0b06a 100644
--- a/source3/auth/auth_rhosts.c
+++ b/source3/auth/auth_rhosts.c
@@ -162,7 +162,7 @@ static NTSTATUS check_hostsequiv_security(const struct auth_context *auth_contex
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
- NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
+ NTSTATUS nt_status = NT_STATUS_NOT_IMPLEMENTED;
SAM_ACCOUNT *account = NULL;
if (!NT_STATUS_IS_OK(nt_status =
auth_get_sam_account(user_info->internal_username.str,
@@ -174,7 +174,6 @@ static NTSTATUS check_hostsequiv_security(const struct auth_context *auth_contex
nt_status = make_server_info_sam(server_info, account);
} else {
pdb_free_sam(&account);
- nt_status = NT_STATUS_LOGON_FAILURE;
}
return nt_status;
@@ -203,7 +202,7 @@ static NTSTATUS check_rhosts_security(const struct auth_context *auth_context,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
- NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
+ NTSTATUS nt_status = NT_STATUS_NOT_IMPLEMENTED;
SAM_ACCOUNT *account = NULL;
pstring rhostsfile;
const char *home;
@@ -223,12 +222,10 @@ static NTSTATUS check_rhosts_security(const struct auth_context *auth_context,
nt_status = make_server_info_sam(server_info, account);
} else {
pdb_free_sam(&account);
- nt_status = NT_STATUS_LOGON_FAILURE;
}
unbecome_root();
} else {
pdb_free_sam(&account);
- nt_status = NT_STATUS_LOGON_FAILURE;
}
return nt_status;
diff --git a/source3/auth/auth_server.c b/source3/auth/auth_server.c
index 2a1e4a48d9..af0848e12a 100644
--- a/source3/auth/auth_server.c
+++ b/source3/auth/auth_server.c
@@ -222,7 +222,7 @@ static NTSTATUS check_smbserver_security(const struct auth_context *auth_context
static fstring baduser;
static BOOL tested_password_server = False;
static BOOL bad_password_server = False;
- NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
+ NTSTATUS nt_status = NT_STATUS_NOT_IMPLEMENTED;
BOOL locally_made_cli = False;
/*
@@ -233,7 +233,7 @@ static NTSTATUS check_smbserver_security(const struct auth_context *auth_context
if(is_myname(user_info->domain.str)) {
DEBUG(3,("check_smbserver_security: Requested domain was for this machine.\n"));
- return NT_STATUS_LOGON_FAILURE;
+ return nt_status;
}
cli = my_private_data;
diff --git a/source3/auth/auth_util.c b/source3/auth/auth_util.c
index 4e25d7fd34..ea46d27e9e 100644
--- a/source3/auth/auth_util.c
+++ b/source3/auth/auth_util.c
@@ -764,6 +764,7 @@ NTSTATUS make_server_info_sam(auth_serversupplied_info **server_info,
SAM_ACCOUNT *sampass)
{
NTSTATUS nt_status;
+ struct passwd *pwd;
if (!NT_STATUS_IS_OK(nt_status = make_server_info(server_info)))
return nt_status;
@@ -773,16 +774,35 @@ NTSTATUS make_server_info_sam(auth_serversupplied_info **server_info,
if (!NT_STATUS_IS_OK(nt_status = sid_to_uid(pdb_get_user_sid(sampass), &((*server_info)->uid))))
return nt_status;
- if (!NT_STATUS_IS_OK(nt_status = sid_to_gid(pdb_get_group_sid(sampass), &((*server_info)->gid))))
+ if (!(pwd = getpwuid_alloc(((*server_info)->uid)))) {
+ fstring sid;
+ DEBUG(1, ("User %s in passdb (%s) maps to UID, but getpwuid(%u) fails!\n",
+ pdb_get_username(sampass),
+ sid_to_string(sid, pdb_get_user_sid(sampass)),
+ (unsigned)(*server_info)->uid));
+ free_server_info(server_info);
+ return NT_STATUS_NO_SUCH_USER;
+ }
+ (*server_info)->unix_name = smb_xstrdup(pwd->pw_name);
+ passwd_free(&pwd);
+
+ if (!NT_STATUS_IS_OK(nt_status = sid_to_gid(pdb_get_group_sid(sampass),
+ &((*server_info)->gid)))) {
+ free_server_info(server_info);
return nt_status;
+ }
if (!NT_STATUS_IS_OK(nt_status = add_user_groups(server_info, sampass,
- (*server_info)->uid, (*server_info)->gid)))
+ (*server_info)->uid,
+ (*server_info)->gid))) {
+ free_server_info(server_info);
return nt_status;
+ }
(*server_info)->sam_fill_level = SAM_FILL_ALL;
- DEBUG(5,("make_server_info_sam: made server info for user %s\n",
- pdb_get_username((*server_info)->sam_account)));
+ DEBUG(5,("make_server_info_sam: made server info for user %s -> %s\n",
+ pdb_get_username(sampass),
+ (*server_info)->unix_name));
return nt_status;
}
@@ -809,6 +829,8 @@ NTSTATUS make_server_info_pw(auth_serversupplied_info **server_info, const struc
return nt_status;
}
+ (*server_info)->unix_name = smb_xstrdup(pwd->pw_name);
+
(*server_info)->sam_fill_level = SAM_FILL_ALL;
(*server_info)->uid = pwd->pw_uid;
(*server_info)->gid = pwd->pw_gid;
@@ -852,8 +874,10 @@ NTSTATUS make_server_info_guest(auth_serversupplied_info **server_info)
Purely internal function for make_server_info_info3
Fill the sam account from getpwnam
***************************************************************************/
-static NTSTATUS fill_sam_account(const char *domain,
+static NTSTATUS fill_sam_account(TALLOC_CTX *mem_ctx,
+ const char *domain,
const char *username,
+ char **found_username,
uid_t *uid, gid_t *gid,
SAM_ACCOUNT **sam_account)
{
@@ -878,6 +902,8 @@ static NTSTATUS fill_sam_account(const char *domain,
*uid = passwd->pw_uid;
*gid = passwd->pw_gid;
+ *found_username = talloc_strdup(mem_ctx, passwd->pw_name);
+
return pdb_init_sam_pw(sam_account, passwd);
}
@@ -893,7 +919,7 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx,
NET_USER_INFO_3 *info3)
{
NTSTATUS nt_status = NT_STATUS_OK;
-
+ char *found_username;
const char *nt_domain;
const char *nt_username;
@@ -958,13 +984,15 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx,
gid = passwd->pw_gid;
/* we should check this is the same name */
-
+ found_username = talloc_strdup(mem_ctx, passwd->pw_name);
+
passwd_free(&passwd);
} else {
/* User not from winbind - try and find them by getpwnam() */
- nt_status = fill_sam_account(nt_domain,
+ nt_status = fill_sam_account(mem_ctx, nt_domain,
internal_username,
+ &found_username,
&uid, &gid,
&sam_account);
@@ -972,8 +1000,9 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx,
DEBUG(3,("User %s does not exist, trying to add it\n",
internal_username));
auth_add_user_script(nt_domain, internal_username);
- nt_status = fill_sam_account(nt_domain,
+ nt_status = fill_sam_account(mem_ctx, nt_domain,
internal_username,
+ &found_username,
&uid, &gid,
&sam_account);
}
@@ -984,17 +1013,12 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx,
return nt_status;
}
- if (!pdb_set_user_sid(sam_account, &user_sid, PDB_CHANGED)) {
+ if (!pdb_set_nt_username(sam_account, nt_username, PDB_CHANGED)) {
pdb_free_sam(&sam_account);
- return NT_STATUS_UNSUCCESSFUL;
+ return NT_STATUS_NO_MEMORY;
}
- if (!pdb_set_group_sid(sam_account, &group_sid, PDB_CHANGED)) {
- pdb_free_sam(&sam_account);
- return NT_STATUS_UNSUCCESSFUL;
- }
-
- if (!pdb_set_nt_username(sam_account, nt_username, PDB_CHANGED)) {
+ if (!pdb_set_username(sam_account, nt_username, PDB_CHANGED)) {
pdb_free_sam(&sam_account);
return NT_STATUS_NO_MEMORY;
}
@@ -1004,7 +1028,18 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx,
return NT_STATUS_NO_MEMORY;
}
- if (!pdb_set_fullname(sam_account, unistr2_static(&(info3->uni_full_name)), PDB_CHANGED)) {
+ if (!pdb_set_user_sid(sam_account, &user_sid, PDB_CHANGED)) {
+ pdb_free_sam(&sam_account);
+ return NT_STATUS_UNSUCCESSFUL;
+ }
+
+ if (!pdb_set_group_sid(sam_account, &group_sid, PDB_CHANGED)) {
+ pdb_free_sam(&sam_account);
+ return NT_STATUS_UNSUCCESSFUL;
+ }
+
+ if (!pdb_set_fullname(sam_account, unistr2_static(&(info3->uni_full_name)),
+ PDB_CHANGED)) {
pdb_free_sam(&sam_account);
return NT_STATUS_NO_MEMORY;
}
@@ -1040,6 +1075,8 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx,
(*server_info)->sam_account = sam_account;
+ (*server_info)->unix_name = smb_xstrdup(found_username);
+
/* Fill in the unix info we found on the way */
(*server_info)->sam_fill_level = SAM_FILL_ALL;
@@ -1050,7 +1087,7 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx,
returned to the caller. */
if (!NT_STATUS_IS_OK(nt_status
- = get_user_groups_from_local_sam(pdb_get_username(sam_account),
+ = get_user_groups_from_local_sam((*server_info)->unix_name,
uid, gid,
&n_lgroupSIDs,
&lgroupSIDs,
@@ -1070,6 +1107,7 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx,
if (!all_group_SIDs) {
DEBUG(0, ("malloc() failed for DOM_SID list!\n"));
SAFE_FREE(lgroupSIDs);
+ free_server_info(server_info);
return NT_STATUS_NO_MEMORY;
}
@@ -1085,6 +1123,7 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx,
DEBUG(3,("could not append additional group rid 0x%x\n",
info3->gids[i].g_rid));
SAFE_FREE(lgroupSIDs);
+ free_server_info(server_info);
return nt_status;
}
}
@@ -1110,6 +1149,7 @@ NTSTATUS make_server_info_info3(TALLOC_CTX *mem_ctx,
all_group_SIDs, False, &token))) {
DEBUG(4,("create_nt_user_token failed\n"));
SAFE_FREE(all_group_SIDs);
+ free_server_info(server_info);
return nt_status;
}
@@ -1161,6 +1201,7 @@ void free_server_info(auth_serversupplied_info **server_info)
/* call pam_end here, unless we know we are keeping it */
delete_nt_token( &(*server_info)->ptok );
SAFE_FREE((*server_info)->groups);
+ SAFE_FREE((*server_info)->unix_name);
ZERO_STRUCT(**server_info);
}
SAFE_FREE(*server_info);
diff --git a/source3/auth/auth_winbind.c b/source3/auth/auth_winbind.c
index 6ae8685b11..856b8f5a82 100644
--- a/source3/auth/auth_winbind.c
+++ b/source3/auth/auth_winbind.c
@@ -72,9 +72,14 @@ static NTSTATUS check_winbind_security(const struct auth_context *auth_context,
if (!auth_context) {
DEBUG(3,("Password for user %s cannot be checked because we have no auth_info to get the challenge from.\n",
user_info->internal_username.str));
- return NT_STATUS_UNSUCCESSFUL;
+ return NT_STATUS_INVALID_PARAMETER;
}
+ if (strequal(user_info->domain.str, get_global_sam_name())) {
+ DEBUG(3,("check_winbind_security: Not using winbind, requested domain was for this SAM.\n"));
+ return NT_STATUS_NOT_IMPLEMENTED;
+ }
+
/* Send off request */
ZERO_STRUCT(request);
@@ -100,8 +105,11 @@ static NTSTATUS check_winbind_security(const struct auth_context *auth_context,
request.data.auth_crap.lm_resp_len);
memcpy(request.data.auth_crap.nt_resp, user_info->nt_resp.data,
request.data.auth_crap.nt_resp_len);
-
+
+ /* we are contacting the privileged pipe */
+ become_root();
result = winbindd_request(WINBINDD_PAM_AUTH_CRAP, &request, &response);
+ unbecome_root();
if ( result == NSS_STATUS_UNAVAIL ) {
struct auth_methods *auth_method = my_private_data;
@@ -129,7 +137,7 @@ static NTSTATUS check_winbind_security(const struct auth_context *auth_context,
}
}
} else if (NT_STATUS_IS_OK(nt_status)) {
- nt_status = NT_STATUS_UNSUCCESSFUL;
+ nt_status = NT_STATUS_NO_LOGON_SERVERS;
}
return nt_status;