diff options
Diffstat (limited to 'source3')
-rw-r--r-- | source3/rpc_client/cli_samr.c | 95 | ||||
-rw-r--r-- | source3/rpcclient/cmd_samr.c | 26 | ||||
-rw-r--r-- | source3/winbindd/winbindd_pam.c | 37 |
3 files changed, 85 insertions, 73 deletions
diff --git a/source3/rpc_client/cli_samr.c b/source3/rpc_client/cli_samr.c index 4765e529be..d94649c4eb 100644 --- a/source3/rpc_client/cli_samr.c +++ b/source3/rpc_client/cli_samr.c @@ -22,6 +22,11 @@ #include "includes.h" +static void init_lsa_String(struct lsa_String *name, const char *s) +{ + name->string = s; +} + /* Query user info */ NTSTATUS rpccli_samr_query_userinfo(struct rpc_pipe_client *cli, @@ -601,80 +606,76 @@ NTSTATUS rpccli_samr_chng_pswd_auth_crap(struct rpc_pipe_client *cli, /* change password 3 */ NTSTATUS rpccli_samr_chgpasswd3(struct rpc_pipe_client *cli, - TALLOC_CTX *mem_ctx, - const char *username, - const char *newpassword, + TALLOC_CTX *mem_ctx, + const char *username, + const char *newpassword, const char *oldpassword, - SAM_UNK_INFO_1 *info, - SAMR_CHANGE_REJECT *reject) + struct samr_DomInfo1 **dominfo1, + struct samr_ChangeReject **reject) { - prs_struct qbuf, rbuf; - SAMR_Q_CHGPASSWD_USER3 q; - SAMR_R_CHGPASSWD_USER3 r; + NTSTATUS status; + + struct samr_CryptPassword new_nt_password; + struct samr_CryptPassword new_lm_password; + struct samr_Password old_nt_hash_enc; + struct samr_Password old_lanman_hash_enc; - uchar new_nt_password[516]; - uchar new_lm_password[516]; uchar old_nt_hash[16]; uchar old_lanman_hash[16]; - uchar old_nt_hash_enc[16]; - uchar old_lanman_hash_enc[16]; - uchar new_nt_hash[16]; uchar new_lanman_hash[16]; - char *srv_name_slash = talloc_asprintf(mem_ctx, "\\\\%s", cli->cli->desthost); + struct lsa_String server, account; + char *srv_name_slash = NULL; DEBUG(10,("rpccli_samr_chgpasswd_user3\n")); - ZERO_STRUCT(q); - ZERO_STRUCT(r); + srv_name_slash = talloc_asprintf(mem_ctx, "\\\\%s", cli->cli->desthost); + if (!srv_name_slash) { + return NT_STATUS_NO_MEMORY; + } + + init_lsa_String(&server, srv_name_slash); + init_lsa_String(&account, username); /* Calculate the MD4 hash (NT compatible) of the password */ E_md4hash(oldpassword, old_nt_hash); E_md4hash(newpassword, new_nt_hash); - if (lp_client_lanman_auth() - && E_deshash(newpassword, new_lanman_hash) - && E_deshash(oldpassword, old_lanman_hash)) { + if (lp_client_lanman_auth() && + E_deshash(newpassword, new_lanman_hash) && + E_deshash(oldpassword, old_lanman_hash)) { /* E_deshash returns false for 'long' passwords (> 14 DOS chars). This allows us to match Win2k, which does not store a LM hash for these passwords (which would reduce the effective password length to 14) */ - encode_pw_buffer(new_lm_password, newpassword, STR_UNICODE); + encode_pw_buffer(new_lm_password.data, newpassword, STR_UNICODE); - SamOEMhash( new_lm_password, old_nt_hash, 516); - E_old_pw_hash( new_nt_hash, old_lanman_hash, old_lanman_hash_enc); + SamOEMhash(new_lm_password.data, old_nt_hash, 516); + E_old_pw_hash(new_nt_hash, old_lanman_hash, old_lanman_hash_enc.hash); } else { ZERO_STRUCT(new_lm_password); ZERO_STRUCT(old_lanman_hash_enc); } - encode_pw_buffer(new_nt_password, newpassword, STR_UNICODE); - - SamOEMhash( new_nt_password, old_nt_hash, 516); - E_old_pw_hash( new_nt_hash, old_nt_hash, old_nt_hash_enc); - - /* Marshall data and send request */ - - init_samr_q_chgpasswd_user3(&q, srv_name_slash, username, - new_nt_password, - old_nt_hash_enc, - new_lm_password, - old_lanman_hash_enc); - r.info = info; - r.reject = reject; - - CLI_DO_RPC(cli, mem_ctx, PI_SAMR, SAMR_CHGPASSWD_USER3, - q, r, - qbuf, rbuf, - samr_io_q_chgpasswd_user3, - samr_io_r_chgpasswd_user3, - NT_STATUS_UNSUCCESSFUL); - - /* Return output parameters */ - - return r.status; + encode_pw_buffer(new_nt_password.data, newpassword, STR_UNICODE); + + SamOEMhash(new_nt_password.data, old_nt_hash, 516); + E_old_pw_hash(new_nt_hash, old_nt_hash, old_nt_hash_enc.hash); + + status = rpccli_samr_ChangePasswordUser3(cli, mem_ctx, + &server, + &account, + &new_nt_password, + &old_nt_hash_enc, + true, + &new_lm_password, + &old_lanman_hash_enc, + NULL, + dominfo1, + reject); + return status; } /* This function returns the bizzare set of (max_entries, max_size) required diff --git a/source3/rpcclient/cmd_samr.c b/source3/rpcclient/cmd_samr.c index 3429f921b8..8a6b9a0df1 100644 --- a/source3/rpcclient/cmd_samr.c +++ b/source3/rpcclient/cmd_samr.c @@ -2367,10 +2367,10 @@ static NTSTATUS cmd_samr_chgpasswd2(struct rpc_pipe_client *cli, user = argv[1]; oldpass = argv[2]; newpass = argv[3]; - + /* Get sam policy handle */ - result = try_samr_connects(cli, mem_ctx, MAXIMUM_ALLOWED_ACCESS, + result = try_samr_connects(cli, mem_ctx, MAXIMUM_ALLOWED_ACCESS, &connect_pol); if (!NT_STATUS_IS_OK(result)) @@ -2406,16 +2406,16 @@ static NTSTATUS cmd_samr_chgpasswd2(struct rpc_pipe_client *cli, /* Change user password */ -static NTSTATUS cmd_samr_chgpasswd3(struct rpc_pipe_client *cli, +static NTSTATUS cmd_samr_chgpasswd3(struct rpc_pipe_client *cli, TALLOC_CTX *mem_ctx, - int argc, const char **argv) + int argc, const char **argv) { POLICY_HND connect_pol, domain_pol; NTSTATUS result = NT_STATUS_UNSUCCESSFUL; const char *user, *oldpass, *newpass; uint32 access_mask = MAXIMUM_ALLOWED_ACCESS; - SAM_UNK_INFO_1 info; - SAMR_CHANGE_REJECT reject; + struct samr_DomInfo1 *info = NULL; + struct samr_ChangeReject *reject = NULL; if (argc < 3) { printf("Usage: %s username oldpass newpass\n", argv[0]); @@ -2446,13 +2446,18 @@ static NTSTATUS cmd_samr_chgpasswd3(struct rpc_pipe_client *cli, goto done; /* Change user password */ - result = rpccli_samr_chgpasswd3(cli, mem_ctx, user, newpass, oldpass, &info, &reject); + result = rpccli_samr_chgpasswd3(cli, mem_ctx, + user, + newpass, + oldpass, + &info, + &reject); if (NT_STATUS_EQUAL(result, NT_STATUS_PASSWORD_RESTRICTION)) { - /*display_sam_dom_info_1(&info);*/ + display_sam_dom_info_1(info); - switch (reject.reject_reason) { + switch (reject->reason) { case SAMR_REJECT_TOO_SHORT: d_printf("SAMR_REJECT_TOO_SHORT\n"); break; @@ -2466,7 +2471,8 @@ static NTSTATUS cmd_samr_chgpasswd3(struct rpc_pipe_client *cli, d_printf("SAMR_REJECT_OTHER\n"); break; default: - d_printf("unknown reject reason: %d\n", reject.reject_reason); + d_printf("unknown reject reason: %d\n", + reject->reason); break; } } diff --git a/source3/winbindd/winbindd_pam.c b/source3/winbindd/winbindd_pam.c index c1a277f9b5..759adb366e 100644 --- a/source3/winbindd/winbindd_pam.c +++ b/source3/winbindd/winbindd_pam.c @@ -1936,8 +1936,8 @@ enum winbindd_result winbindd_dual_pam_chauthtok(struct winbindd_domain *contact POLICY_HND dom_pol; struct rpc_pipe_client *cli; bool got_info = False; - SAM_UNK_INFO_1 info; - SAMR_CHANGE_REJECT reject; + struct samr_DomInfo1 *info = NULL; + struct samr_ChangeReject *reject = NULL; NTSTATUS result = NT_STATUS_UNSUCCESSFUL; fstring domain, user; @@ -1965,24 +1965,29 @@ enum winbindd_result winbindd_dual_pam_chauthtok(struct winbindd_domain *contact goto done; } - result = rpccli_samr_chgpasswd3(cli, state->mem_ctx, user, newpass, oldpass, &info, &reject); + result = rpccli_samr_chgpasswd3(cli, state->mem_ctx, + user, + newpass, + oldpass, + &info, + &reject); /* Windows 2003 returns NT_STATUS_PASSWORD_RESTRICTION */ if (NT_STATUS_EQUAL(result, NT_STATUS_PASSWORD_RESTRICTION) ) { - state->response.data.auth.policy.min_length_password = - info.min_length_password; - state->response.data.auth.policy.password_history = - info.password_history; - state->response.data.auth.policy.password_properties = - info.password_properties; - state->response.data.auth.policy.expire = - nt_time_to_unix_abs(&info.expire); - state->response.data.auth.policy.min_passwordage = - nt_time_to_unix_abs(&info.min_passwordage); - - state->response.data.auth.reject_reason = - reject.reject_reason; + state->response.data.auth.policy.min_length_password = + info->min_password_length; + state->response.data.auth.policy.password_history = + info->password_history_length; + state->response.data.auth.policy.password_properties = + info->password_properties; + state->response.data.auth.policy.expire = + nt_time_to_unix_abs((NTTIME *)&info->max_password_age); + state->response.data.auth.policy.min_passwordage = + nt_time_to_unix_abs((NTTIME *)&info->min_password_age); + + state->response.data.auth.reject_reason = + reject->reason; got_info = True; } |