1
0
mirror of https://github.com/samba-team/samba.git synced 2025-11-04 00:23:49 +03:00

r1952: change the _RPC levels into _SAMR

because we may have other rpc levels in future

add more comments about what's going on

check the rsult of samr_OpenUser

metze
This commit is contained in:
Stefan Metzmacher
2004-08-20 10:22:22 +00:00
committed by Gerald (Jerry) Carter
parent b660e5b9e6
commit 741f95909b
2 changed files with 134 additions and 100 deletions

View File

@@ -79,7 +79,7 @@ union libnet_rpc_connect {
/* struct and enum for doing a remote password change */
enum libnet_ChangePassword_level {
LIBNET_CHANGE_PASSWORD_GENERIC,
LIBNET_CHANGE_PASSWORD_RPC,
LIBNET_CHANGE_PASSWORD_SAMR,
LIBNET_CHANGE_PASSWORD_KRB5,
LIBNET_CHANGE_PASSWORD_LDAP,
LIBNET_CHANGE_PASSWORD_RAP
@@ -105,7 +105,7 @@ union libnet_ChangePassword {
enum libnet_ChangePassword_level level;
struct _libnet_ChangePassword_in in;
struct _libnet_ChangePassword_out out;
} rpc;
} samr;
struct {
enum libnet_ChangePassword_level level;
@@ -129,7 +129,7 @@ union libnet_ChangePassword {
/* struct and enum for doing a remote password set */
enum libnet_SetPassword_level {
LIBNET_SET_PASSWORD_GENERIC,
LIBNET_SET_PASSWORD_RPC,
LIBNET_SET_PASSWORD_SAMR,
LIBNET_SET_PASSWORD_KRB5,
LIBNET_SET_PASSWORD_LDAP,
LIBNET_SET_PASSWORD_RAP
@@ -154,7 +154,7 @@ union libnet_SetPassword {
enum libnet_SetPassword_level level;
struct _libnet_SetPassword_in in;
struct _libnet_SetPassword_out out;
} rpc;
} samr;
struct {
enum libnet_SetPassword_level level;

View File

@@ -23,9 +23,12 @@
/*
* do a password change using DCERPC/SAMR calls
* 1. connect to the SAMR pipe of users domain PDC (maybe a standalone server or workstation)
* 2. try samr_ChangePassword3
* 2. try samr_ChangePasswordUser3
* 3. try samr_ChangePasswordUser2
* 4. try samr_OemChangePasswordUser2
* (not yet: 5. try samr_ChangePasswordUser)
*/
static NTSTATUS libnet_ChangePassword_rpc(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, union libnet_ChangePassword *r)
static NTSTATUS libnet_ChangePassword_samr(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, union libnet_ChangePassword *r)
{
NTSTATUS status;
union libnet_rpc_connect c;
@@ -44,37 +47,38 @@ static NTSTATUS libnet_ChangePassword_rpc(struct libnet_context *ctx, TALLOC_CTX
uint8_t old_nt_hash[16], new_nt_hash[16];
uint8_t old_lm_hash[16], new_lm_hash[16];
/* prepare connect to the SAMR pipe of the */
/* prepare connect to the SAMR pipe of the users domain PDC */
c.pdc.level = LIBNET_RPC_CONNECT_PDC;
c.pdc.in.domain_name = r->rpc.in.domain_name;
c.pdc.in.domain_name = r->samr.in.domain_name;
c.pdc.in.dcerpc_iface_name = DCERPC_SAMR_NAME;
c.pdc.in.dcerpc_iface_uuid = DCERPC_SAMR_UUID;
c.pdc.in.dcerpc_iface_version = DCERPC_SAMR_VERSION;
/* do connect to the SAMR pipe of the */
/* 1. connect to the SAMR pipe of users domain PDC (maybe a standalone server or workstation) */
status = libnet_rpc_connect(ctx, mem_ctx, &c);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"Connection to SAMR pipe of PDC of domain '%s' failed: %s\n",
r->rpc.in.domain_name, nt_errstr(status));
r->samr.in.domain_name, nt_errstr(status));
return status;
}
/* prepare password change for account */
server.name = talloc_asprintf(mem_ctx, "\\\\%s", dcerpc_server_name(c.pdc.out.dcerpc_pipe));
account.name = r->rpc.in.account_name;
account.name = r->samr.in.account_name;
E_md4hash(r->rpc.in.oldpassword, old_nt_hash);
E_md4hash(r->rpc.in.newpassword, new_nt_hash);
E_md4hash(r->samr.in.oldpassword, old_nt_hash);
E_md4hash(r->samr.in.newpassword, new_nt_hash);
E_deshash(r->rpc.in.oldpassword, old_lm_hash);
E_deshash(r->rpc.in.newpassword, new_lm_hash);
E_deshash(r->samr.in.oldpassword, old_lm_hash);
E_deshash(r->samr.in.newpassword, new_lm_hash);
encode_pw_buffer(lm_pass.data, r->rpc.in.newpassword, STR_UNICODE);
/* prepare samr_ChangePasswordUser3 */
encode_pw_buffer(lm_pass.data, r->samr.in.newpassword, STR_UNICODE);
arcfour_crypt(lm_pass.data, old_nt_hash, 516);
E_old_pw_hash(new_lm_hash, old_lm_hash, lm_verifier.hash);
encode_pw_buffer(nt_pass.data, r->rpc.in.newpassword, STR_UNICODE);
encode_pw_buffer(nt_pass.data, r->samr.in.newpassword, STR_UNICODE);
arcfour_crypt(nt_pass.data, old_nt_hash, 516);
E_old_pw_hash(new_nt_hash, old_nt_hash, nt_verifier.hash);
@@ -87,20 +91,20 @@ static NTSTATUS libnet_ChangePassword_rpc(struct libnet_context *ctx, TALLOC_CTX
pw3.in.lm_verifier = &lm_verifier;
pw3.in.password3 = NULL;
/* do password change for account */
/* 2. try samr_ChangePasswordUser3 */
status = dcerpc_samr_ChangePasswordUser3(c.pdc.out.dcerpc_pipe, mem_ctx, &pw3);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_ChangePasswordUser3 failed: %s\n",
nt_errstr(status));
goto ChangePasswordUser2;
}
/* check result of password change */
/* check result of samr_ChangePasswordUser3 */
if (!NT_STATUS_IS_OK(pw3.out.result)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_ChangePasswordUser3 for '%s\\%s' failed: %s\n",
r->rpc.in.domain_name, r->rpc.in.account_name,
r->samr.in.domain_name, r->samr.in.account_name,
nt_errstr(pw3.out.result));
/* TODO: give the reason of the reject */
if (NT_STATUS_EQUAL(status, NT_STATUS_PASSWORD_RESTRICTION)) {
@@ -112,12 +116,12 @@ static NTSTATUS libnet_ChangePassword_rpc(struct libnet_context *ctx, TALLOC_CTX
goto disconnect;
ChangePasswordUser2:
encode_pw_buffer(lm_pass.data, r->rpc.in.newpassword, STR_ASCII|STR_TERMINATE);
/* prepare samr_ChangePasswordUser2 */
encode_pw_buffer(lm_pass.data, r->samr.in.newpassword, STR_ASCII|STR_TERMINATE);
arcfour_crypt(lm_pass.data, old_lm_hash, 516);
E_old_pw_hash(new_lm_hash, old_lm_hash, lm_verifier.hash);
encode_pw_buffer(nt_pass.data, r->rpc.in.newpassword, STR_UNICODE);
encode_pw_buffer(nt_pass.data, r->samr.in.newpassword, STR_UNICODE);
arcfour_crypt(nt_pass.data, old_nt_hash, 516);
E_old_pw_hash(new_nt_hash, old_nt_hash, nt_verifier.hash);
@@ -129,19 +133,20 @@ ChangePasswordUser2:
pw2.in.lm_password = &lm_pass;
pw2.in.lm_verifier = &lm_verifier;
/* 3. try samr_ChangePasswordUser2 */
status = dcerpc_samr_ChangePasswordUser2(c.pdc.out.dcerpc_pipe, mem_ctx, &pw2);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_ChangePasswordUser2 failed: %s\n",
nt_errstr(status));
goto OemChangePasswordUser2;
}
/* check result of password change */
/* check result of samr_ChangePasswordUser2 */
if (!NT_STATUS_IS_OK(pw2.out.result)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_ChangePasswordUser2 for '%s\\%s' failed: %s\n",
r->rpc.in.domain_name, r->rpc.in.account_name,
r->samr.in.domain_name, r->samr.in.account_name,
nt_errstr(pw2.out.result));
goto OemChangePasswordUser2;
}
@@ -149,11 +154,11 @@ ChangePasswordUser2:
goto disconnect;
OemChangePasswordUser2:
/* prepare samr_OemChangePasswordUser2 */
a_server.name = talloc_asprintf(mem_ctx, "\\\\%s", dcerpc_server_name(c.pdc.out.dcerpc_pipe));
a_account.name = r->rpc.in.account_name;
a_account.name = r->samr.in.account_name;
encode_pw_buffer(lm_pass.data, r->rpc.in.newpassword, STR_ASCII);
encode_pw_buffer(lm_pass.data, r->samr.in.newpassword, STR_ASCII);
arcfour_crypt(lm_pass.data, old_lm_hash, 516);
E_old_pw_hash(new_lm_hash, old_lm_hash, lm_verifier.hash);
@@ -162,19 +167,20 @@ OemChangePasswordUser2:
oe2.in.password = &lm_pass;
oe2.in.hash = &lm_verifier;
/* 4. try samr_OemChangePasswordUser2 */
status = dcerpc_samr_OemChangePasswordUser2(c.pdc.out.dcerpc_pipe, mem_ctx, &oe2);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_OemChangePasswordUser2 failed: %s\n",
nt_errstr(status));
goto ChangePasswordUser;
}
/* check result of password change */
/* check result of samr_OemChangePasswordUser2 */
if (!NT_STATUS_IS_OK(oe2.out.result)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_OemChangePasswordUser2 for '%s\\%s' failed: %s\n",
r->rpc.in.domain_name, r->rpc.in.account_name,
r->samr.in.domain_name, r->samr.in.account_name,
nt_errstr(oe2.out.result));
goto ChangePasswordUser;
}
@@ -183,6 +189,7 @@ OemChangePasswordUser2:
ChangePasswordUser:
#if 0
/* prepare samr_ChangePasswordUser */
E_old_pw_hash(new_lm_hash, old_lm_hash, hash1.hash);
E_old_pw_hash(old_lm_hash, new_lm_hash, hash2.hash);
E_old_pw_hash(new_nt_hash, old_nt_hash, hash3.hash);
@@ -203,19 +210,20 @@ ChangePasswordUser:
pw.in.cross2_present = 1;
pw.in.lm_cross = &hash6;
/* 5. try samr_ChangePasswordUser */
status = dcerpc_samr_ChangePasswordUser(c.pdc.out.dcerpc_pipe, mem_ctx, &pw);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_ChangePasswordUser failed: %s\n",
nt_errstr(status));
goto disconnect;
}
/* check result of password change */
/* check result of samr_ChangePasswordUser */
if (!NT_STATUS_IS_OK(pw.out.result)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_ChangePasswordUser for '%s\\%s' failed: %s\n",
r->rpc.in.domain_name, r->rpc.in.account_name,
r->samr.in.domain_name, r->samr.in.account_name,
nt_errstr(pw.out.result));
goto disconnect;
}
@@ -232,15 +240,15 @@ static NTSTATUS libnet_ChangePassword_generic(struct libnet_context *ctx, TALLOC
NTSTATUS status;
union libnet_ChangePassword r2;
r2.rpc.level = LIBNET_CHANGE_PASSWORD_RPC;
r2.rpc.in.account_name = r->generic.in.account_name;
r2.rpc.in.domain_name = r->generic.in.domain_name;
r2.rpc.in.oldpassword = r->generic.in.oldpassword;
r2.rpc.in.newpassword = r->generic.in.newpassword;
r2.samr.level = LIBNET_CHANGE_PASSWORD_SAMR;
r2.samr.in.account_name = r->generic.in.account_name;
r2.samr.in.domain_name = r->generic.in.domain_name;
r2.samr.in.oldpassword = r->generic.in.oldpassword;
r2.samr.in.newpassword = r->generic.in.newpassword;
status = libnet_ChangePassword(ctx, mem_ctx, &r2);
r->generic.out.error_string = r2.rpc.out.error_string;
r->generic.out.error_string = r2.samr.out.error_string;
return status;
}
@@ -250,8 +258,8 @@ NTSTATUS libnet_ChangePassword(struct libnet_context *ctx, TALLOC_CTX *mem_ctx,
switch (r->generic.level) {
case LIBNET_CHANGE_PASSWORD_GENERIC:
return libnet_ChangePassword_generic(ctx, mem_ctx, r);
case LIBNET_CHANGE_PASSWORD_RPC:
return libnet_ChangePassword_rpc(ctx, mem_ctx, r);
case LIBNET_CHANGE_PASSWORD_SAMR:
return libnet_ChangePassword_samr(ctx, mem_ctx, r);
case LIBNET_CHANGE_PASSWORD_KRB5:
return NT_STATUS_NOT_IMPLEMENTED;
case LIBNET_CHANGE_PASSWORD_LDAP:
@@ -265,10 +273,16 @@ NTSTATUS libnet_ChangePassword(struct libnet_context *ctx, TALLOC_CTX *mem_ctx,
/*
* set a password with DCERPC/SAMR calls
*
* is it correct to contact the the pdc of the domain of the user who's password should be set?
* 1. connect to the SAMR pipe of users domain PDC (maybe a standalone server or workstation)
* is it correct to contact the the pdc of the domain of the user who's password should be set?
* 2. do a samr_Connect to get a policy handle
* 3. do a samr_LookupDomain to get the domain sid
* 4. do a samr_OpenDomain to get a domain handle
* 5. do a samr_LookupNames to get the users rid
* 6. do a samr_OpenUser to get a user handle
* 7. try samr_SetUserInfo level 26 to set the password
*/
static NTSTATUS libnet_SetPassword_rpc(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, union libnet_SetPassword *r)
static NTSTATUS libnet_SetPassword_samr(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, union libnet_SetPassword *r)
{
NTSTATUS status;
union libnet_rpc_connect c;
@@ -288,138 +302,157 @@ static NTSTATUS libnet_SetPassword_rpc(struct libnet_context *ctx, TALLOC_CTX *m
uint8_t confounder[16];
struct MD5Context md5;
/* prepare connect to the SAMR pipe of the */
/* prepare connect to the SAMR pipe of users domain PDC */
c.pdc.level = LIBNET_RPC_CONNECT_PDC;
c.pdc.in.domain_name = r->rpc.in.domain_name;
c.pdc.in.domain_name = r->samr.in.domain_name;
c.pdc.in.dcerpc_iface_name = DCERPC_SAMR_NAME;
c.pdc.in.dcerpc_iface_uuid = DCERPC_SAMR_UUID;
c.pdc.in.dcerpc_iface_version = DCERPC_SAMR_VERSION;
/* do connect to the SAMR pipe of the */
/* 1. connect to the SAMR pipe of users domain PDC (maybe a standalone server or workstation) */
status = libnet_rpc_connect(ctx, mem_ctx, &c);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"Connection to SAMR pipe of PDC of domain '%s' failed: %s\n",
r->rpc.in.domain_name, nt_errstr(status));
r->samr.in.domain_name, nt_errstr(status));
return status;
}
/* do a samr_Connect to get a policy handle */
/* prepare samr_Connect */
ZERO_STRUCT(p_handle);
sc.in.system_name = 0;
sc.in.access_mask = SEC_RIGHTS_MAXIMUM_ALLOWED;
sc.out.handle = &p_handle;
/* 2. do a samr_Connect to get a policy handle */
status = dcerpc_samr_Connect(c.pdc.out.dcerpc_pipe, mem_ctx, &sc);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_Connect failed: %s\n",
nt_errstr(status));
goto disconnect;
}
/* check result of samr_connect */
/* check result of samr_Connect */
if (!NT_STATUS_IS_OK(sc.out.result)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_Connect failed: %s\n",
nt_errstr(sc.out.result));
goto disconnect;
}
/* do a samr_LookupDomain */
d_name.name = r->rpc.in.domain_name;
/* prepare samr_LookupDomain */
d_name.name = r->samr.in.domain_name;
ld.in.handle = &p_handle;
ld.in.domain = &d_name;
/* 3. do a samr_LookupDomain to get the domain sid */
status = dcerpc_samr_LookupDomain(c.pdc.out.dcerpc_pipe, mem_ctx, &ld);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_LookupDomain for [%s] failed: %s\n",
r->rpc.in.domain_name, nt_errstr(status));
r->samr.in.domain_name, nt_errstr(status));
goto disconnect;
}
/* check result of samr_LookupDomain */
if (!NT_STATUS_IS_OK(ld.out.result)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_LookupDomain for [%s] failed: %s\n",
r->rpc.in.domain_name, nt_errstr(ld.out.result));
r->samr.in.domain_name, nt_errstr(ld.out.result));
goto disconnect;
}
/* do a samr_OpenDomain to get a domain handle */
/* prepare samr_OpenDomain */
ZERO_STRUCT(d_handle);
od.in.handle = &p_handle;
od.in.access_mask = SEC_RIGHTS_MAXIMUM_ALLOWED;
od.in.sid = ld.out.sid;
od.out.domain_handle = &d_handle;
/* 4. do a samr_OpenDomain to get a domain handle */
status = dcerpc_samr_OpenDomain(c.pdc.out.dcerpc_pipe, mem_ctx, &od);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_OpenDomain for [%s] failed: %s\n",
r->rpc.in.domain_name, nt_errstr(status));
r->samr.in.domain_name, nt_errstr(status));
goto disconnect;
}
/* check result of samr_LookupDomain */
/* check result of samr_OpenDomain */
if (!NT_STATUS_IS_OK(od.out.result)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_OpenDomain for [%s] failed: %s\n",
r->rpc.in.domain_name, nt_errstr(od.out.result));
r->samr.in.domain_name, nt_errstr(od.out.result));
goto disconnect;
}
/* do a samr_LookupNames for the account_name to get the RID */
/* prepare samr_LookupNames */
ln.in.handle = &d_handle;
ln.in.num_names = 1;
ln.in.names = talloc_array_p(mem_ctx, struct samr_Name, 1);
if (!ln.in.names) {
r->rpc.out.error_string = "Out of Memory";
r->samr.out.error_string = "Out of Memory";
return NT_STATUS_NO_MEMORY;
}
ln.in.names[0].name = r->rpc.in.account_name;
ln.in.names[0].name = r->samr.in.account_name;
/* 5. do a samr_LookupNames to get the users rid */
status = dcerpc_samr_LookupNames(c.pdc.out.dcerpc_pipe, mem_ctx, &ln);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_LookupNames for [%s] failed: %s\n",
r->rpc.in.account_name, nt_errstr(status));
r->samr.in.account_name, nt_errstr(status));
goto disconnect;
}
/* check result of samr_LookupDomain */
/* check result of samr_LookupNames */
if (!NT_STATUS_IS_OK(ln.out.result)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_LookupNames for [%s] failed: %s\n",
r->rpc.in.account_name, nt_errstr(ln.out.result));
r->samr.in.account_name, nt_errstr(ln.out.result));
goto disconnect;
}
/* check if we got one RID for the user */
if (ln.out.rids.count != 1) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_LookupNames for [%s] returns %d RIDs\n",
r->rpc.in.account_name, ln.out.rids.count);
r->samr.in.account_name, ln.out.rids.count);
goto disconnect;
}
/* do samr_OpenUser to get the user handle */
/* prepare samr_OpenUser */
ZERO_STRUCT(u_handle);
ou.in.handle = &d_handle;
ou.in.access_mask = SEC_RIGHTS_MAXIMUM_ALLOWED;
ou.in.rid = ln.out.rids.ids[0];
ou.out.acct_handle = &u_handle;
/* 6. do a samr_OpenUser to get a user handle */
status = dcerpc_samr_OpenUser(c.pdc.out.dcerpc_pipe, mem_ctx, &ou);
if (!NT_STATUS_IS_OK(status)) {
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_OpenUser for [%s] failed: %s\n",
r->samr.in.account_name, nt_errstr(status));
goto disconnect;
}
/* prepare password set with samr_UserInfo26 */
encode_pw_buffer(u_info.info26.password.data, r->rpc.in.newpassword, STR_UNICODE);
u_info.info26.pw_len = strlen(r->rpc.in.newpassword);
/* check result of samr_OpenUser */
if (!NT_STATUS_IS_OK(ou.out.result)) {
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"samr_OpenUser for [%s] failed: %s\n",
r->samr.in.account_name, nt_errstr(ou.out.result));
goto disconnect;
}
/* prepare samr_SetUserInfo level 26 */
encode_pw_buffer(u_info.info26.password.data, r->samr.in.newpassword, STR_UNICODE);
u_info.info26.pw_len = strlen(r->samr.in.newpassword);
status = dcerpc_fetch_session_key(c.pdc.out.dcerpc_pipe, &session_key);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"dcerpc_fetch_session_key failed: %s\n",
nt_errstr(status));
goto disconnect;
@@ -439,19 +472,20 @@ static NTSTATUS libnet_SetPassword_rpc(struct libnet_context *ctx, TALLOC_CTX *m
sui.in.info = &u_info;
sui.in.level = 26;
/* 7. try samr_SetUserInfo level 26 to set the password */
status = dcerpc_samr_SetUserInfo(c.pdc.out.dcerpc_pipe, mem_ctx, &sui);
if (!NT_STATUS_IS_OK(status)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"SetUserInfo level 26 for [%s] failed: %s\n",
r->rpc.in.account_name, nt_errstr(status));
r->samr.in.account_name, nt_errstr(status));
goto UserInfo25;
}
/* check result of samr_LookupDomain */
/* check result of samr_SetUserInfo level 26 */
if (!NT_STATUS_IS_OK(sui.out.result)) {
r->rpc.out.error_string = talloc_asprintf(mem_ctx,
r->samr.out.error_string = talloc_asprintf(mem_ctx,
"SetUserInfo level 26 for [%s] failed: %s\n",
r->rpc.in.account_name, nt_errstr(sui.out.result));
r->samr.in.account_name, nt_errstr(sui.out.result));
goto UserInfo25;
}
@@ -469,14 +503,14 @@ static NTSTATUS libnet_SetPassword_generic(struct libnet_context *ctx, TALLOC_CT
NTSTATUS status;
union libnet_SetPassword r2;
r2.rpc.level = LIBNET_SET_PASSWORD_RPC;
r2.rpc.in.account_name = r->generic.in.account_name;
r2.rpc.in.domain_name = r->generic.in.domain_name;
r2.rpc.in.newpassword = r->generic.in.newpassword;
r2.samr.level = LIBNET_SET_PASSWORD_SAMR;
r2.samr.in.account_name = r->generic.in.account_name;
r2.samr.in.domain_name = r->generic.in.domain_name;
r2.samr.in.newpassword = r->generic.in.newpassword;
status = libnet_SetPassword(ctx, mem_ctx, &r2);
r->generic.out.error_string = r2.rpc.out.error_string;
r->generic.out.error_string = r2.samr.out.error_string;
return status;
}
@@ -486,8 +520,8 @@ NTSTATUS libnet_SetPassword(struct libnet_context *ctx, TALLOC_CTX *mem_ctx, uni
switch (r->generic.level) {
case LIBNET_SET_PASSWORD_GENERIC:
return libnet_SetPassword_generic(ctx, mem_ctx, r);
case LIBNET_SET_PASSWORD_RPC:
return libnet_SetPassword_rpc(ctx, mem_ctx, r);
case LIBNET_SET_PASSWORD_SAMR:
return libnet_SetPassword_samr(ctx, mem_ctx, r);
case LIBNET_SET_PASSWORD_KRB5:
return NT_STATUS_NOT_IMPLEMENTED;
case LIBNET_SET_PASSWORD_LDAP: