2 Unix SMB/CIFS implementation.
3 test suite for samr rpc operations
5 Copyright (C) Andrew Tridgell 2003
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
25 static BOOL test_QueryUserInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
26 struct policy_handle *handle);
29 this makes the debug code display the right thing
31 static void init_samr_Name(struct samr_Name *name, const char *s)
33 name->name_len = strlen_m(s)*2;
34 name->name_size = name->name_len;
35 if (name->name_len == 0) {
42 static BOOL test_Close(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
43 struct policy_handle *handle)
49 r.out.handle = handle;
51 status = dcerpc_samr_Close(p, mem_ctx, &r);
52 if (!NT_STATUS_IS_OK(status)) {
53 printf("Close handle failed - %s\n", nt_errstr(status));
61 static BOOL test_QuerySecurity(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
62 struct policy_handle *handle)
65 struct samr_QuerySecurity r;
70 status = dcerpc_samr_QuerySecurity(p, mem_ctx, &r);
71 if (!NT_STATUS_IS_OK(status)) {
72 printf("QuerySecurity failed - %s\n", nt_errstr(status));
80 static BOOL test_SetUserInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
81 struct policy_handle *handle)
84 struct samr_SetUserInfo s;
85 struct samr_QueryUserInfo q;
86 struct samr_QueryUserInfo q0;
87 union samr_UserInfo u;
96 #define TESTCALL(call, r) \
97 status = dcerpc_samr_ ##call(p, mem_ctx, &r); \
98 if (!NT_STATUS_IS_OK(status)) { \
99 printf(#call " level %u failed - %s (line %d)\n", \
100 r.in.level, nt_errstr(status), __LINE__); \
105 #define STRING_EQUAL(s1, s2, field) \
106 if ((s1 && !s2) || (s2 && !s1) || strcmp(s1, s2)) { \
107 printf("Failed to set %s to '%s' (line %d)\n", \
108 #field, s2, __LINE__); \
113 #define INT_EQUAL(i1, i2, field) \
115 printf("Failed to set %s to %u (line %d)\n", \
116 #field, i2, __LINE__); \
121 #define TEST_USERINFO_NAME(lvl1, field1, lvl2, field2, value) do { \
122 printf("field test %d/%s vs %d/%s\n", lvl1, #field1, lvl2, #field2); \
124 TESTCALL(QueryUserInfo, q) \
127 init_samr_Name(&u.info ## lvl1.field1, value); \
128 TESTCALL(SetUserInfo, s) \
129 init_samr_Name(&u.info ## lvl1.field1, ""); \
130 TESTCALL(QueryUserInfo, q); \
132 STRING_EQUAL(u.info ## lvl1.field1.name, value, field1); \
134 TESTCALL(QueryUserInfo, q) \
136 STRING_EQUAL(u.info ## lvl2.field2.name, value, field2); \
139 #define TEST_USERINFO_INT(lvl1, field1, lvl2, field2, value) do { \
140 printf("field test %d/%s vs %d/%s\n", lvl1, #field1, lvl2, #field2); \
142 TESTCALL(QueryUserInfo, q) \
145 u.info ## lvl1.field1 = value; \
146 TESTCALL(SetUserInfo, s) \
147 u.info ## lvl1.field1 = 0; \
148 TESTCALL(QueryUserInfo, q); \
150 INT_EQUAL(u.info ## lvl1.field1, value, field1); \
152 TESTCALL(QueryUserInfo, q) \
154 INT_EQUAL(u.info ## lvl2.field2, value, field1); \
158 do { TESTCALL(QueryUserInfo, q0) } while (0);
160 TEST_USERINFO_NAME(2, comment, 1, comment, "xx2-1 comment");
161 TEST_USERINFO_NAME(2, comment, 21, comment, "xx2-21 comment");
163 TEST_USERINFO_NAME(6, full_name, 1, full_name, "xx6-1 full_name");
164 TEST_USERINFO_NAME(6, full_name, 3, full_name, "xx6-3 full_name");
165 TEST_USERINFO_NAME(6, full_name, 5, full_name, "xx6-5 full_name");
166 TEST_USERINFO_NAME(6, full_name, 6, full_name, "xx6-6 full_name");
167 TEST_USERINFO_NAME(6, full_name, 8, full_name, "xx6-8 full_name");
168 TEST_USERINFO_NAME(6, full_name, 21, full_name, "xx6-21 full_name");
169 TEST_USERINFO_NAME(8, full_name, 21, full_name, "xx7-21 full_name");
171 TEST_USERINFO_NAME(11, logon_script, 3, logon_script, "xx11-3 logon_script");
172 TEST_USERINFO_NAME(11, logon_script, 5, logon_script, "xx11-5 logon_script");
173 TEST_USERINFO_NAME(11, logon_script, 21, logon_script, "xx11-21 logon_script");
175 TEST_USERINFO_NAME(12, profile, 3, profile, "xx12-3 profile");
176 TEST_USERINFO_NAME(12, profile, 5, profile, "xx12-5 profile");
177 TEST_USERINFO_NAME(12, profile, 21, profile, "xx12-21 profile");
179 TEST_USERINFO_NAME(13, description, 1, description, "xx13-1 description");
180 TEST_USERINFO_NAME(13, description, 5, description, "xx13-5 description");
181 TEST_USERINFO_NAME(13, description, 21, description, "xx13-21 description");
183 TEST_USERINFO_NAME(14, workstations, 3, workstations, "testworkstation3");
184 TEST_USERINFO_NAME(14, workstations, 5, workstations, "testworkstation5");
185 TEST_USERINFO_NAME(14, workstations, 21, workstations, "testworkstation21");
187 TEST_USERINFO_NAME(20, callback, 21, callback, "xx20-21 callback");
189 TEST_USERINFO_INT(2, country_code, 21, country_code, __LINE__);
190 TEST_USERINFO_INT(2, code_page, 21, code_page, __LINE__);
192 TEST_USERINFO_INT(4, logon_hours[3], 3, logon_hours[3], __LINE__);
193 TEST_USERINFO_INT(4, logon_hours[3], 5, logon_hours[3], __LINE__);
194 TEST_USERINFO_INT(4, logon_hours[3], 21, logon_hours[3], __LINE__);
196 TEST_USERINFO_INT(9, primary_gid, 1, primary_gid, 513);
197 TEST_USERINFO_INT(9, primary_gid, 3, primary_gid, 513);
198 TEST_USERINFO_INT(9, primary_gid, 5, primary_gid, 513);
199 TEST_USERINFO_INT(9, primary_gid, 21, primary_gid, 513);
205 static BOOL test_user_ops(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
206 struct policy_handle *handle)
210 if (!test_QuerySecurity(p, mem_ctx, handle)) {
214 if (!test_QueryUserInfo(p, mem_ctx, handle)) {
218 if (!test_SetUserInfo(p, mem_ctx, handle)) {
226 static BOOL test_DeleteUser_byname(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
227 struct policy_handle *handle, const char *name)
230 struct samr_LookupNames n;
231 struct samr_OpenUser r;
232 struct samr_DeleteUser d;
233 struct policy_handle acct_handle;
234 struct samr_Name sname;
236 init_samr_Name(&sname, name);
238 n.in.handle = handle;
241 status = dcerpc_samr_LookupNames(p, mem_ctx, &n);
242 if (!NT_STATUS_IS_OK(status)) {
246 r.in.handle = handle;
247 r.in.access_mask = SEC_RIGHTS_MAXIMUM_ALLOWED;
248 r.in.rid = n.out.rids.ids[0];
249 r.out.acct_handle = &acct_handle;
250 status = dcerpc_samr_OpenUser(p, mem_ctx, &r);
251 if (!NT_STATUS_IS_OK(status)) {
255 d.in.handle = &acct_handle;
256 d.out.handle = &acct_handle;
257 status = dcerpc_samr_DeleteUser(p, mem_ctx, &d);
258 if (!NT_STATUS_IS_OK(status)) {
265 printf("DeleteUser_byname(%s) failed - %s\n", name, nt_errstr(status));
270 static BOOL test_CreateUser(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
271 struct policy_handle *handle)
274 struct samr_CreateUser r;
275 struct samr_DeleteUser d;
276 struct policy_handle acct_handle;
278 struct samr_Name name;
281 init_samr_Name(&name, "samrtorturetest");
283 r.in.handle = handle;
284 r.in.username = &name;
285 r.in.access_mask = SEC_RIGHTS_MAXIMUM_ALLOWED;
286 r.out.acct_handle = &acct_handle;
289 printf("Testing CreateUser(%s)\n", r.in.username->name);
291 status = dcerpc_samr_CreateUser(p, mem_ctx, &r);
293 if (NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
294 printf("Server refused create of '%s'\n", r.in.username->name);
298 if (NT_STATUS_EQUAL(status, NT_STATUS_USER_EXISTS)) {
299 if (!test_DeleteUser_byname(p, mem_ctx, handle, r.in.username->name)) {
302 status = dcerpc_samr_CreateUser(p, mem_ctx, &r);
304 if (!NT_STATUS_IS_OK(status)) {
305 printf("CreateUser failed - %s\n", nt_errstr(status));
310 if (!test_user_ops(p, mem_ctx, &acct_handle)) {
314 printf("Testing DeleteUser\n");
316 d.in.handle = &acct_handle;
317 d.out.handle = &acct_handle;
319 status = dcerpc_samr_DeleteUser(p, mem_ctx, &d);
320 if (!NT_STATUS_IS_OK(status)) {
321 printf("DeleteUser failed - %s\n", nt_errstr(status));
328 static BOOL test_QueryAliasInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
329 struct policy_handle *handle)
332 struct samr_QueryAliasInfo r;
333 uint16 levels[] = {1, 2, 3};
337 for (i=0;i<ARRAY_SIZE(levels);i++) {
338 printf("Testing QueryAliasInfo level %u\n", levels[i]);
340 r.in.handle = handle;
341 r.in.level = levels[i];
343 status = dcerpc_samr_QueryAliasInfo(p, mem_ctx, &r);
344 if (!NT_STATUS_IS_OK(status)) {
345 printf("QueryAliasInfo level %u failed - %s\n",
346 levels[i], nt_errstr(status));
354 static BOOL test_QueryGroupInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
355 struct policy_handle *handle)
358 struct samr_QueryGroupInfo r;
359 uint16 levels[] = {1, 2, 3, 4};
363 for (i=0;i<ARRAY_SIZE(levels);i++) {
364 printf("Testing QueryGroupInfo level %u\n", levels[i]);
366 r.in.handle = handle;
367 r.in.level = levels[i];
369 status = dcerpc_samr_QueryGroupInfo(p, mem_ctx, &r);
370 if (!NT_STATUS_IS_OK(status)) {
371 printf("QueryGroupInfo level %u failed - %s\n",
372 levels[i], nt_errstr(status));
380 static BOOL test_QueryUserInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
381 struct policy_handle *handle)
384 struct samr_QueryUserInfo r;
385 uint16 levels[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
386 11, 12, 13, 14, 16, 17, 20, 21};
390 for (i=0;i<ARRAY_SIZE(levels);i++) {
391 printf("Testing QueryUserInfo level %u\n", levels[i]);
393 r.in.handle = handle;
394 r.in.level = levels[i];
396 status = dcerpc_samr_QueryUserInfo(p, mem_ctx, &r);
397 if (!NT_STATUS_IS_OK(status)) {
398 printf("QueryUserInfo level %u failed - %s\n",
399 levels[i], nt_errstr(status));
407 static BOOL test_OpenUser(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
408 struct policy_handle *handle, uint32 rid)
411 struct samr_OpenUser r;
412 struct policy_handle acct_handle;
415 printf("Testing OpenUser(%u)\n", rid);
417 r.in.handle = handle;
418 r.in.access_mask = SEC_RIGHTS_MAXIMUM_ALLOWED;
420 r.out.acct_handle = &acct_handle;
422 status = dcerpc_samr_OpenUser(p, mem_ctx, &r);
423 if (!NT_STATUS_IS_OK(status)) {
424 printf("OpenUser(%u) failed - %s\n", rid, nt_errstr(status));
428 if (!test_QuerySecurity(p, mem_ctx, &acct_handle)) {
432 if (!test_QueryUserInfo(p, mem_ctx, &acct_handle)) {
436 if (!test_Close(p, mem_ctx, &acct_handle)) {
443 static BOOL test_OpenGroup(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
444 struct policy_handle *handle, uint32 rid)
447 struct samr_OpenGroup r;
448 struct policy_handle acct_handle;
451 printf("Testing OpenGroup(%u)\n", rid);
453 r.in.handle = handle;
454 r.in.access_mask = SEC_RIGHTS_MAXIMUM_ALLOWED;
456 r.out.acct_handle = &acct_handle;
458 status = dcerpc_samr_OpenGroup(p, mem_ctx, &r);
459 if (!NT_STATUS_IS_OK(status)) {
460 printf("OpenGroup(%u) failed - %s\n", rid, nt_errstr(status));
464 if (!test_QuerySecurity(p, mem_ctx, &acct_handle)) {
468 if (!test_QueryGroupInfo(p, mem_ctx, &acct_handle)) {
472 if (!test_Close(p, mem_ctx, &acct_handle)) {
479 static BOOL test_OpenAlias(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
480 struct policy_handle *handle, uint32 rid)
483 struct samr_OpenAlias r;
484 struct policy_handle acct_handle;
487 printf("Testing OpenAlias(%u)\n", rid);
489 r.in.handle = handle;
490 r.in.access_mask = SEC_RIGHTS_MAXIMUM_ALLOWED;
492 r.out.acct_handle = &acct_handle;
494 status = dcerpc_samr_OpenAlias(p, mem_ctx, &r);
495 if (!NT_STATUS_IS_OK(status)) {
496 printf("OpenAlias(%u) failed - %s\n", rid, nt_errstr(status));
500 if (!test_QuerySecurity(p, mem_ctx, &acct_handle)) {
504 if (!test_QueryAliasInfo(p, mem_ctx, &acct_handle)) {
508 if (!test_Close(p, mem_ctx, &acct_handle)) {
515 static BOOL test_EnumDomainUsers(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
516 struct policy_handle *handle)
519 struct samr_EnumDomainUsers r;
520 uint32 resume_handle=0;
523 struct samr_LookupNames n;
524 struct samr_LookupRids lr ;
526 printf("Testing EnumDomainUsers\n");
528 r.in.handle = handle;
529 r.in.resume_handle = &resume_handle;
531 r.in.max_size = (uint32)-1;
532 r.out.resume_handle = &resume_handle;
534 status = dcerpc_samr_EnumDomainUsers(p, mem_ctx, &r);
535 if (!NT_STATUS_IS_OK(status)) {
536 printf("EnumDomainUsers failed - %s\n", nt_errstr(status));
544 if (r.out.sam->count == 0) {
548 for (i=0;i<r.out.sam->count;i++) {
549 if (!test_OpenUser(p, mem_ctx, handle, r.out.sam->entries[i].idx)) {
554 printf("Testing LookupNames\n");
555 n.in.handle = handle;
556 n.in.num_names = r.out.sam->count;
557 n.in.names = talloc(mem_ctx, r.out.sam->count * sizeof(struct samr_Name));
558 for (i=0;i<r.out.sam->count;i++) {
559 n.in.names[i] = r.out.sam->entries[i].name;
561 status = dcerpc_samr_LookupNames(p, mem_ctx, &n);
562 if (!NT_STATUS_IS_OK(status)) {
563 printf("LookupNames failed - %s\n", nt_errstr(status));
568 printf("Testing LookupRids\n");
569 lr.in.handle = handle;
570 lr.in.num_rids = r.out.sam->count;
571 lr.in.rids = talloc(mem_ctx, r.out.sam->count * sizeof(uint32));
572 for (i=0;i<r.out.sam->count;i++) {
573 lr.in.rids[i] = r.out.sam->entries[i].idx;
575 status = dcerpc_samr_LookupRids(p, mem_ctx, &lr);
576 if (!NT_STATUS_IS_OK(status)) {
577 printf("LookupRids failed - %s\n", nt_errstr(status));
584 static BOOL test_EnumDomainGroups(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
585 struct policy_handle *handle)
588 struct samr_EnumDomainGroups r;
589 uint32 resume_handle=0;
593 printf("Testing EnumDomainGroups\n");
595 r.in.handle = handle;
596 r.in.resume_handle = &resume_handle;
597 r.in.max_size = (uint32)-1;
598 r.out.resume_handle = &resume_handle;
600 status = dcerpc_samr_EnumDomainGroups(p, mem_ctx, &r);
601 if (!NT_STATUS_IS_OK(status)) {
602 printf("EnumDomainGroups failed - %s\n", nt_errstr(status));
610 for (i=0;i<r.out.sam->count;i++) {
611 if (!test_OpenGroup(p, mem_ctx, handle, r.out.sam->entries[i].idx)) {
619 static BOOL test_EnumDomainAliases(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
620 struct policy_handle *handle)
623 struct samr_EnumDomainAliases r;
624 uint32 resume_handle=0;
628 printf("Testing EnumDomainAliases\n");
630 r.in.handle = handle;
631 r.in.resume_handle = &resume_handle;
632 r.in.max_size = (uint32)-1;
633 r.out.resume_handle = &resume_handle;
635 status = dcerpc_samr_EnumDomainAliases(p, mem_ctx, &r);
636 if (!NT_STATUS_IS_OK(status)) {
637 printf("EnumDomainAliases failed - %s\n", nt_errstr(status));
645 for (i=0;i<r.out.sam->count;i++) {
646 if (!test_OpenAlias(p, mem_ctx, handle, r.out.sam->entries[i].idx)) {
654 static BOOL test_QueryDomainInfo(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
655 struct policy_handle *handle)
658 struct samr_QueryDomainInfo r;
659 uint16 levels[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 11, 12, 13};
663 for (i=0;i<ARRAY_SIZE(levels);i++) {
664 printf("Testing QueryDomainInfo level %u\n", levels[i]);
666 r.in.handle = handle;
667 r.in.level = levels[i];
669 status = dcerpc_samr_QueryDomainInfo(p, mem_ctx, &r);
670 if (!NT_STATUS_IS_OK(status)) {
671 printf("QueryDomainInfo level %u failed - %s\n",
672 r.in.level, nt_errstr(status));
681 static BOOL test_OpenDomain(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
682 struct policy_handle *handle, struct dom_sid2 *sid)
685 struct samr_OpenDomain r;
686 struct policy_handle domain_handle;
689 printf("Testing OpenDomain\n");
691 r.in.handle = handle;
692 r.in.access_mask = SEC_RIGHTS_MAXIMUM_ALLOWED;
694 r.out.domain_handle = &domain_handle;
696 status = dcerpc_samr_OpenDomain(p, mem_ctx, &r);
697 if (!NT_STATUS_IS_OK(status)) {
698 printf("OpenDomain failed - %s\n", nt_errstr(status));
702 if (!test_CreateUser(p, mem_ctx, &domain_handle)) {
706 if (!test_QuerySecurity(p, mem_ctx, &domain_handle)) {
710 if (!test_QueryDomainInfo(p, mem_ctx, &domain_handle)) {
714 if (!test_EnumDomainUsers(p, mem_ctx, &domain_handle)) {
718 if (!test_EnumDomainGroups(p, mem_ctx, &domain_handle)) {
722 if (!test_EnumDomainAliases(p, mem_ctx, &domain_handle)) {
726 if (!test_Close(p, mem_ctx, &domain_handle)) {
733 static BOOL test_LookupDomain(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
734 struct policy_handle *handle, struct samr_Name *domain)
737 struct samr_LookupDomain r;
739 printf("Testing LookupDomain(%s)\n", domain->name);
741 r.in.handle = handle;
742 r.in.domain = domain;
744 status = dcerpc_samr_LookupDomain(p, mem_ctx, &r);
745 if (!NT_STATUS_IS_OK(status)) {
746 printf("LookupDomain failed - %s\n", nt_errstr(status));
750 if (!test_OpenDomain(p, mem_ctx, handle, r.out.sid)) {
758 static BOOL test_EnumDomains(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
759 struct policy_handle *handle)
762 struct samr_EnumDomains r;
763 uint32 resume_handle = 0;
764 uint32 num_entries=0;
768 r.in.handle = handle;
769 r.in.resume_handle = &resume_handle;
770 r.in.buf_size = (uint32)-1;
771 r.out.resume_handle = &resume_handle;
772 r.out.num_entries = &num_entries;
774 status = dcerpc_samr_EnumDomains(p, mem_ctx, &r);
775 if (!NT_STATUS_IS_OK(status)) {
776 printf("EnumDomains failed - %s\n", nt_errstr(status));
784 for (i=0;i<r.out.sam->count;i++) {
785 if (!test_LookupDomain(p, mem_ctx, handle,
786 &r.out.sam->entries[i].name)) {
795 static BOOL test_Connect(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx,
796 struct policy_handle *handle)
799 struct samr_Connect r;
800 struct samr_Connect4 r4;
802 r.in.system_name = 0;
803 r.in.access_mask = SEC_RIGHTS_MAXIMUM_ALLOWED;
804 r.out.handle = handle;
806 status = dcerpc_samr_Connect(p, mem_ctx, &r);
807 if (!NT_STATUS_IS_OK(status)) {
808 printf("Connect failed - %s\n", nt_errstr(status));
812 r4.in.system_name = "";
814 r4.in.access_mask = SEC_RIGHTS_MAXIMUM_ALLOWED;
815 r4.out.handle = handle;
817 status = dcerpc_samr_Connect4(p, mem_ctx, &r4);
818 if (!NT_STATUS_IS_OK(status)) {
819 printf("Connect4 failed - %s\n", nt_errstr(status));
827 BOOL torture_rpc_samr(int dummy)
830 struct dcerpc_pipe *p;
833 struct policy_handle handle;
835 mem_ctx = talloc_init("torture_rpc_samr");
837 status = torture_rpc_connection(&p,
840 DCERPC_SAMR_VERSION);
841 if (!NT_STATUS_IS_OK(status)) {
845 p->flags |= DCERPC_DEBUG_PRINT_BOTH;
847 if (!test_Connect(p, mem_ctx, &handle)) {
851 if (!test_QuerySecurity(p, mem_ctx, &handle)) {
855 if (!test_EnumDomains(p, mem_ctx, &handle)) {
859 if (!test_Close(p, mem_ctx, &handle)) {
863 torture_rpc_close(p);