2 Unix SMB/CIFS implementation.
3 test suite for samr rpc operations
5 Copyright (C) Andrew Tridgell 2003
6 Copyright (C) Andrew Bartlett <abartlet@samba.org> 2003
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
24 #include "librpc/gen_ndr/ndr_lsa.h"
25 #include "librpc/gen_ndr/ndr_samr.h"
26 #include "lib/crypto/crypto.h"
28 #define TEST_ACCOUNT_NAME "samrtorturetest"
29 #define TEST_ALIASNAME "samrtorturetestalias"
30 #define TEST_GROUPNAME "samrtorturetestgroup"
31 #define TEST_MACHINENAME "samrtestmach$"
32 #define TEST_DOMAINNAME "samrtestdom$"
35 static BOOL test_QueryUserInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
36 struct policy_handle *handle);
38 static BOOL test_QueryUserInfo2(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
39 struct policy_handle *handle);
41 static BOOL test_QueryAliasInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
42 struct policy_handle *handle);
44 static void init_samr_String(struct samr_String *string, const char *s)
49 BOOL test_samr_handle_Close(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
50 struct policy_handle *handle)
56 r.out.handle = handle;
58 status = dcerpc_samr_Close(p, mem_ctx, &r);
59 if (!NT_STATUS_IS_OK(status)) {
60 printf("Close handle failed - %s\n", nt_errstr(status));
67 static BOOL test_Shutdown(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
68 struct policy_handle *handle)
71 struct samr_Shutdown r;
73 if (!lp_parm_bool(-1, "torture", "dangerous", False)) {
74 printf("samr_Shutdown disabled - enable dangerous tests to use\n");
78 r.in.connect_handle = handle;
80 printf("testing samr_Shutdown\n");
82 status = dcerpc_samr_Shutdown(p, mem_ctx, &r);
83 if (!NT_STATUS_IS_OK(status)) {
84 printf("samr_Shutdown failed - %s\n", nt_errstr(status));
91 static BOOL test_SetDsrmPassword(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
92 struct policy_handle *handle)
95 struct samr_SetDsrmPassword r;
96 struct samr_String string;
97 struct samr_Password hash;
99 if (!lp_parm_bool(-1, "torture", "dangerous", False)) {
100 printf("samr_SetDsrmPassword disabled - enable dangerous tests to use\n");
104 E_md4hash("TeSTDSRM123", hash.hash);
106 init_samr_String(&string, "Administrator");
112 printf("testing samr_SetDsrmPassword\n");
114 status = dcerpc_samr_SetDsrmPassword(p, mem_ctx, &r);
115 if (!NT_STATUS_EQUAL(status, NT_STATUS_NOT_SUPPORTED)) {
116 printf("samr_SetDsrmPassword failed - %s\n", nt_errstr(status));
124 static BOOL test_QuerySecurity(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
125 struct policy_handle *handle)
128 struct samr_QuerySecurity r;
129 struct samr_SetSecurity s;
131 r.in.handle = handle;
134 status = dcerpc_samr_QuerySecurity(p, mem_ctx, &r);
135 if (!NT_STATUS_IS_OK(status)) {
136 printf("QuerySecurity failed - %s\n", nt_errstr(status));
140 if (r.out.sdbuf == NULL) {
144 s.in.handle = handle;
146 s.in.sdbuf = r.out.sdbuf;
148 status = dcerpc_samr_SetSecurity(p, mem_ctx, &s);
149 if (!NT_STATUS_IS_OK(status)) {
150 printf("SetSecurity failed - %s\n", nt_errstr(status));
154 status = dcerpc_samr_QuerySecurity(p, mem_ctx, &r);
155 if (!NT_STATUS_IS_OK(status)) {
156 printf("QuerySecurity failed - %s\n", nt_errstr(status));
164 static BOOL test_SetUserInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
165 struct policy_handle *handle, uint32_t base_acct_flags,
166 const char *base_account_name)
169 struct samr_SetUserInfo s;
170 struct samr_SetUserInfo2 s2;
171 struct samr_QueryUserInfo q;
172 struct samr_QueryUserInfo q0;
173 union samr_UserInfo u;
175 const char *test_account_name;
177 uint32_t user_extra_flags = 0;
178 if (base_acct_flags == ACB_NORMAL) {
179 /* Don't know what this is, but it is always here for users - you can't get rid of it */
180 user_extra_flags = 0x20000;
183 s.in.user_handle = handle;
186 s2.in.user_handle = handle;
189 q.in.user_handle = handle;
193 #define TESTCALL(call, r) \
194 status = dcerpc_samr_ ##call(p, mem_ctx, &r); \
195 if (!NT_STATUS_IS_OK(status)) { \
196 printf(#call " level %u failed - %s (%s)\n", \
197 r.in.level, nt_errstr(status), __location__); \
202 #define STRING_EQUAL(s1, s2, field) \
203 if ((s1 && !s2) || (s2 && !s1) || strcmp(s1, s2)) { \
204 printf("Failed to set %s to '%s' (%s)\n", \
205 #field, s2, __location__); \
210 #define INT_EQUAL(i1, i2, field) \
212 printf("Failed to set %s to 0x%x - got 0x%x (%s)\n", \
213 #field, i2, i1, __location__); \
218 #define TEST_USERINFO_STRING(lvl1, field1, lvl2, field2, value, fpval) do { \
219 printf("field test %d/%s vs %d/%s\n", lvl1, #field1, lvl2, #field2); \
221 TESTCALL(QueryUserInfo, q) \
223 s2.in.level = lvl1; \
226 ZERO_STRUCT(u.info21); \
227 u.info21.fields_present = fpval; \
229 init_samr_String(&u.info ## lvl1.field1, value); \
230 TESTCALL(SetUserInfo, s) \
231 TESTCALL(SetUserInfo2, s2) \
232 init_samr_String(&u.info ## lvl1.field1, ""); \
233 TESTCALL(QueryUserInfo, q); \
235 STRING_EQUAL(u.info ## lvl1.field1.string, value, field1); \
237 TESTCALL(QueryUserInfo, q) \
239 STRING_EQUAL(u.info ## lvl2.field2.string, value, field2); \
242 #define TEST_USERINFO_INT_EXP(lvl1, field1, lvl2, field2, value, exp_value, fpval) do { \
243 printf("field test %d/%s vs %d/%s\n", lvl1, #field1, lvl2, #field2); \
245 TESTCALL(QueryUserInfo, q) \
247 s2.in.level = lvl1; \
250 uint8_t *bits = u.info21.logon_hours.bits; \
251 ZERO_STRUCT(u.info21); \
252 if (fpval == SAMR_FIELD_LOGON_HOURS) { \
253 u.info21.logon_hours.units_per_week = 168; \
254 u.info21.logon_hours.bits = bits; \
256 u.info21.fields_present = fpval; \
258 u.info ## lvl1.field1 = value; \
259 TESTCALL(SetUserInfo, s) \
260 TESTCALL(SetUserInfo2, s2) \
261 u.info ## lvl1.field1 = 0; \
262 TESTCALL(QueryUserInfo, q); \
264 INT_EQUAL(u.info ## lvl1.field1, exp_value, field1); \
266 TESTCALL(QueryUserInfo, q) \
268 INT_EQUAL(u.info ## lvl2.field2, exp_value, field1); \
271 #define TEST_USERINFO_INT(lvl1, field1, lvl2, field2, value, fpval) do { \
272 TEST_USERINFO_INT_EXP(lvl1, field1, lvl2, field2, value, value, fpval); \
276 do { TESTCALL(QueryUserInfo, q0) } while (0);
278 TEST_USERINFO_STRING(2, comment, 1, comment, "xx2-1 comment", 0);
279 TEST_USERINFO_STRING(2, comment, 21, comment, "xx2-21 comment", 0);
280 TEST_USERINFO_STRING(21, comment, 21, comment, "xx21-21 comment",
283 test_account_name = talloc_asprintf(mem_ctx, "%sxx7-1", base_account_name);
284 TEST_USERINFO_STRING(7, account_name, 1, account_name, base_account_name, 0);
285 test_account_name = talloc_asprintf(mem_ctx, "%sxx7-3", base_account_name);
286 TEST_USERINFO_STRING(7, account_name, 3, account_name, base_account_name, 0);
287 test_account_name = talloc_asprintf(mem_ctx, "%sxx7-5", base_account_name);
288 TEST_USERINFO_STRING(7, account_name, 5, account_name, base_account_name, 0);
289 test_account_name = talloc_asprintf(mem_ctx, "%sxx7-6", base_account_name);
290 TEST_USERINFO_STRING(7, account_name, 6, account_name, base_account_name, 0);
291 test_account_name = talloc_asprintf(mem_ctx, "%sxx7-7", base_account_name);
292 TEST_USERINFO_STRING(7, account_name, 7, account_name, base_account_name, 0);
293 test_account_name = talloc_asprintf(mem_ctx, "%sxx7-21", base_account_name);
294 TEST_USERINFO_STRING(7, account_name, 21, account_name, base_account_name, 0);
295 test_account_name = base_account_name;
296 TEST_USERINFO_STRING(21, account_name, 21, account_name, base_account_name,
297 SAMR_FIELD_ACCOUNT_NAME);
299 TEST_USERINFO_STRING(6, full_name, 1, full_name, "xx6-1 full_name", 0);
300 TEST_USERINFO_STRING(6, full_name, 3, full_name, "xx6-3 full_name", 0);
301 TEST_USERINFO_STRING(6, full_name, 5, full_name, "xx6-5 full_name", 0);
302 TEST_USERINFO_STRING(6, full_name, 6, full_name, "xx6-6 full_name", 0);
303 TEST_USERINFO_STRING(6, full_name, 8, full_name, "xx6-8 full_name", 0);
304 TEST_USERINFO_STRING(6, full_name, 21, full_name, "xx6-21 full_name", 0);
305 TEST_USERINFO_STRING(8, full_name, 21, full_name, "xx8-21 full_name", 0);
306 TEST_USERINFO_STRING(21, full_name, 21, full_name, "xx21-21 full_name",
307 SAMR_FIELD_FULL_NAME);
309 TEST_USERINFO_STRING(11, logon_script, 3, logon_script, "xx11-3 logon_script", 0);
310 TEST_USERINFO_STRING(11, logon_script, 5, logon_script, "xx11-5 logon_script", 0);
311 TEST_USERINFO_STRING(11, logon_script, 21, logon_script, "xx11-21 logon_script", 0);
312 TEST_USERINFO_STRING(21, logon_script, 21, logon_script, "xx21-21 logon_script",
313 SAMR_FIELD_LOGON_SCRIPT);
315 TEST_USERINFO_STRING(12, profile_path, 3, profile_path, "xx12-3 profile_path", 0);
316 TEST_USERINFO_STRING(12, profile_path, 5, profile_path, "xx12-5 profile_path", 0);
317 TEST_USERINFO_STRING(12, profile_path, 21, profile_path, "xx12-21 profile_path", 0);
318 TEST_USERINFO_STRING(21, profile_path, 21, profile_path, "xx21-21 profile_path",
319 SAMR_FIELD_PROFILE_PATH);
321 TEST_USERINFO_STRING(13, description, 1, description, "xx13-1 description", 0);
322 TEST_USERINFO_STRING(13, description, 5, description, "xx13-5 description", 0);
323 TEST_USERINFO_STRING(13, description, 21, description, "xx13-21 description", 0);
324 TEST_USERINFO_STRING(21, description, 21, description, "xx21-21 description",
325 SAMR_FIELD_DESCRIPTION);
327 TEST_USERINFO_STRING(14, workstations, 3, workstations, "14workstation3", 0);
328 TEST_USERINFO_STRING(14, workstations, 5, workstations, "14workstation4", 0);
329 TEST_USERINFO_STRING(14, workstations, 21, workstations, "14workstation21", 0);
330 TEST_USERINFO_STRING(21, workstations, 21, workstations, "21workstation21",
331 SAMR_FIELD_WORKSTATIONS);
333 TEST_USERINFO_STRING(20, parameters, 21, parameters, "xx20-21 parameters", 0);
334 TEST_USERINFO_STRING(21, parameters, 21, parameters, "xx21-21 parameters",
335 SAMR_FIELD_PARAMETERS);
337 TEST_USERINFO_INT(2, country_code, 21, country_code, __LINE__, 0);
338 TEST_USERINFO_INT(21, country_code, 21, country_code, __LINE__,
339 SAMR_FIELD_COUNTRY_CODE);
341 TEST_USERINFO_INT(2, code_page, 21, code_page, __LINE__, 0);
342 TEST_USERINFO_INT(21, code_page, 21, code_page, __LINE__,
343 SAMR_FIELD_CODE_PAGE);
345 TEST_USERINFO_INT(4, logon_hours.bits[3], 3, logon_hours.bits[3], 1, 0);
346 TEST_USERINFO_INT(4, logon_hours.bits[3], 5, logon_hours.bits[3], 2, 0);
347 TEST_USERINFO_INT(4, logon_hours.bits[3], 21, logon_hours.bits[3], 3, 0);
348 TEST_USERINFO_INT(21, logon_hours.bits[3], 21, logon_hours.bits[3], 4,
349 SAMR_FIELD_LOGON_HOURS);
351 TEST_USERINFO_INT_EXP(16, acct_flags, 5, acct_flags,
352 (base_acct_flags | ACB_DISABLED | ACB_HOMDIRREQ),
353 (base_acct_flags | ACB_DISABLED | ACB_HOMDIRREQ | user_extra_flags),
355 TEST_USERINFO_INT_EXP(16, acct_flags, 5, acct_flags,
356 (base_acct_flags | ACB_DISABLED),
357 (base_acct_flags | ACB_DISABLED | user_extra_flags),
360 /* Setting PWNOEXP clears the magic 0x20000 flag */
361 TEST_USERINFO_INT_EXP(16, acct_flags, 5, acct_flags,
362 (base_acct_flags | ACB_DISABLED | ACB_PWNOEXP),
363 (base_acct_flags | ACB_DISABLED | ACB_PWNOEXP),
365 TEST_USERINFO_INT_EXP(16, acct_flags, 21, acct_flags,
366 (base_acct_flags | ACB_DISABLED | ACB_HOMDIRREQ),
367 (base_acct_flags | ACB_DISABLED | ACB_HOMDIRREQ | user_extra_flags),
370 /* The 'autolock' flag doesn't stick - check this */
371 TEST_USERINFO_INT_EXP(16, acct_flags, 21, acct_flags,
372 (base_acct_flags | ACB_DISABLED | ACB_AUTOLOCK),
373 (base_acct_flags | ACB_DISABLED | user_extra_flags),
375 TEST_USERINFO_INT_EXP(21, acct_flags, 21, acct_flags,
376 (base_acct_flags | ACB_DISABLED),
377 (base_acct_flags | ACB_DISABLED | user_extra_flags),
378 SAMR_FIELD_ACCT_FLAGS);
381 /* these fail with win2003 - it appears you can't set the primary gid?
382 the set succeeds, but the gid isn't changed. Very weird! */
383 TEST_USERINFO_INT(9, primary_gid, 1, primary_gid, 513);
384 TEST_USERINFO_INT(9, primary_gid, 3, primary_gid, 513);
385 TEST_USERINFO_INT(9, primary_gid, 5, primary_gid, 513);
386 TEST_USERINFO_INT(9, primary_gid, 21, primary_gid, 513);
393 generate a random password for password change tests
395 static char *samr_rand_pass(TALLOC_CTX *mem_ctx, int min_len)
397 size_t len = MAX(8, min_len) + (random() % 6);
398 char *s = generate_random_str(mem_ctx, len);
399 printf("Generated password '%s'\n", s);
403 static BOOL test_SetUserPass(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
404 struct policy_handle *handle, char **password)
407 struct samr_SetUserInfo s;
408 union samr_UserInfo u;
410 DATA_BLOB session_key;
412 struct samr_GetUserPwInfo pwp;
413 int policy_min_pw_len = 0;
414 pwp.in.user_handle = handle;
416 status = dcerpc_samr_GetUserPwInfo(p, mem_ctx, &pwp);
417 if (NT_STATUS_IS_OK(status)) {
418 policy_min_pw_len = pwp.out.info.min_password_length;
420 newpass = samr_rand_pass(mem_ctx, policy_min_pw_len);
422 s.in.user_handle = handle;
426 encode_pw_buffer(u.info24.password.data, newpass, STR_UNICODE);
427 /* w2k3 ignores this length */
428 u.info24.pw_len = strlen_m(newpass) * 2;
430 status = dcerpc_fetch_session_key(p, &session_key);
431 if (!NT_STATUS_IS_OK(status)) {
432 printf("SetUserInfo level %u - no session key - %s\n",
433 s.in.level, nt_errstr(status));
437 arcfour_crypt_blob(u.info24.password.data, 516, &session_key);
439 printf("Testing SetUserInfo level 24 (set password)\n");
441 status = dcerpc_samr_SetUserInfo(p, mem_ctx, &s);
442 if (!NT_STATUS_IS_OK(status)) {
443 printf("SetUserInfo level %u failed - %s\n",
444 s.in.level, nt_errstr(status));
454 static BOOL test_SetUserPass_23(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
455 struct policy_handle *handle, uint32_t fields_present,
459 struct samr_SetUserInfo s;
460 union samr_UserInfo u;
462 DATA_BLOB session_key;
464 struct samr_GetUserPwInfo pwp;
465 int policy_min_pw_len = 0;
466 pwp.in.user_handle = handle;
468 status = dcerpc_samr_GetUserPwInfo(p, mem_ctx, &pwp);
469 if (NT_STATUS_IS_OK(status)) {
470 policy_min_pw_len = pwp.out.info.min_password_length;
472 newpass = samr_rand_pass(mem_ctx, policy_min_pw_len);
474 s.in.user_handle = handle;
480 u.info23.info.fields_present = fields_present;
482 encode_pw_buffer(u.info23.password.data, newpass, STR_UNICODE);
484 status = dcerpc_fetch_session_key(p, &session_key);
485 if (!NT_STATUS_IS_OK(status)) {
486 printf("SetUserInfo level %u - no session key - %s\n",
487 s.in.level, nt_errstr(status));
491 arcfour_crypt_blob(u.info23.password.data, 516, &session_key);
493 printf("Testing SetUserInfo level 23 (set password)\n");
495 status = dcerpc_samr_SetUserInfo(p, mem_ctx, &s);
496 if (!NT_STATUS_IS_OK(status)) {
497 printf("SetUserInfo level %u failed - %s\n",
498 s.in.level, nt_errstr(status));
508 static BOOL test_SetUserPassEx(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
509 struct policy_handle *handle, char **password)
512 struct samr_SetUserInfo s;
513 union samr_UserInfo u;
515 DATA_BLOB session_key;
516 DATA_BLOB confounded_session_key = data_blob_talloc(mem_ctx, NULL, 16);
517 uint8_t confounder[16];
519 struct MD5Context ctx;
520 struct samr_GetUserPwInfo pwp;
521 int policy_min_pw_len = 0;
522 pwp.in.user_handle = handle;
524 status = dcerpc_samr_GetUserPwInfo(p, mem_ctx, &pwp);
525 if (NT_STATUS_IS_OK(status)) {
526 policy_min_pw_len = pwp.out.info.min_password_length;
528 newpass = samr_rand_pass(mem_ctx, policy_min_pw_len);
530 s.in.user_handle = handle;
534 encode_pw_buffer(u.info26.password.data, newpass, STR_UNICODE);
535 u.info26.pw_len = strlen(newpass);
537 status = dcerpc_fetch_session_key(p, &session_key);
538 if (!NT_STATUS_IS_OK(status)) {
539 printf("SetUserInfo level %u - no session key - %s\n",
540 s.in.level, nt_errstr(status));
544 generate_random_buffer((uint8_t *)confounder, 16);
547 MD5Update(&ctx, confounder, 16);
548 MD5Update(&ctx, session_key.data, session_key.length);
549 MD5Final(confounded_session_key.data, &ctx);
551 arcfour_crypt_blob(u.info26.password.data, 516, &confounded_session_key);
552 memcpy(&u.info26.password.data[516], confounder, 16);
554 printf("Testing SetUserInfo level 26 (set password ex)\n");
556 status = dcerpc_samr_SetUserInfo(p, mem_ctx, &s);
557 if (!NT_STATUS_IS_OK(status)) {
558 printf("SetUserInfo level %u failed - %s\n",
559 s.in.level, nt_errstr(status));
568 static BOOL test_SetUserPass_25(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
569 struct policy_handle *handle, uint32_t fields_present,
573 struct samr_SetUserInfo s;
574 union samr_UserInfo u;
576 DATA_BLOB session_key;
577 DATA_BLOB confounded_session_key = data_blob_talloc(mem_ctx, NULL, 16);
578 struct MD5Context ctx;
579 uint8_t confounder[16];
581 struct samr_GetUserPwInfo pwp;
582 int policy_min_pw_len = 0;
583 pwp.in.user_handle = handle;
585 status = dcerpc_samr_GetUserPwInfo(p, mem_ctx, &pwp);
586 if (NT_STATUS_IS_OK(status)) {
587 policy_min_pw_len = pwp.out.info.min_password_length;
589 newpass = samr_rand_pass(mem_ctx, policy_min_pw_len);
591 s.in.user_handle = handle;
597 u.info25.info.fields_present = fields_present;
599 encode_pw_buffer(u.info25.password.data, newpass, STR_UNICODE);
601 status = dcerpc_fetch_session_key(p, &session_key);
602 if (!NT_STATUS_IS_OK(status)) {
603 printf("SetUserInfo level %u - no session key - %s\n",
604 s.in.level, nt_errstr(status));
608 generate_random_buffer((uint8_t *)confounder, 16);
611 MD5Update(&ctx, confounder, 16);
612 MD5Update(&ctx, session_key.data, session_key.length);
613 MD5Final(confounded_session_key.data, &ctx);
615 arcfour_crypt_blob(u.info25.password.data, 516, &confounded_session_key);
616 memcpy(&u.info25.password.data[516], confounder, 16);
618 printf("Testing SetUserInfo level 25 (set password ex)\n");
620 status = dcerpc_samr_SetUserInfo(p, mem_ctx, &s);
621 if (!NT_STATUS_IS_OK(status)) {
622 printf("SetUserInfo level %u failed - %s\n",
623 s.in.level, nt_errstr(status));
632 static BOOL test_SetAliasInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
633 struct policy_handle *handle)
636 struct samr_SetAliasInfo r;
637 struct samr_QueryAliasInfo q;
638 uint16_t levels[] = {2, 3};
642 /* Ignoring switch level 1, as that includes the number of members for the alias
643 * and setting this to a wrong value might have negative consequences
646 for (i=0;i<ARRAY_SIZE(levels);i++) {
647 printf("Testing SetAliasInfo level %u\n", levels[i]);
649 r.in.alias_handle = handle;
650 r.in.level = levels[i];
651 r.in.info = talloc(mem_ctx, union samr_AliasInfo);
652 switch (r.in.level) {
653 case 2 : init_samr_String(&r.in.info->name,TEST_ALIASNAME); break;
654 case 3 : init_samr_String(&r.in.info->description,
655 "Test Description, should test I18N as well"); break;
658 status = dcerpc_samr_SetAliasInfo(p, mem_ctx, &r);
659 if (!NT_STATUS_IS_OK(status)) {
660 printf("SetAliasInfo level %u failed - %s\n",
661 levels[i], nt_errstr(status));
665 q.in.alias_handle = handle;
666 q.in.level = levels[i];
668 status = dcerpc_samr_QueryAliasInfo(p, mem_ctx, &q);
669 if (!NT_STATUS_IS_OK(status)) {
670 printf("QueryAliasInfo level %u failed - %s\n",
671 levels[i], nt_errstr(status));
679 static BOOL test_GetGroupsForUser(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
680 struct policy_handle *user_handle)
682 struct samr_GetGroupsForUser r;
686 printf("testing GetGroupsForUser\n");
688 r.in.user_handle = user_handle;
690 status = dcerpc_samr_GetGroupsForUser(p, mem_ctx, &r);
691 if (!NT_STATUS_IS_OK(status)) {
692 printf("GetGroupsForUser failed - %s\n",nt_errstr(status));
700 static BOOL test_GetDomPwInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
701 struct samr_String *domain_name)
704 struct samr_GetDomPwInfo r;
707 r.in.domain_name = domain_name;
708 printf("Testing GetDomPwInfo with name %s\n", r.in.domain_name->string);
710 status = dcerpc_samr_GetDomPwInfo(p, mem_ctx, &r);
711 if (!NT_STATUS_IS_OK(status)) {
712 printf("GetDomPwInfo failed - %s\n", nt_errstr(status));
716 r.in.domain_name->string = talloc_asprintf(mem_ctx, "\\\\%s", dcerpc_server_name(p));
717 printf("Testing GetDomPwInfo with name %s\n", r.in.domain_name->string);
719 status = dcerpc_samr_GetDomPwInfo(p, mem_ctx, &r);
720 if (!NT_STATUS_IS_OK(status)) {
721 printf("GetDomPwInfo failed - %s\n", nt_errstr(status));
725 r.in.domain_name->string = "\\\\__NONAME__";
726 printf("Testing GetDomPwInfo with name %s\n", r.in.domain_name->string);
728 status = dcerpc_samr_GetDomPwInfo(p, mem_ctx, &r);
729 if (!NT_STATUS_IS_OK(status)) {
730 printf("GetDomPwInfo failed - %s\n", nt_errstr(status));
734 r.in.domain_name->string = "\\\\Builtin";
735 printf("Testing GetDomPwInfo with name %s\n", r.in.domain_name->string);
737 status = dcerpc_samr_GetDomPwInfo(p, mem_ctx, &r);
738 if (!NT_STATUS_IS_OK(status)) {
739 printf("GetDomPwInfo failed - %s\n", nt_errstr(status));
747 static BOOL test_GetUserPwInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
748 struct policy_handle *handle)
751 struct samr_GetUserPwInfo r;
754 printf("Testing GetUserPwInfo\n");
756 r.in.user_handle = handle;
758 status = dcerpc_samr_GetUserPwInfo(p, mem_ctx, &r);
759 if (!NT_STATUS_IS_OK(status)) {
760 printf("GetUserPwInfo failed - %s\n", nt_errstr(status));
767 static NTSTATUS test_LookupName(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
768 struct policy_handle *domain_handle, const char *name,
772 struct samr_LookupNames n;
773 struct samr_String sname[2];
775 init_samr_String(&sname[0], name);
777 n.in.domain_handle = domain_handle;
780 status = dcerpc_samr_LookupNames(p, mem_ctx, &n);
781 if (NT_STATUS_IS_OK(status)) {
782 *rid = n.out.rids.ids[0];
787 init_samr_String(&sname[1], "xxNONAMExx");
789 status = dcerpc_samr_LookupNames(p, mem_ctx, &n);
790 if (!NT_STATUS_EQUAL(status, STATUS_SOME_UNMAPPED)) {
791 printf("LookupNames[2] failed - %s\n", nt_errstr(status));
795 init_samr_String(&sname[1], "xxNONAMExx");
797 status = dcerpc_samr_LookupNames(p, mem_ctx, &n);
798 if (!NT_STATUS_IS_OK(status)) {
799 printf("LookupNames[0] failed - %s\n", nt_errstr(status));
805 static NTSTATUS test_OpenUser_byname(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
806 struct policy_handle *domain_handle,
807 const char *name, struct policy_handle *user_handle)
810 struct samr_OpenUser r;
813 status = test_LookupName(p, mem_ctx, domain_handle, name, &rid);
814 if (!NT_STATUS_IS_OK(status)) {
818 r.in.domain_handle = domain_handle;
819 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
821 r.out.user_handle = user_handle;
822 status = dcerpc_samr_OpenUser(p, mem_ctx, &r);
823 if (!NT_STATUS_IS_OK(status)) {
824 printf("OpenUser_byname(%s) failed - %s\n", name, nt_errstr(status));
831 static BOOL test_ChangePasswordNT3(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
832 struct policy_handle *handle)
835 struct samr_ChangePasswordUser r;
837 struct samr_Password hash1, hash2, hash3, hash4, hash5, hash6;
838 struct policy_handle user_handle;
839 char *oldpass = "test";
840 char *newpass = "test2";
841 uint8_t old_nt_hash[16], new_nt_hash[16];
842 uint8_t old_lm_hash[16], new_lm_hash[16];
844 status = test_OpenUser_byname(p, mem_ctx, handle, "testuser", &user_handle);
845 if (!NT_STATUS_IS_OK(status)) {
849 printf("Testing ChangePasswordUser for user 'testuser'\n");
851 printf("old password: %s\n", oldpass);
852 printf("new password: %s\n", newpass);
854 E_md4hash(oldpass, old_nt_hash);
855 E_md4hash(newpass, new_nt_hash);
856 E_deshash(oldpass, old_lm_hash);
857 E_deshash(newpass, new_lm_hash);
859 E_old_pw_hash(new_lm_hash, old_lm_hash, hash1.hash);
860 E_old_pw_hash(old_lm_hash, new_lm_hash, hash2.hash);
861 E_old_pw_hash(new_nt_hash, old_nt_hash, hash3.hash);
862 E_old_pw_hash(old_nt_hash, new_nt_hash, hash4.hash);
863 E_old_pw_hash(old_lm_hash, new_nt_hash, hash5.hash);
864 E_old_pw_hash(old_nt_hash, new_lm_hash, hash6.hash);
866 r.in.handle = &user_handle;
868 r.in.old_lm_crypted = &hash1;
869 r.in.new_lm_crypted = &hash2;
871 r.in.old_nt_crypted = &hash3;
872 r.in.new_nt_crypted = &hash4;
873 r.in.cross1_present = 1;
874 r.in.nt_cross = &hash5;
875 r.in.cross2_present = 1;
876 r.in.lm_cross = &hash6;
878 status = dcerpc_samr_ChangePasswordUser(p, mem_ctx, &r);
879 if (!NT_STATUS_IS_OK(status)) {
880 printf("ChangePasswordUser failed - %s\n", nt_errstr(status));
884 if (!test_samr_handle_Close(p, mem_ctx, &user_handle)) {
892 static BOOL test_ChangePasswordUser(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
893 struct policy_handle *handle, char **password)
896 struct samr_ChangePasswordUser r;
898 struct samr_Password hash1, hash2, hash3, hash4, hash5, hash6;
899 struct policy_handle user_handle;
900 char *oldpass = *password;
901 uint8_t old_nt_hash[16], new_nt_hash[16];
902 uint8_t old_lm_hash[16], new_lm_hash[16];
905 struct samr_GetUserPwInfo pwp;
906 int policy_min_pw_len = 0;
908 status = test_OpenUser_byname(p, mem_ctx, handle, TEST_ACCOUNT_NAME, &user_handle);
909 if (!NT_STATUS_IS_OK(status)) {
912 pwp.in.user_handle = &user_handle;
914 status = dcerpc_samr_GetUserPwInfo(p, mem_ctx, &pwp);
915 if (NT_STATUS_IS_OK(status)) {
916 policy_min_pw_len = pwp.out.info.min_password_length;
918 newpass = samr_rand_pass(mem_ctx, policy_min_pw_len);
920 printf("Testing ChangePasswordUser\n");
922 E_md4hash(oldpass, old_nt_hash);
923 E_md4hash(newpass, new_nt_hash);
924 E_deshash(oldpass, old_lm_hash);
925 E_deshash(newpass, new_lm_hash);
927 E_old_pw_hash(new_lm_hash, old_lm_hash, hash1.hash);
928 E_old_pw_hash(old_lm_hash, new_lm_hash, hash2.hash);
929 E_old_pw_hash(new_nt_hash, old_nt_hash, hash3.hash);
930 E_old_pw_hash(old_nt_hash, new_nt_hash, hash4.hash);
931 E_old_pw_hash(old_lm_hash, new_nt_hash, hash5.hash);
932 E_old_pw_hash(old_nt_hash, new_lm_hash, hash6.hash);
934 r.in.user_handle = &user_handle;
936 r.in.old_lm_crypted = &hash1;
937 r.in.new_lm_crypted = &hash2;
939 r.in.old_nt_crypted = &hash3;
940 r.in.new_nt_crypted = &hash4;
941 r.in.cross1_present = 1;
942 r.in.nt_cross = &hash5;
943 r.in.cross2_present = 1;
944 r.in.lm_cross = &hash6;
946 status = dcerpc_samr_ChangePasswordUser(p, mem_ctx, &r);
947 if (!NT_STATUS_IS_OK(status)) {
948 printf("ChangePasswordUser failed - %s\n", nt_errstr(status));
954 if (!test_samr_handle_Close(p, mem_ctx, &user_handle)) {
962 static BOOL test_OemChangePasswordUser2(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
963 struct policy_handle *handle, char **password)
966 struct samr_OemChangePasswordUser2 r;
968 struct samr_Password lm_verifier;
969 struct samr_CryptPassword lm_pass;
970 struct samr_AsciiName server, account;
971 char *oldpass = *password;
973 uint8_t old_lm_hash[16], new_lm_hash[16];
975 struct samr_GetDomPwInfo dom_pw_info;
976 int policy_min_pw_len = 0;
978 struct samr_String domain_name;
979 domain_name.string = "";
980 dom_pw_info.in.domain_name = &domain_name;
982 printf("Testing OemChangePasswordUser2\n");
984 status = dcerpc_samr_GetDomPwInfo(p, mem_ctx, &dom_pw_info);
985 if (NT_STATUS_IS_OK(status)) {
986 policy_min_pw_len = dom_pw_info.out.info.min_password_length;
989 newpass = samr_rand_pass(mem_ctx, policy_min_pw_len);
991 server.string = talloc_asprintf(mem_ctx, "\\\\%s", dcerpc_server_name(p));
992 account.string = TEST_ACCOUNT_NAME;
994 E_deshash(oldpass, old_lm_hash);
995 E_deshash(newpass, new_lm_hash);
997 encode_pw_buffer(lm_pass.data, newpass, STR_ASCII);
998 arcfour_crypt(lm_pass.data, old_lm_hash, 516);
999 E_old_pw_hash(new_lm_hash, old_lm_hash, lm_verifier.hash);
1001 r.in.server = &server;
1002 r.in.account = &account;
1003 r.in.password = &lm_pass;
1004 r.in.hash = &lm_verifier;
1006 status = dcerpc_samr_OemChangePasswordUser2(p, mem_ctx, &r);
1007 if (!NT_STATUS_IS_OK(status)) {
1008 printf("OemChangePasswordUser2 failed - %s\n", nt_errstr(status));
1011 *password = newpass;
1018 static BOOL test_ChangePasswordUser2(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1019 struct policy_handle *handle, char **password)
1022 struct samr_ChangePasswordUser2 r;
1024 struct samr_String server, account;
1025 struct samr_CryptPassword nt_pass, lm_pass;
1026 struct samr_Password nt_verifier, lm_verifier;
1027 char *oldpass = *password;
1029 uint8_t old_nt_hash[16], new_nt_hash[16];
1030 uint8_t old_lm_hash[16], new_lm_hash[16];
1032 struct samr_GetDomPwInfo dom_pw_info;
1033 int policy_min_pw_len = 0;
1035 struct samr_String domain_name;
1036 domain_name.string = "";
1037 dom_pw_info.in.domain_name = &domain_name;
1039 printf("Testing ChangePasswordUser2\n");
1041 status = dcerpc_samr_GetDomPwInfo(p, mem_ctx, &dom_pw_info);
1042 if (NT_STATUS_IS_OK(status)) {
1043 policy_min_pw_len = dom_pw_info.out.info.min_password_length;
1046 newpass = samr_rand_pass(mem_ctx, policy_min_pw_len);
1048 server.string = talloc_asprintf(mem_ctx, "\\\\%s", dcerpc_server_name(p));
1049 init_samr_String(&account, TEST_ACCOUNT_NAME);
1051 E_md4hash(oldpass, old_nt_hash);
1052 E_md4hash(newpass, new_nt_hash);
1054 E_deshash(oldpass, old_lm_hash);
1055 E_deshash(newpass, new_lm_hash);
1057 encode_pw_buffer(lm_pass.data, newpass, STR_ASCII|STR_TERMINATE);
1058 arcfour_crypt(lm_pass.data, old_lm_hash, 516);
1059 E_old_pw_hash(new_nt_hash, old_lm_hash, lm_verifier.hash);
1061 encode_pw_buffer(nt_pass.data, newpass, STR_UNICODE);
1062 arcfour_crypt(nt_pass.data, old_nt_hash, 516);
1063 E_old_pw_hash(new_nt_hash, old_nt_hash, nt_verifier.hash);
1065 r.in.server = &server;
1066 r.in.account = &account;
1067 r.in.nt_password = &nt_pass;
1068 r.in.nt_verifier = &nt_verifier;
1070 r.in.lm_password = &lm_pass;
1071 r.in.lm_verifier = &lm_verifier;
1073 status = dcerpc_samr_ChangePasswordUser2(p, mem_ctx, &r);
1074 if (!NT_STATUS_IS_OK(status)) {
1075 printf("ChangePasswordUser2 failed - %s\n", nt_errstr(status));
1078 *password = newpass;
1085 static BOOL test_ChangePasswordUser3(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1086 struct policy_handle *handle,
1087 int policy_min_pw_len,
1091 struct samr_ChangePasswordUser3 r;
1093 struct samr_String server, account;
1094 struct samr_CryptPassword nt_pass, lm_pass;
1095 struct samr_Password nt_verifier, lm_verifier;
1096 char *oldpass = *password;
1097 char *newpass = samr_rand_pass(mem_ctx, policy_min_pw_len);
1098 uint8_t old_nt_hash[16], new_nt_hash[16];
1099 uint8_t old_lm_hash[16], new_lm_hash[16];
1101 printf("Testing ChangePasswordUser3\n");
1103 server.string = talloc_asprintf(mem_ctx, "\\\\%s", dcerpc_server_name(p));
1104 init_samr_String(&account, TEST_ACCOUNT_NAME);
1106 E_md4hash(oldpass, old_nt_hash);
1107 E_md4hash(newpass, new_nt_hash);
1109 E_deshash(oldpass, old_lm_hash);
1110 E_deshash(newpass, new_lm_hash);
1112 encode_pw_buffer(lm_pass.data, newpass, STR_UNICODE);
1113 arcfour_crypt(lm_pass.data, old_nt_hash, 516);
1114 E_old_pw_hash(new_nt_hash, old_lm_hash, lm_verifier.hash);
1116 encode_pw_buffer(nt_pass.data, newpass, STR_UNICODE);
1117 arcfour_crypt(nt_pass.data, old_nt_hash, 516);
1118 E_old_pw_hash(new_nt_hash, old_nt_hash, nt_verifier.hash);
1120 r.in.server = &server;
1121 r.in.account = &account;
1122 r.in.nt_password = &nt_pass;
1123 r.in.nt_verifier = &nt_verifier;
1125 r.in.lm_password = &lm_pass;
1126 r.in.lm_verifier = &lm_verifier;
1127 r.in.password3 = NULL;
1129 status = dcerpc_samr_ChangePasswordUser3(p, mem_ctx, &r);
1130 if (NT_STATUS_EQUAL(status, NT_STATUS_PASSWORD_RESTRICTION)
1131 && !policy_min_pw_len) {
1132 if (r.out.dominfo) {
1133 policy_min_pw_len = r.out.dominfo->min_password_length;
1135 if (policy_min_pw_len) /* try again with the right min password length */ {
1136 ret = test_ChangePasswordUser3(p, mem_ctx, handle, policy_min_pw_len, password);
1138 printf("ChangePasswordUser3 failed - %s\n", nt_errstr(status));
1141 } else if (!NT_STATUS_IS_OK(status)) {
1142 printf("ChangePasswordUser3 failed - %s\n", nt_errstr(status));
1145 *password = newpass;
1152 static BOOL test_GetMembersInAlias(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1153 struct policy_handle *alias_handle)
1155 struct samr_GetMembersInAlias r;
1156 struct lsa_SidArray sids;
1160 printf("Testing GetMembersInAlias\n");
1162 r.in.alias_handle = alias_handle;
1165 status = dcerpc_samr_GetMembersInAlias(p, mem_ctx, &r);
1166 if (!NT_STATUS_IS_OK(status)) {
1167 printf("GetMembersInAlias failed - %s\n",
1175 static BOOL test_AddMemberToAlias(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1176 struct policy_handle *alias_handle,
1177 const struct dom_sid *domain_sid)
1179 struct samr_AddAliasMember r;
1180 struct samr_DeleteAliasMember d;
1183 struct dom_sid *sid;
1185 sid = dom_sid_add_rid(mem_ctx, domain_sid, 512);
1187 printf("testing AddAliasMember\n");
1188 r.in.alias_handle = alias_handle;
1191 status = dcerpc_samr_AddAliasMember(p, mem_ctx, &r);
1192 if (!NT_STATUS_IS_OK(status)) {
1193 printf("AddAliasMember failed - %s\n", nt_errstr(status));
1197 d.in.alias_handle = alias_handle;
1200 status = dcerpc_samr_DeleteAliasMember(p, mem_ctx, &d);
1201 if (!NT_STATUS_IS_OK(status)) {
1202 printf("DelAliasMember failed - %s\n", nt_errstr(status));
1209 static BOOL test_AddMultipleMembersToAlias(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1210 struct policy_handle *alias_handle)
1212 struct samr_AddMultipleMembersToAlias a;
1213 struct samr_RemoveMultipleMembersFromAlias r;
1216 struct lsa_SidArray sids;
1218 printf("testing AddMultipleMembersToAlias\n");
1219 a.in.alias_handle = alias_handle;
1223 sids.sids = talloc_array(mem_ctx, struct lsa_SidPtr, 3);
1225 sids.sids[0].sid = dom_sid_parse_talloc(mem_ctx, "S-1-5-32-1-2-3-1");
1226 sids.sids[1].sid = dom_sid_parse_talloc(mem_ctx, "S-1-5-32-1-2-3-2");
1227 sids.sids[2].sid = dom_sid_parse_talloc(mem_ctx, "S-1-5-32-1-2-3-3");
1229 status = dcerpc_samr_AddMultipleMembersToAlias(p, mem_ctx, &a);
1230 if (!NT_STATUS_IS_OK(status)) {
1231 printf("AddMultipleMembersToAlias failed - %s\n", nt_errstr(status));
1236 printf("testing RemoveMultipleMembersFromAlias\n");
1237 r.in.alias_handle = alias_handle;
1240 status = dcerpc_samr_RemoveMultipleMembersFromAlias(p, mem_ctx, &r);
1241 if (!NT_STATUS_IS_OK(status)) {
1242 printf("RemoveMultipleMembersFromAlias failed - %s\n", nt_errstr(status));
1246 /* strange! removing twice doesn't give any error */
1247 status = dcerpc_samr_RemoveMultipleMembersFromAlias(p, mem_ctx, &r);
1248 if (!NT_STATUS_IS_OK(status)) {
1249 printf("RemoveMultipleMembersFromAlias failed - %s\n", nt_errstr(status));
1253 /* but removing an alias that isn't there does */
1254 sids.sids[2].sid = dom_sid_parse_talloc(mem_ctx, "S-1-5-32-1-2-3-4");
1256 status = dcerpc_samr_RemoveMultipleMembersFromAlias(p, mem_ctx, &r);
1257 if (!NT_STATUS_EQUAL(NT_STATUS_OBJECT_NAME_NOT_FOUND, status)) {
1258 printf("RemoveMultipleMembersFromAlias failed - %s\n", nt_errstr(status));
1265 static BOOL test_TestPrivateFunctionsUser(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1266 struct policy_handle *user_handle)
1268 struct samr_TestPrivateFunctionsUser r;
1272 printf("Testing TestPrivateFunctionsUser\n");
1274 r.in.user_handle = user_handle;
1276 status = dcerpc_samr_TestPrivateFunctionsUser(p, mem_ctx, &r);
1277 if (!NT_STATUS_EQUAL(NT_STATUS_NOT_IMPLEMENTED, status)) {
1278 printf("TestPrivateFunctionsUser failed - %s\n", nt_errstr(status));
1286 static BOOL test_user_ops(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1287 struct policy_handle *handle, uint32_t base_acct_flags,
1288 const char *base_acct_name)
1292 if (!test_QuerySecurity(p, mem_ctx, handle)) {
1296 if (!test_QueryUserInfo(p, mem_ctx, handle)) {
1300 if (!test_QueryUserInfo2(p, mem_ctx, handle)) {
1304 if (!test_SetUserInfo(p, mem_ctx, handle, base_acct_flags,
1309 if (!test_GetUserPwInfo(p, mem_ctx, handle)) {
1313 if (!test_TestPrivateFunctionsUser(p, mem_ctx, handle)) {
1320 static BOOL test_alias_ops(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1321 struct policy_handle *alias_handle,
1322 const struct dom_sid *domain_sid)
1326 if (!test_QuerySecurity(p, mem_ctx, alias_handle)) {
1330 if (!test_QueryAliasInfo(p, mem_ctx, alias_handle)) {
1334 if (!test_SetAliasInfo(p, mem_ctx, alias_handle)) {
1338 if (!test_AddMemberToAlias(p, mem_ctx, alias_handle, domain_sid)) {
1342 if (!test_AddMultipleMembersToAlias(p, mem_ctx, alias_handle)) {
1350 BOOL test_DeleteUser_byname(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1351 struct policy_handle *handle, const char *name)
1354 struct samr_DeleteUser d;
1355 struct policy_handle user_handle;
1358 status = test_LookupName(p, mem_ctx, handle, name, &rid);
1359 if (!NT_STATUS_IS_OK(status)) {
1363 status = test_OpenUser_byname(p, mem_ctx, handle, name, &user_handle);
1364 if (!NT_STATUS_IS_OK(status)) {
1368 d.in.user_handle = &user_handle;
1369 d.out.user_handle = &user_handle;
1370 status = dcerpc_samr_DeleteUser(p, mem_ctx, &d);
1371 if (!NT_STATUS_IS_OK(status)) {
1378 printf("DeleteUser_byname(%s) failed - %s\n", name, nt_errstr(status));
1383 static BOOL test_DeleteGroup_byname(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1384 struct policy_handle *handle, const char *name)
1387 struct samr_OpenGroup r;
1388 struct samr_DeleteDomainGroup d;
1389 struct policy_handle group_handle;
1392 status = test_LookupName(p, mem_ctx, handle, name, &rid);
1393 if (!NT_STATUS_IS_OK(status)) {
1397 r.in.domain_handle = handle;
1398 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
1400 r.out.group_handle = &group_handle;
1401 status = dcerpc_samr_OpenGroup(p, mem_ctx, &r);
1402 if (!NT_STATUS_IS_OK(status)) {
1406 d.in.group_handle = &group_handle;
1407 d.out.group_handle = &group_handle;
1408 status = dcerpc_samr_DeleteDomainGroup(p, mem_ctx, &d);
1409 if (!NT_STATUS_IS_OK(status)) {
1416 printf("DeleteGroup_byname(%s) failed - %s\n", name, nt_errstr(status));
1421 static BOOL test_DeleteAlias_byname(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1422 struct policy_handle *domain_handle, const char *name)
1425 struct samr_OpenAlias r;
1426 struct samr_DeleteDomAlias d;
1427 struct policy_handle alias_handle;
1430 printf("testing DeleteAlias_byname\n");
1432 status = test_LookupName(p, mem_ctx, domain_handle, name, &rid);
1433 if (!NT_STATUS_IS_OK(status)) {
1437 r.in.domain_handle = domain_handle;
1438 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
1440 r.out.alias_handle = &alias_handle;
1441 status = dcerpc_samr_OpenAlias(p, mem_ctx, &r);
1442 if (!NT_STATUS_IS_OK(status)) {
1446 d.in.alias_handle = &alias_handle;
1447 d.out.alias_handle = &alias_handle;
1448 status = dcerpc_samr_DeleteDomAlias(p, mem_ctx, &d);
1449 if (!NT_STATUS_IS_OK(status)) {
1456 printf("DeleteUser_byname(%s) failed - %s\n", name, nt_errstr(status));
1460 static BOOL test_DeleteAlias(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1461 struct policy_handle *alias_handle)
1463 struct samr_DeleteDomAlias d;
1466 printf("Testing DeleteAlias\n");
1468 d.in.alias_handle = alias_handle;
1469 d.out.alias_handle = alias_handle;
1471 status = dcerpc_samr_DeleteDomAlias(p, mem_ctx, &d);
1472 if (!NT_STATUS_IS_OK(status)) {
1473 printf("DeleteAlias failed - %s\n", nt_errstr(status));
1480 static BOOL test_CreateAlias(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1481 struct policy_handle *domain_handle,
1482 struct policy_handle *alias_handle,
1483 const struct dom_sid *domain_sid)
1486 struct samr_CreateDomAlias r;
1487 struct samr_String name;
1491 init_samr_String(&name, TEST_ALIASNAME);
1492 r.in.domain_handle = domain_handle;
1493 r.in.aliasname = &name;
1494 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
1495 r.out.alias_handle = alias_handle;
1498 printf("Testing CreateAlias (%s)\n", r.in.aliasname->string);
1500 status = dcerpc_samr_CreateDomAlias(p, mem_ctx, &r);
1502 if (NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
1503 printf("Server refused create of '%s'\n", r.in.aliasname->string);
1507 if (NT_STATUS_EQUAL(status, NT_STATUS_ALIAS_EXISTS)) {
1508 if (!test_DeleteAlias_byname(p, mem_ctx, domain_handle, r.in.aliasname->string)) {
1511 status = dcerpc_samr_CreateDomAlias(p, mem_ctx, &r);
1514 if (!NT_STATUS_IS_OK(status)) {
1515 printf("CreateAlias failed - %s\n", nt_errstr(status));
1519 if (!test_alias_ops(p, mem_ctx, alias_handle, domain_sid)) {
1526 static BOOL test_ChangePassword(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1527 struct policy_handle *domain_handle, char **password)
1535 if (!test_ChangePasswordUser(p, mem_ctx, domain_handle, password)) {
1539 if (!test_ChangePasswordUser2(p, mem_ctx, domain_handle, password)) {
1543 if (!test_OemChangePasswordUser2(p, mem_ctx, domain_handle, password)) {
1547 /* we change passwords twice - this has the effect of verifying
1548 they were changed correctly for the final call */
1549 if (!test_ChangePasswordUser3(p, mem_ctx, domain_handle, 0, password)) {
1553 if (!test_ChangePasswordUser3(p, mem_ctx, domain_handle, 0, password)) {
1560 static BOOL test_CreateUser(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1561 struct policy_handle *domain_handle, struct policy_handle *user_handle)
1564 struct samr_CreateUser r;
1565 struct samr_QueryUserInfo q;
1567 char *password = NULL;
1570 const uint32_t password_fields[] = {
1571 SAMR_FIELD_PASSWORD,
1572 SAMR_FIELD_PASSWORD2,
1573 SAMR_FIELD_PASSWORD | SAMR_FIELD_PASSWORD2,
1577 TALLOC_CTX *user_ctx;
1579 /* This call creates a 'normal' account - check that it really does */
1580 const uint32_t acct_flags = ACB_NORMAL;
1581 struct samr_String name;
1584 user_ctx = talloc_named(mem_ctx, 0, "test_CreateUser2 per-user context");
1585 init_samr_String(&name, TEST_ACCOUNT_NAME);
1587 r.in.domain_handle = domain_handle;
1588 r.in.account_name = &name;
1589 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
1590 r.out.user_handle = user_handle;
1593 printf("Testing CreateUser(%s)\n", r.in.account_name->string);
1595 status = dcerpc_samr_CreateUser(p, user_ctx, &r);
1597 if (NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
1598 printf("Server refused create of '%s'\n", r.in.account_name->string);
1599 ZERO_STRUCTP(user_handle);
1600 talloc_free(user_ctx);
1604 if (NT_STATUS_EQUAL(status, NT_STATUS_USER_EXISTS)) {
1605 if (!test_DeleteUser_byname(p, user_ctx, domain_handle, r.in.account_name->string)) {
1606 talloc_free(user_ctx);
1609 status = dcerpc_samr_CreateUser(p, user_ctx, &r);
1611 if (!NT_STATUS_IS_OK(status)) {
1612 talloc_free(user_ctx);
1613 printf("CreateUser failed - %s\n", nt_errstr(status));
1617 q.in.user_handle = user_handle;
1620 status = dcerpc_samr_QueryUserInfo(p, user_ctx, &q);
1621 if (!NT_STATUS_IS_OK(status)) {
1622 printf("QueryUserInfo level %u failed - %s\n",
1623 q.in.level, nt_errstr(status));
1626 if ((q.out.info->info16.acct_flags & acct_flags) != acct_flags) {
1627 printf("QuerUserInfo level 16 failed, it returned 0x%08x (%u) when we expected flags of 0x%08x (%u)\n",
1628 q.out.info->info16.acct_flags, q.out.info->info16.acct_flags,
1629 acct_flags, acct_flags);
1634 if (!test_user_ops(p, user_ctx, user_handle, acct_flags, name.string)) {
1638 if (!test_SetUserPass(p, user_ctx, user_handle, &password)) {
1642 for (i = 0; password_fields[i]; i++) {
1643 if (!test_SetUserPass_23(p, user_ctx, user_handle, password_fields[i], &password)) {
1647 /* check it was set right */
1648 if (!test_ChangePasswordUser3(p, user_ctx, domain_handle, 0, &password)) {
1653 for (i = 0; password_fields[i]; i++) {
1654 if (!test_SetUserPass_25(p, user_ctx, user_handle, password_fields[i], &password)) {
1658 /* check it was set right */
1659 if (!test_ChangePasswordUser3(p, user_ctx, domain_handle, 0, &password)) {
1664 if (!test_SetUserPassEx(p, user_ctx, user_handle, &password)) {
1668 if (!test_ChangePassword(p, user_ctx, domain_handle, &password)) {
1672 talloc_free(user_ctx);
1678 static BOOL test_DeleteUser(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1679 struct policy_handle *user_handle)
1681 struct samr_DeleteUser d;
1685 printf("Testing DeleteUser\n");
1687 d.in.user_handle = user_handle;
1688 d.out.user_handle = user_handle;
1690 status = dcerpc_samr_DeleteUser(p, mem_ctx, &d);
1691 if (!NT_STATUS_IS_OK(status)) {
1692 printf("DeleteUser failed - %s\n", nt_errstr(status));
1699 static BOOL test_CreateUser2(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1700 struct policy_handle *handle)
1703 struct samr_CreateUser2 r;
1704 struct samr_QueryUserInfo q;
1705 struct samr_DeleteUser d;
1706 struct policy_handle user_handle;
1708 struct samr_String name;
1713 uint32_t acct_flags;
1714 const char *account_name;
1716 } account_types[] = {
1717 { ACB_NORMAL, TEST_ACCOUNT_NAME, NT_STATUS_OK },
1718 { ACB_NORMAL | ACB_DISABLED, TEST_ACCOUNT_NAME, NT_STATUS_INVALID_PARAMETER },
1719 { ACB_NORMAL | ACB_PWNOEXP, TEST_ACCOUNT_NAME, NT_STATUS_INVALID_PARAMETER },
1720 { ACB_WSTRUST, TEST_MACHINENAME, NT_STATUS_OK },
1721 { ACB_WSTRUST | ACB_DISABLED, TEST_MACHINENAME, NT_STATUS_INVALID_PARAMETER },
1722 { ACB_WSTRUST | ACB_PWNOEXP, TEST_MACHINENAME, NT_STATUS_INVALID_PARAMETER },
1723 { ACB_SVRTRUST, TEST_MACHINENAME, NT_STATUS_OK },
1724 { ACB_SVRTRUST | ACB_DISABLED, TEST_MACHINENAME, NT_STATUS_INVALID_PARAMETER },
1725 { ACB_SVRTRUST | ACB_PWNOEXP, TEST_MACHINENAME, NT_STATUS_INVALID_PARAMETER },
1726 { ACB_DOMTRUST, TEST_DOMAINNAME, NT_STATUS_OK },
1727 { ACB_DOMTRUST | ACB_DISABLED, TEST_DOMAINNAME, NT_STATUS_INVALID_PARAMETER },
1728 { ACB_DOMTRUST | ACB_PWNOEXP, TEST_DOMAINNAME, NT_STATUS_INVALID_PARAMETER },
1729 { 0, TEST_ACCOUNT_NAME, NT_STATUS_INVALID_PARAMETER },
1730 { ACB_DISABLED, TEST_ACCOUNT_NAME, NT_STATUS_INVALID_PARAMETER },
1731 { 0, NULL, NT_STATUS_INVALID_PARAMETER }
1734 for (i = 0; account_types[i].account_name; i++) {
1735 TALLOC_CTX *user_ctx;
1736 uint32_t acct_flags = account_types[i].acct_flags;
1737 uint32_t access_granted;
1738 user_ctx = talloc_named(mem_ctx, 0, "test_CreateUser2 per-user context");
1739 init_samr_String(&name, account_types[i].account_name);
1741 r.in.domain_handle = handle;
1742 r.in.account_name = &name;
1743 r.in.acct_flags = acct_flags;
1744 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
1745 r.out.user_handle = &user_handle;
1746 r.out.access_granted = &access_granted;
1749 printf("Testing CreateUser2(%s, 0x%x)\n", r.in.account_name->string, acct_flags);
1751 status = dcerpc_samr_CreateUser2(p, user_ctx, &r);
1753 if (NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
1754 talloc_free(user_ctx);
1755 printf("Server refused create of '%s'\n", r.in.account_name->string);
1758 } else if (NT_STATUS_EQUAL(status, NT_STATUS_USER_EXISTS)) {
1759 if (!test_DeleteUser_byname(p, user_ctx, handle, r.in.account_name->string)) {
1760 talloc_free(user_ctx);
1764 status = dcerpc_samr_CreateUser2(p, user_ctx, &r);
1767 if (!NT_STATUS_EQUAL(status, account_types[i].nt_status)) {
1768 printf("CreateUser2 failed gave incorrect error return - %s (should be %s)\n",
1769 nt_errstr(status), nt_errstr(account_types[i].nt_status));
1773 if (NT_STATUS_IS_OK(status)) {
1774 q.in.user_handle = &user_handle;
1777 status = dcerpc_samr_QueryUserInfo(p, user_ctx, &q);
1778 if (!NT_STATUS_IS_OK(status)) {
1779 printf("QueryUserInfo level %u failed - %s\n",
1780 q.in.level, nt_errstr(status));
1783 if ((q.out.info->info16.acct_flags & acct_flags) != acct_flags) {
1784 printf("QuerUserInfo level 16 failed, it returned 0x%08x when we expected flags of 0x%08x\n",
1785 q.out.info->info16.acct_flags,
1791 if (!test_user_ops(p, user_ctx, &user_handle, acct_flags, name.string)) {
1795 printf("Testing DeleteUser (createuser2 test)\n");
1797 d.in.user_handle = &user_handle;
1798 d.out.user_handle = &user_handle;
1800 status = dcerpc_samr_DeleteUser(p, user_ctx, &d);
1801 if (!NT_STATUS_IS_OK(status)) {
1802 printf("DeleteUser failed - %s\n", nt_errstr(status));
1806 talloc_free(user_ctx);
1812 static BOOL test_QueryAliasInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1813 struct policy_handle *handle)
1816 struct samr_QueryAliasInfo r;
1817 uint16_t levels[] = {1, 2, 3};
1821 for (i=0;i<ARRAY_SIZE(levels);i++) {
1822 printf("Testing QueryAliasInfo level %u\n", levels[i]);
1824 r.in.alias_handle = handle;
1825 r.in.level = levels[i];
1827 status = dcerpc_samr_QueryAliasInfo(p, mem_ctx, &r);
1828 if (!NT_STATUS_IS_OK(status)) {
1829 printf("QueryAliasInfo level %u failed - %s\n",
1830 levels[i], nt_errstr(status));
1838 static BOOL test_QueryGroupInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1839 struct policy_handle *handle)
1842 struct samr_QueryGroupInfo r;
1843 uint16_t levels[] = {1, 2, 3, 4, 5};
1847 for (i=0;i<ARRAY_SIZE(levels);i++) {
1848 printf("Testing QueryGroupInfo level %u\n", levels[i]);
1850 r.in.group_handle = handle;
1851 r.in.level = levels[i];
1853 status = dcerpc_samr_QueryGroupInfo(p, mem_ctx, &r);
1854 if (!NT_STATUS_IS_OK(status)) {
1855 printf("QueryGroupInfo level %u failed - %s\n",
1856 levels[i], nt_errstr(status));
1864 static BOOL test_QueryGroupMember(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1865 struct policy_handle *handle)
1868 struct samr_QueryGroupMember r;
1871 printf("Testing QueryGroupMember\n");
1873 r.in.group_handle = handle;
1875 status = dcerpc_samr_QueryGroupMember(p, mem_ctx, &r);
1876 if (!NT_STATUS_IS_OK(status)) {
1877 printf("QueryGroupInfo failed - %s\n", nt_errstr(status));
1885 static BOOL test_SetGroupInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1886 struct policy_handle *handle)
1889 struct samr_QueryGroupInfo r;
1890 struct samr_SetGroupInfo s;
1891 uint16_t levels[] = {1, 2, 3, 4};
1892 uint16_t set_ok[] = {0, 1, 1, 1};
1896 for (i=0;i<ARRAY_SIZE(levels);i++) {
1897 printf("Testing QueryGroupInfo level %u\n", levels[i]);
1899 r.in.group_handle = handle;
1900 r.in.level = levels[i];
1902 status = dcerpc_samr_QueryGroupInfo(p, mem_ctx, &r);
1903 if (!NT_STATUS_IS_OK(status)) {
1904 printf("QueryGroupInfo level %u failed - %s\n",
1905 levels[i], nt_errstr(status));
1909 printf("Testing SetGroupInfo level %u\n", levels[i]);
1911 s.in.group_handle = handle;
1912 s.in.level = levels[i];
1913 s.in.info = r.out.info;
1916 /* disabled this, as it changes the name only from the point of view of samr,
1917 but leaves the name from the point of view of w2k3 internals (and ldap). This means
1918 the name is still reserved, so creating the old name fails, but deleting by the old name
1920 if (s.in.level == 2) {
1921 init_samr_String(&s.in.info->string, "NewName");
1925 if (s.in.level == 4) {
1926 init_samr_String(&s.in.info->description, "test description");
1929 status = dcerpc_samr_SetGroupInfo(p, mem_ctx, &s);
1931 if (!NT_STATUS_IS_OK(status)) {
1932 printf("SetGroupInfo level %u failed - %s\n",
1933 r.in.level, nt_errstr(status));
1938 if (!NT_STATUS_EQUAL(NT_STATUS_INVALID_INFO_CLASS, status)) {
1939 printf("SetGroupInfo level %u gave %s - should have been NT_STATUS_INVALID_INFO_CLASS\n",
1940 r.in.level, nt_errstr(status));
1950 static BOOL test_QueryUserInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1951 struct policy_handle *handle)
1954 struct samr_QueryUserInfo r;
1955 uint16_t levels[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
1956 11, 12, 13, 14, 16, 17, 20, 21};
1960 for (i=0;i<ARRAY_SIZE(levels);i++) {
1961 printf("Testing QueryUserInfo level %u\n", levels[i]);
1963 r.in.user_handle = handle;
1964 r.in.level = levels[i];
1966 status = dcerpc_samr_QueryUserInfo(p, mem_ctx, &r);
1967 if (!NT_STATUS_IS_OK(status)) {
1968 printf("QueryUserInfo level %u failed - %s\n",
1969 levels[i], nt_errstr(status));
1977 static BOOL test_QueryUserInfo2(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
1978 struct policy_handle *handle)
1981 struct samr_QueryUserInfo2 r;
1982 uint16_t levels[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
1983 11, 12, 13, 14, 16, 17, 20, 21};
1987 for (i=0;i<ARRAY_SIZE(levels);i++) {
1988 printf("Testing QueryUserInfo2 level %u\n", levels[i]);
1990 r.in.user_handle = handle;
1991 r.in.level = levels[i];
1993 status = dcerpc_samr_QueryUserInfo2(p, mem_ctx, &r);
1994 if (!NT_STATUS_IS_OK(status)) {
1995 printf("QueryUserInfo2 level %u failed - %s\n",
1996 levels[i], nt_errstr(status));
2004 static BOOL test_OpenUser(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2005 struct policy_handle *handle, uint32_t rid)
2008 struct samr_OpenUser r;
2009 struct policy_handle user_handle;
2012 printf("Testing OpenUser(%u)\n", rid);
2014 r.in.domain_handle = handle;
2015 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
2017 r.out.user_handle = &user_handle;
2019 status = dcerpc_samr_OpenUser(p, mem_ctx, &r);
2020 if (!NT_STATUS_IS_OK(status)) {
2021 printf("OpenUser(%u) failed - %s\n", rid, nt_errstr(status));
2025 if (!test_QuerySecurity(p, mem_ctx, &user_handle)) {
2029 if (!test_QueryUserInfo(p, mem_ctx, &user_handle)) {
2033 if (!test_QueryUserInfo2(p, mem_ctx, &user_handle)) {
2037 if (!test_GetUserPwInfo(p, mem_ctx, &user_handle)) {
2041 if (!test_GetGroupsForUser(p,mem_ctx, &user_handle)) {
2045 if (!test_samr_handle_Close(p, mem_ctx, &user_handle)) {
2052 static BOOL test_OpenGroup(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2053 struct policy_handle *handle, uint32_t rid)
2056 struct samr_OpenGroup r;
2057 struct policy_handle group_handle;
2060 printf("Testing OpenGroup(%u)\n", rid);
2062 r.in.domain_handle = handle;
2063 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
2065 r.out.group_handle = &group_handle;
2067 status = dcerpc_samr_OpenGroup(p, mem_ctx, &r);
2068 if (!NT_STATUS_IS_OK(status)) {
2069 printf("OpenGroup(%u) failed - %s\n", rid, nt_errstr(status));
2073 if (!test_QuerySecurity(p, mem_ctx, &group_handle)) {
2077 if (!test_QueryGroupInfo(p, mem_ctx, &group_handle)) {
2081 if (!test_QueryGroupMember(p, mem_ctx, &group_handle)) {
2085 if (!test_samr_handle_Close(p, mem_ctx, &group_handle)) {
2092 static BOOL test_OpenAlias(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2093 struct policy_handle *handle, uint32_t rid)
2096 struct samr_OpenAlias r;
2097 struct policy_handle alias_handle;
2100 printf("Testing OpenAlias(%u)\n", rid);
2102 r.in.domain_handle = handle;
2103 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
2105 r.out.alias_handle = &alias_handle;
2107 status = dcerpc_samr_OpenAlias(p, mem_ctx, &r);
2108 if (!NT_STATUS_IS_OK(status)) {
2109 printf("OpenAlias(%u) failed - %s\n", rid, nt_errstr(status));
2113 if (!test_QuerySecurity(p, mem_ctx, &alias_handle)) {
2117 if (!test_QueryAliasInfo(p, mem_ctx, &alias_handle)) {
2121 if (!test_GetMembersInAlias(p, mem_ctx, &alias_handle)) {
2125 if (!test_samr_handle_Close(p, mem_ctx, &alias_handle)) {
2132 static BOOL test_EnumDomainUsers(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2133 struct policy_handle *handle)
2136 struct samr_EnumDomainUsers r;
2137 uint32_t resume_handle=0;
2140 struct samr_LookupNames n;
2141 struct samr_LookupRids lr ;
2143 printf("Testing EnumDomainUsers\n");
2145 r.in.domain_handle = handle;
2146 r.in.resume_handle = &resume_handle;
2147 r.in.acct_flags = 0;
2148 r.in.max_size = (uint32_t)-1;
2149 r.out.resume_handle = &resume_handle;
2151 status = dcerpc_samr_EnumDomainUsers(p, mem_ctx, &r);
2152 if (!NT_STATUS_IS_OK(status)) {
2153 printf("EnumDomainUsers failed - %s\n", nt_errstr(status));
2161 if (r.out.sam->count == 0) {
2165 for (i=0;i<r.out.sam->count;i++) {
2166 if (!test_OpenUser(p, mem_ctx, handle, r.out.sam->entries[i].idx)) {
2171 printf("Testing LookupNames\n");
2172 n.in.domain_handle = handle;
2173 n.in.num_names = r.out.sam->count;
2174 n.in.names = talloc_array(mem_ctx, struct samr_String, r.out.sam->count);
2175 for (i=0;i<r.out.sam->count;i++) {
2176 n.in.names[i] = r.out.sam->entries[i].name;
2178 status = dcerpc_samr_LookupNames(p, mem_ctx, &n);
2179 if (!NT_STATUS_IS_OK(status)) {
2180 printf("LookupNames failed - %s\n", nt_errstr(status));
2185 printf("Testing LookupRids\n");
2186 lr.in.domain_handle = handle;
2187 lr.in.num_rids = r.out.sam->count;
2188 lr.in.rids = talloc_array(mem_ctx, uint32_t, r.out.sam->count);
2189 for (i=0;i<r.out.sam->count;i++) {
2190 lr.in.rids[i] = r.out.sam->entries[i].idx;
2192 status = dcerpc_samr_LookupRids(p, mem_ctx, &lr);
2193 if (!NT_STATUS_IS_OK(status)) {
2194 printf("LookupRids failed - %s\n", nt_errstr(status));
2202 try blasting the server with a bunch of sync requests
2204 static BOOL test_EnumDomainUsers_async(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2205 struct policy_handle *handle)
2208 struct samr_EnumDomainUsers r;
2209 uint32_t resume_handle=0;
2211 #define ASYNC_COUNT 100
2212 struct rpc_request *req[ASYNC_COUNT];
2214 if (!lp_parm_bool(-1, "torture", "dangerous", False)) {
2215 printf("samr async test disabled - enable dangerous tests to use\n");
2219 printf("Testing EnumDomainUsers_async\n");
2221 r.in.domain_handle = handle;
2222 r.in.resume_handle = &resume_handle;
2223 r.in.acct_flags = 0;
2224 r.in.max_size = (uint32_t)-1;
2225 r.out.resume_handle = &resume_handle;
2227 for (i=0;i<ASYNC_COUNT;i++) {
2228 req[i] = dcerpc_samr_EnumDomainUsers_send(p, mem_ctx, &r);
2231 for (i=0;i<ASYNC_COUNT;i++) {
2232 status = dcerpc_ndr_request_recv(req[i]);
2233 if (!NT_STATUS_IS_OK(status)) {
2234 printf("EnumDomainUsers[%d] failed - %s\n",
2235 i, nt_errstr(status));
2240 printf("%d async requests OK\n", i);
2245 static BOOL test_EnumDomainGroups(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2246 struct policy_handle *handle)
2249 struct samr_EnumDomainGroups r;
2250 uint32_t resume_handle=0;
2254 printf("Testing EnumDomainGroups\n");
2256 r.in.domain_handle = handle;
2257 r.in.resume_handle = &resume_handle;
2258 r.in.max_size = (uint32_t)-1;
2259 r.out.resume_handle = &resume_handle;
2261 status = dcerpc_samr_EnumDomainGroups(p, mem_ctx, &r);
2262 if (!NT_STATUS_IS_OK(status)) {
2263 printf("EnumDomainGroups failed - %s\n", nt_errstr(status));
2271 for (i=0;i<r.out.sam->count;i++) {
2272 if (!test_OpenGroup(p, mem_ctx, handle, r.out.sam->entries[i].idx)) {
2280 static BOOL test_EnumDomainAliases(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2281 struct policy_handle *handle)
2284 struct samr_EnumDomainAliases r;
2285 uint32_t resume_handle=0;
2289 printf("Testing EnumDomainAliases\n");
2291 r.in.domain_handle = handle;
2292 r.in.resume_handle = &resume_handle;
2293 r.in.acct_flags = (uint32_t)-1;
2294 r.out.resume_handle = &resume_handle;
2296 status = dcerpc_samr_EnumDomainAliases(p, mem_ctx, &r);
2297 if (!NT_STATUS_IS_OK(status)) {
2298 printf("EnumDomainAliases failed - %s\n", nt_errstr(status));
2306 for (i=0;i<r.out.sam->count;i++) {
2307 if (!test_OpenAlias(p, mem_ctx, handle, r.out.sam->entries[i].idx)) {
2315 static BOOL test_GetDisplayEnumerationIndex(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2316 struct policy_handle *handle)
2319 struct samr_GetDisplayEnumerationIndex r;
2321 uint16_t levels[] = {1, 2, 3, 4, 5};
2322 uint16_t ok_lvl[] = {1, 1, 1, 0, 0};
2325 for (i=0;i<ARRAY_SIZE(levels);i++) {
2326 printf("Testing GetDisplayEnumerationIndex level %u\n", levels[i]);
2328 r.in.domain_handle = handle;
2329 r.in.level = levels[i];
2330 init_samr_String(&r.in.name, TEST_ACCOUNT_NAME);
2332 status = dcerpc_samr_GetDisplayEnumerationIndex(p, mem_ctx, &r);
2335 !NT_STATUS_IS_OK(status) &&
2336 !NT_STATUS_EQUAL(NT_STATUS_NO_MORE_ENTRIES, status)) {
2337 printf("GetDisplayEnumerationIndex level %u failed - %s\n",
2338 levels[i], nt_errstr(status));
2342 init_samr_String(&r.in.name, "zzzzzzzz");
2344 status = dcerpc_samr_GetDisplayEnumerationIndex(p, mem_ctx, &r);
2346 if (ok_lvl[i] && !NT_STATUS_EQUAL(NT_STATUS_NO_MORE_ENTRIES, status)) {
2347 printf("GetDisplayEnumerationIndex level %u failed - %s\n",
2348 levels[i], nt_errstr(status));
2356 static BOOL test_GetDisplayEnumerationIndex2(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2357 struct policy_handle *handle)
2360 struct samr_GetDisplayEnumerationIndex2 r;
2362 uint16_t levels[] = {1, 2, 3, 4, 5};
2363 uint16_t ok_lvl[] = {1, 1, 1, 0, 0};
2366 for (i=0;i<ARRAY_SIZE(levels);i++) {
2367 printf("Testing GetDisplayEnumerationIndex2 level %u\n", levels[i]);
2369 r.in.domain_handle = handle;
2370 r.in.level = levels[i];
2371 init_samr_String(&r.in.name, TEST_ACCOUNT_NAME);
2373 status = dcerpc_samr_GetDisplayEnumerationIndex2(p, mem_ctx, &r);
2375 !NT_STATUS_IS_OK(status) &&
2376 !NT_STATUS_EQUAL(NT_STATUS_NO_MORE_ENTRIES, status)) {
2377 printf("GetDisplayEnumerationIndex2 level %u failed - %s\n",
2378 levels[i], nt_errstr(status));
2382 init_samr_String(&r.in.name, "zzzzzzzz");
2384 status = dcerpc_samr_GetDisplayEnumerationIndex2(p, mem_ctx, &r);
2385 if (ok_lvl[i] && !NT_STATUS_EQUAL(NT_STATUS_NO_MORE_ENTRIES, status)) {
2386 printf("GetDisplayEnumerationIndex2 level %u failed - %s\n",
2387 levels[i], nt_errstr(status));
2395 static BOOL test_QueryDisplayInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2396 struct policy_handle *handle)
2399 struct samr_QueryDisplayInfo r;
2401 uint16_t levels[] = {1, 2, 3, 4, 5};
2404 for (i=0;i<ARRAY_SIZE(levels);i++) {
2405 printf("Testing QueryDisplayInfo level %u\n", levels[i]);
2407 r.in.domain_handle = handle;
2408 r.in.level = levels[i];
2410 r.in.max_entries = 1000;
2411 r.in.buf_size = (uint32_t)-1;
2413 status = dcerpc_samr_QueryDisplayInfo(p, mem_ctx, &r);
2414 if (!NT_STATUS_IS_OK(status)) {
2415 printf("QueryDisplayInfo level %u failed - %s\n",
2416 levels[i], nt_errstr(status));
2424 static BOOL test_QueryDisplayInfo2(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2425 struct policy_handle *handle)
2428 struct samr_QueryDisplayInfo2 r;
2430 uint16_t levels[] = {1, 2, 3, 4, 5};
2433 for (i=0;i<ARRAY_SIZE(levels);i++) {
2434 printf("Testing QueryDisplayInfo2 level %u\n", levels[i]);
2436 r.in.domain_handle = handle;
2437 r.in.level = levels[i];
2439 r.in.max_entries = 1000;
2440 r.in.buf_size = (uint32_t)-1;
2442 status = dcerpc_samr_QueryDisplayInfo2(p, mem_ctx, &r);
2443 if (!NT_STATUS_IS_OK(status)) {
2444 printf("QueryDisplayInfo2 level %u failed - %s\n",
2445 levels[i], nt_errstr(status));
2453 static BOOL test_QueryDisplayInfo3(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2454 struct policy_handle *handle)
2457 struct samr_QueryDisplayInfo3 r;
2459 uint16_t levels[] = {1, 2, 3, 4, 5};
2462 for (i=0;i<ARRAY_SIZE(levels);i++) {
2463 printf("Testing QueryDisplayInfo3 level %u\n", levels[i]);
2465 r.in.domain_handle = handle;
2466 r.in.level = levels[i];
2468 r.in.max_entries = 1000;
2469 r.in.buf_size = (uint32_t)-1;
2471 status = dcerpc_samr_QueryDisplayInfo3(p, mem_ctx, &r);
2472 if (!NT_STATUS_IS_OK(status)) {
2473 printf("QueryDisplayInfo3 level %u failed - %s\n",
2474 levels[i], nt_errstr(status));
2482 static BOOL test_QueryDomainInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2483 struct policy_handle *handle)
2486 struct samr_QueryDomainInfo r;
2487 struct samr_SetDomainInfo s;
2488 uint16_t levels[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 11, 12, 13};
2489 uint16_t set_ok[] = {1, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0};
2493 for (i=0;i<ARRAY_SIZE(levels);i++) {
2494 printf("Testing QueryDomainInfo level %u\n", levels[i]);
2496 r.in.domain_handle = handle;
2497 r.in.level = levels[i];
2499 status = dcerpc_samr_QueryDomainInfo(p, mem_ctx, &r);
2500 if (!NT_STATUS_IS_OK(status)) {
2501 printf("QueryDomainInfo level %u failed - %s\n",
2502 r.in.level, nt_errstr(status));
2507 printf("Testing SetDomainInfo level %u\n", levels[i]);
2509 s.in.domain_handle = handle;
2510 s.in.level = levels[i];
2511 s.in.info = r.out.info;
2513 status = dcerpc_samr_SetDomainInfo(p, mem_ctx, &s);
2515 if (!NT_STATUS_IS_OK(status)) {
2516 printf("SetDomainInfo level %u failed - %s\n",
2517 r.in.level, nt_errstr(status));
2522 if (!NT_STATUS_EQUAL(NT_STATUS_INVALID_INFO_CLASS, status)) {
2523 printf("SetDomainInfo level %u gave %s - should have been NT_STATUS_INVALID_INFO_CLASS\n",
2524 r.in.level, nt_errstr(status));
2530 status = dcerpc_samr_QueryDomainInfo(p, mem_ctx, &r);
2531 if (!NT_STATUS_IS_OK(status)) {
2532 printf("QueryDomainInfo level %u failed - %s\n",
2533 r.in.level, nt_errstr(status));
2543 static BOOL test_QueryDomainInfo2(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2544 struct policy_handle *handle)
2547 struct samr_QueryDomainInfo2 r;
2548 uint16_t levels[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 11, 12, 13};
2552 for (i=0;i<ARRAY_SIZE(levels);i++) {
2553 printf("Testing QueryDomainInfo2 level %u\n", levels[i]);
2555 r.in.domain_handle = handle;
2556 r.in.level = levels[i];
2558 status = dcerpc_samr_QueryDomainInfo2(p, mem_ctx, &r);
2559 if (!NT_STATUS_IS_OK(status)) {
2560 printf("QueryDomainInfo2 level %u failed - %s\n",
2561 r.in.level, nt_errstr(status));
2570 /* Test whether querydispinfo level 5 and enumdomgroups return the same
2571 set of group names. */
2572 static BOOL test_GroupList(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2573 struct policy_handle *handle)
2575 struct samr_EnumDomainGroups q1;
2576 struct samr_QueryDisplayInfo q2;
2578 uint32_t resume_handle=0;
2583 const char **names = NULL;
2585 printf("Testing coherency of querydispinfo vs enumdomgroups\n");
2587 q1.in.domain_handle = handle;
2588 q1.in.resume_handle = &resume_handle;
2590 q1.out.resume_handle = &resume_handle;
2592 status = STATUS_MORE_ENTRIES;
2593 while (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) {
2594 status = dcerpc_samr_EnumDomainGroups(p, mem_ctx, &q1);
2596 if (!NT_STATUS_IS_OK(status) &&
2597 !NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES))
2600 for (i=0; i<q1.out.num_entries; i++) {
2601 add_string_to_array(mem_ctx,
2602 q1.out.sam->entries[i].name.string,
2603 &names, &num_names);
2607 if (!NT_STATUS_IS_OK(status)) {
2608 printf("EnumDomainGroups failed - %s\n", nt_errstr(status));
2616 q2.in.domain_handle = handle;
2618 q2.in.start_idx = 0;
2619 q2.in.max_entries = 5;
2620 q2.in.buf_size = (uint32_t)-1;
2622 status = STATUS_MORE_ENTRIES;
2623 while (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) {
2624 status = dcerpc_samr_QueryDisplayInfo(p, mem_ctx, &q2);
2626 if (!NT_STATUS_IS_OK(status) &&
2627 !NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES))
2630 for (i=0; i<q2.out.info.info5.count; i++) {
2632 const char *name = q2.out.info.info5.entries[i].account_name.string;
2634 for (j=0; j<num_names; j++) {
2635 if (names[j] == NULL)
2637 /* Hmm. No strequal in samba4 */
2638 if (strequal(names[j], name)) {
2646 printf("QueryDisplayInfo gave name [%s] that EnumDomainGroups did not\n",
2651 q2.in.start_idx += q2.out.info.info5.count;
2654 if (!NT_STATUS_IS_OK(status)) {
2655 printf("QueryDisplayInfo level 5 failed - %s\n",
2660 for (i=0; i<num_names; i++) {
2661 if (names[i] != NULL) {
2662 printf("EnumDomainGroups gave name [%s] that QueryDisplayInfo did not\n",
2671 static BOOL test_DeleteDomainGroup(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2672 struct policy_handle *group_handle)
2674 struct samr_DeleteDomainGroup d;
2678 printf("Testing DeleteDomainGroup\n");
2680 d.in.group_handle = group_handle;
2681 d.out.group_handle = group_handle;
2683 status = dcerpc_samr_DeleteDomainGroup(p, mem_ctx, &d);
2684 if (!NT_STATUS_IS_OK(status)) {
2685 printf("DeleteDomainGroup failed - %s\n", nt_errstr(status));
2692 static BOOL test_TestPrivateFunctionsDomain(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2693 struct policy_handle *domain_handle)
2695 struct samr_TestPrivateFunctionsDomain r;
2699 printf("Testing TestPrivateFunctionsDomain\n");
2701 r.in.domain_handle = domain_handle;
2703 status = dcerpc_samr_TestPrivateFunctionsDomain(p, mem_ctx, &r);
2704 if (!NT_STATUS_EQUAL(NT_STATUS_NOT_IMPLEMENTED, status)) {
2705 printf("TestPrivateFunctionsDomain failed - %s\n", nt_errstr(status));
2712 static BOOL test_RidToSid(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2713 struct policy_handle *domain_handle)
2715 struct samr_RidToSid r;
2719 printf("Testing RidToSid\n");
2721 r.in.domain_handle = domain_handle;
2724 status = dcerpc_samr_RidToSid(p, mem_ctx, &r);
2725 if (!NT_STATUS_IS_OK(status)) {
2726 printf("RidToSid failed - %s\n", nt_errstr(status));
2733 static BOOL test_GetBootKeyInformation(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2734 struct policy_handle *domain_handle)
2736 struct samr_GetBootKeyInformation r;
2740 printf("Testing GetBootKeyInformation\n");
2742 r.in.domain_handle = domain_handle;
2744 status = dcerpc_samr_GetBootKeyInformation(p, mem_ctx, &r);
2745 if (!NT_STATUS_IS_OK(status)) {
2746 /* w2k3 seems to fail this sometimes and pass it sometimes */
2747 printf("GetBootKeyInformation (ignored) - %s\n", nt_errstr(status));
2753 static BOOL test_AddGroupMember(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2754 struct policy_handle *domain_handle,
2755 struct policy_handle *group_handle)
2758 struct samr_AddGroupMember r;
2759 struct samr_DeleteGroupMember d;
2760 struct samr_QueryGroupMember q;
2761 struct samr_SetMemberAttributesOfGroup s;
2765 status = test_LookupName(p, mem_ctx, domain_handle, TEST_ACCOUNT_NAME, &rid);
2766 if (!NT_STATUS_IS_OK(status)) {
2770 r.in.group_handle = group_handle;
2772 r.in.flags = 0; /* ??? */
2774 printf("Testing AddGroupMember and DeleteGroupMember\n");
2776 d.in.group_handle = group_handle;
2779 status = dcerpc_samr_DeleteGroupMember(p, mem_ctx, &d);
2780 if (!NT_STATUS_EQUAL(NT_STATUS_MEMBER_NOT_IN_GROUP, status)) {
2781 printf("DeleteGroupMember gave %s - should be NT_STATUS_MEMBER_NOT_IN_GROUP\n",
2786 status = dcerpc_samr_AddGroupMember(p, mem_ctx, &r);
2787 if (!NT_STATUS_IS_OK(status)) {
2788 printf("AddGroupMember failed - %s\n", nt_errstr(status));
2792 status = dcerpc_samr_AddGroupMember(p, mem_ctx, &r);
2793 if (!NT_STATUS_EQUAL(NT_STATUS_MEMBER_IN_GROUP, status)) {
2794 printf("AddGroupMember gave %s - should be NT_STATUS_MEMBER_IN_GROUP\n",
2799 /* this one is quite strange. I am using random inputs in the
2800 hope of triggering an error that might give us a clue */
2801 s.in.group_handle = group_handle;
2802 s.in.unknown1 = random();
2803 s.in.unknown2 = random();
2805 status = dcerpc_samr_SetMemberAttributesOfGroup(p, mem_ctx, &s);
2806 if (!NT_STATUS_IS_OK(status)) {
2807 printf("SetMemberAttributesOfGroup failed - %s\n", nt_errstr(status));
2811 q.in.group_handle = group_handle;
2813 status = dcerpc_samr_QueryGroupMember(p, mem_ctx, &q);
2814 if (!NT_STATUS_IS_OK(status)) {
2815 printf("QueryGroupMember failed - %s\n", nt_errstr(status));
2819 status = dcerpc_samr_DeleteGroupMember(p, mem_ctx, &d);
2820 if (!NT_STATUS_IS_OK(status)) {
2821 printf("DeleteGroupMember failed - %s\n", nt_errstr(status));
2825 status = dcerpc_samr_AddGroupMember(p, mem_ctx, &r);
2826 if (!NT_STATUS_IS_OK(status)) {
2827 printf("AddGroupMember failed - %s\n", nt_errstr(status));
2835 static BOOL test_CreateDomainGroup(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2836 struct policy_handle *domain_handle, struct policy_handle *group_handle)
2839 struct samr_CreateDomainGroup r;
2841 struct samr_String name;
2844 init_samr_String(&name, TEST_GROUPNAME);
2846 r.in.domain_handle = domain_handle;
2848 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
2849 r.out.group_handle = group_handle;
2852 printf("Testing CreateDomainGroup(%s)\n", r.in.name->string);
2854 status = dcerpc_samr_CreateDomainGroup(p, mem_ctx, &r);
2856 if (NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
2857 printf("Server refused create of '%s'\n", r.in.name->string);
2858 ZERO_STRUCTP(group_handle);
2862 if (NT_STATUS_EQUAL(status, NT_STATUS_GROUP_EXISTS) ||
2863 NT_STATUS_EQUAL(status, NT_STATUS_USER_EXISTS)) {
2864 if (!test_DeleteGroup_byname(p, mem_ctx, domain_handle, r.in.name->string)) {
2867 status = dcerpc_samr_CreateDomainGroup(p, mem_ctx, &r);
2869 if (!NT_STATUS_IS_OK(status)) {
2870 printf("CreateDomainGroup failed - %s\n", nt_errstr(status));
2874 if (!test_AddGroupMember(p, mem_ctx, domain_handle, group_handle)) {
2878 if (!test_SetGroupInfo(p, mem_ctx, group_handle)) {
2887 its not totally clear what this does. It seems to accept any sid you like.
2889 static BOOL test_RemoveMemberFromForeignDomain(struct dcerpc_pipe *p,
2890 TALLOC_CTX *mem_ctx,
2891 struct policy_handle *domain_handle)
2894 struct samr_RemoveMemberFromForeignDomain r;
2896 r.in.domain_handle = domain_handle;
2897 r.in.sid = dom_sid_parse_talloc(mem_ctx, "S-1-5-32-12-34-56-78");
2899 status = dcerpc_samr_RemoveMemberFromForeignDomain(p, mem_ctx, &r);
2900 if (!NT_STATUS_IS_OK(status)) {
2901 printf("RemoveMemberFromForeignDomain failed - %s\n", nt_errstr(status));
2910 static BOOL test_Connect(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2911 struct policy_handle *handle);
2913 static BOOL test_OpenDomain(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2914 struct policy_handle *handle, struct dom_sid *sid)
2917 struct samr_OpenDomain r;
2918 struct policy_handle domain_handle;
2919 struct policy_handle user_handle;
2920 struct policy_handle alias_handle;
2921 struct policy_handle group_handle;
2924 ZERO_STRUCT(user_handle);
2925 ZERO_STRUCT(alias_handle);
2926 ZERO_STRUCT(group_handle);
2927 ZERO_STRUCT(domain_handle);
2929 printf("Testing OpenDomain\n");
2931 r.in.connect_handle = handle;
2932 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
2934 r.out.domain_handle = &domain_handle;
2936 status = dcerpc_samr_OpenDomain(p, mem_ctx, &r);
2937 if (!NT_STATUS_IS_OK(status)) {
2938 printf("OpenDomain failed - %s\n", nt_errstr(status));
2942 /* run the domain tests with the main handle closed - this tests
2943 the servers reference counting */
2944 ret &= test_samr_handle_Close(p, mem_ctx, handle);
2946 ret &= test_QuerySecurity(p, mem_ctx, &domain_handle);
2947 ret &= test_RemoveMemberFromForeignDomain(p, mem_ctx, &domain_handle);
2948 ret &= test_CreateUser2(p, mem_ctx, &domain_handle);
2949 ret &= test_CreateUser(p, mem_ctx, &domain_handle, &user_handle);
2950 ret &= test_CreateAlias(p, mem_ctx, &domain_handle, &alias_handle, sid);
2951 ret &= test_CreateDomainGroup(p, mem_ctx, &domain_handle, &group_handle);
2952 ret &= test_QueryDomainInfo(p, mem_ctx, &domain_handle);
2953 ret &= test_QueryDomainInfo2(p, mem_ctx, &domain_handle);
2954 ret &= test_EnumDomainUsers(p, mem_ctx, &domain_handle);
2955 ret &= test_EnumDomainUsers_async(p, mem_ctx, &domain_handle);
2956 ret &= test_EnumDomainGroups(p, mem_ctx, &domain_handle);
2957 ret &= test_EnumDomainAliases(p, mem_ctx, &domain_handle);
2958 ret &= test_QueryDisplayInfo(p, mem_ctx, &domain_handle);
2959 ret &= test_QueryDisplayInfo2(p, mem_ctx, &domain_handle);
2960 ret &= test_QueryDisplayInfo3(p, mem_ctx, &domain_handle);
2961 ret &= test_GetDisplayEnumerationIndex(p, mem_ctx, &domain_handle);
2962 ret &= test_GetDisplayEnumerationIndex2(p, mem_ctx, &domain_handle);
2963 ret &= test_GroupList(p, mem_ctx, &domain_handle);
2964 ret &= test_TestPrivateFunctionsDomain(p, mem_ctx, &domain_handle);
2965 ret &= test_RidToSid(p, mem_ctx, &domain_handle);
2966 ret &= test_GetBootKeyInformation(p, mem_ctx, &domain_handle);
2968 if (!policy_handle_empty(&user_handle) &&
2969 !test_DeleteUser(p, mem_ctx, &user_handle)) {
2973 if (!policy_handle_empty(&alias_handle) &&
2974 !test_DeleteAlias(p, mem_ctx, &alias_handle)) {
2978 if (!policy_handle_empty(&group_handle) &&
2979 !test_DeleteDomainGroup(p, mem_ctx, &group_handle)) {
2983 ret &= test_samr_handle_Close(p, mem_ctx, &domain_handle);
2985 /* reconnect the main handle */
2986 ret &= test_Connect(p, mem_ctx, handle);
2991 static BOOL test_LookupDomain(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
2992 struct policy_handle *handle, struct samr_String *domain)
2995 struct samr_LookupDomain r;
2996 struct samr_String n2;
2999 printf("Testing LookupDomain(%s)\n", domain->string);
3001 /* check for correct error codes */
3002 r.in.connect_handle = handle;
3003 r.in.domain_name = &n2;
3006 status = dcerpc_samr_LookupDomain(p, mem_ctx, &r);
3007 if (!NT_STATUS_EQUAL(NT_STATUS_INVALID_PARAMETER, status)) {
3008 printf("failed: LookupDomain expected NT_STATUS_INVALID_PARAMETER - %s\n", nt_errstr(status));
3012 n2.string = "xxNODOMAINxx";
3014 status = dcerpc_samr_LookupDomain(p, mem_ctx, &r);
3015 if (!NT_STATUS_EQUAL(NT_STATUS_NO_SUCH_DOMAIN, status)) {
3016 printf("failed: LookupDomain expected NT_STATUS_NO_SUCH_DOMAIN - %s\n", nt_errstr(status));
3020 r.in.connect_handle = handle;
3021 r.in.domain_name = domain;
3023 status = dcerpc_samr_LookupDomain(p, mem_ctx, &r);
3024 if (!NT_STATUS_IS_OK(status)) {
3025 printf("LookupDomain failed - %s\n", nt_errstr(status));
3029 if (!test_GetDomPwInfo(p, mem_ctx, domain)) {
3033 if (!test_OpenDomain(p, mem_ctx, handle, r.out.sid)) {
3041 static BOOL test_EnumDomains(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
3042 struct policy_handle *handle)
3045 struct samr_EnumDomains r;
3046 uint32_t resume_handle = 0;
3050 r.in.connect_handle = handle;
3051 r.in.resume_handle = &resume_handle;
3052 r.in.buf_size = (uint32_t)-1;
3053 r.out.resume_handle = &resume_handle;
3055 status = dcerpc_samr_EnumDomains(p, mem_ctx, &r);
3056 if (!NT_STATUS_IS_OK(status)) {
3057 printf("EnumDomains failed - %s\n", nt_errstr(status));
3065 for (i=0;i<r.out.sam->count;i++) {
3066 if (!test_LookupDomain(p, mem_ctx, handle,
3067 &r.out.sam->entries[i].name)) {
3072 status = dcerpc_samr_EnumDomains(p, mem_ctx, &r);
3073 if (!NT_STATUS_IS_OK(status)) {
3074 printf("EnumDomains failed - %s\n", nt_errstr(status));
3082 static BOOL test_Connect(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
3083 struct policy_handle *handle)
3086 struct samr_Connect r;
3087 struct samr_Connect2 r2;
3088 struct samr_Connect3 r3;
3089 struct samr_Connect4 r4;
3090 struct samr_Connect5 r5;
3091 union samr_ConnectInfo info;
3092 struct policy_handle h;
3093 BOOL ret = True, got_handle = False;
3095 printf("testing samr_Connect\n");
3097 r.in.system_name = 0;
3098 r.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
3099 r.out.connect_handle = &h;
3101 status = dcerpc_samr_Connect(p, mem_ctx, &r);
3102 if (!NT_STATUS_IS_OK(status)) {
3103 printf("Connect failed - %s\n", nt_errstr(status));
3110 printf("testing samr_Connect2\n");
3112 r2.in.system_name = NULL;
3113 r2.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
3114 r2.out.connect_handle = &h;
3116 status = dcerpc_samr_Connect2(p, mem_ctx, &r2);
3117 if (!NT_STATUS_IS_OK(status)) {
3118 printf("Connect2 failed - %s\n", nt_errstr(status));
3122 test_samr_handle_Close(p, mem_ctx, handle);
3128 printf("testing samr_Connect3\n");
3130 r3.in.system_name = NULL;
3132 r3.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
3133 r3.out.connect_handle = &h;
3135 status = dcerpc_samr_Connect3(p, mem_ctx, &r3);
3136 if (!NT_STATUS_IS_OK(status)) {
3137 printf("Connect3 failed - %s\n", nt_errstr(status));
3141 test_samr_handle_Close(p, mem_ctx, handle);
3147 printf("testing samr_Connect4\n");
3149 r4.in.system_name = "";
3151 r4.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
3152 r4.out.connect_handle = &h;
3154 status = dcerpc_samr_Connect4(p, mem_ctx, &r4);
3155 if (!NT_STATUS_IS_OK(status)) {
3156 printf("Connect4 failed - %s\n", nt_errstr(status));
3160 test_samr_handle_Close(p, mem_ctx, handle);
3166 printf("testing samr_Connect5\n");
3168 info.info1.unknown1 = 0;
3169 info.info1.unknown2 = 0;
3171 r5.in.system_name = "";
3172 r5.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
3175 r5.out.info = &info;
3176 r5.out.connect_handle = &h;
3178 status = dcerpc_samr_Connect5(p, mem_ctx, &r5);
3179 if (!NT_STATUS_IS_OK(status)) {
3180 printf("Connect5 failed - %s\n", nt_errstr(status));
3184 test_samr_handle_Close(p, mem_ctx, handle);
3194 BOOL torture_rpc_samr(void)
3197 struct dcerpc_pipe *p;
3198 TALLOC_CTX *mem_ctx;
3200 struct policy_handle handle;
3202 mem_ctx = talloc_init("torture_rpc_samr");
3204 status = torture_rpc_connection(mem_ctx,
3208 DCERPC_SAMR_VERSION);
3209 if (!NT_STATUS_IS_OK(status)) {
3210 talloc_free(mem_ctx);
3214 if (!test_Connect(p, mem_ctx, &handle)) {
3218 if (!test_QuerySecurity(p, mem_ctx, &handle)) {
3222 if (!test_EnumDomains(p, mem_ctx, &handle)) {
3226 if (!test_SetDsrmPassword(p, mem_ctx, &handle)) {
3230 if (!test_Shutdown(p, mem_ctx, &handle)) {
3234 if (!test_samr_handle_Close(p, mem_ctx, &handle)) {
3238 talloc_free(mem_ctx);