2 Unix SMB/CIFS implementation.
4 test suite for netlogon rpc operations
6 Copyright (C) Andrew Tridgell 2003
7 Copyright (C) Andrew Bartlett <abartlet@samba.org> 2003-2004
8 Copyright (C) Tim Potter 2003
10 This program is free software; you can redistribute it and/or modify
11 it under the terms of the GNU General Public License as published by
12 the Free Software Foundation; either version 3 of the License, or
13 (at your option) any later version.
15 This program is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 GNU General Public License for more details.
20 You should have received a copy of the GNU General Public License
21 along with this program. If not, see <http://www.gnu.org/licenses/>.
25 #include "torture/torture.h"
26 #include "lib/events/events.h"
27 #include "auth/auth.h"
28 #include "auth/gensec/gensec.h"
29 #include "lib/cmdline/popt_common.h"
30 #include "torture/rpc/rpc.h"
31 #include "torture/rpc/netlogon.h"
32 #include "../lib/crypto/crypto.h"
33 #include "libcli/auth/libcli_auth.h"
34 #include "librpc/gen_ndr/ndr_netlogon_c.h"
35 #include "librpc/gen_ndr/ndr_lsa_c.h"
36 #include "param/param.h"
38 #define TEST_MACHINE_NAME "torturetest"
40 static bool test_LogonUasLogon(struct torture_context *tctx,
41 struct dcerpc_pipe *p)
44 struct netr_LogonUasLogon r;
45 struct netr_UasInfo *info = NULL;
47 r.in.server_name = NULL;
48 r.in.account_name = cli_credentials_get_username(cmdline_credentials);
49 r.in.workstation = TEST_MACHINE_NAME;
52 status = dcerpc_netr_LogonUasLogon(p, tctx, &r);
53 torture_assert_ntstatus_ok(tctx, status, "LogonUasLogon");
58 static bool test_LogonUasLogoff(struct torture_context *tctx,
59 struct dcerpc_pipe *p)
62 struct netr_LogonUasLogoff r;
63 struct netr_UasLogoffInfo info;
65 r.in.server_name = NULL;
66 r.in.account_name = cli_credentials_get_username(cmdline_credentials);
67 r.in.workstation = TEST_MACHINE_NAME;
70 status = dcerpc_netr_LogonUasLogoff(p, tctx, &r);
71 torture_assert_ntstatus_ok(tctx, status, "LogonUasLogoff");
76 static bool test_SetupCredentials(struct dcerpc_pipe *p, struct torture_context *tctx,
77 struct cli_credentials *credentials,
78 struct creds_CredentialState **creds_out)
81 struct netr_ServerReqChallenge r;
82 struct netr_ServerAuthenticate a;
83 struct netr_Credential credentials1, credentials2, credentials3;
84 struct creds_CredentialState *creds;
85 const struct samr_Password *mach_password;
86 const char *machine_name;
88 mach_password = cli_credentials_get_nt_hash(credentials, tctx);
89 machine_name = cli_credentials_get_workstation(credentials);
91 torture_comment(tctx, "Testing ServerReqChallenge\n");
93 creds = talloc(tctx, struct creds_CredentialState);
94 torture_assert(tctx, creds != NULL, "memory allocation");
96 r.in.server_name = NULL;
97 r.in.computer_name = machine_name;
98 r.in.credentials = &credentials1;
99 r.out.return_credentials = &credentials2;
101 generate_random_buffer(credentials1.data, sizeof(credentials1.data));
103 status = dcerpc_netr_ServerReqChallenge(p, tctx, &r);
104 torture_assert_ntstatus_ok(tctx, status, "ServerReqChallenge");
106 a.in.server_name = NULL;
107 a.in.account_name = talloc_asprintf(tctx, "%s$", machine_name);
108 a.in.secure_channel_type = SEC_CHAN_BDC;
109 a.in.computer_name = machine_name;
110 a.in.credentials = &credentials3;
111 a.out.return_credentials = &credentials3;
113 creds_client_init(creds, &credentials1, &credentials2,
114 mach_password, &credentials3,
117 torture_comment(tctx, "Testing ServerAuthenticate\n");
119 status = dcerpc_netr_ServerAuthenticate(p, tctx, &a);
121 /* This allows the tests to continue against the more fussy windows 2008 */
122 if (NT_STATUS_EQUAL(status, NT_STATUS_DOWNGRADE_DETECTED)) {
123 return test_SetupCredentials2(p, tctx, NETLOGON_NEG_AUTH2_ADS_FLAGS,
124 credentials, SEC_CHAN_BDC, creds_out);
127 torture_assert_ntstatus_ok(tctx, status, "ServerAuthenticate");
129 torture_assert(tctx, creds_client_check(creds, &credentials3),
130 "Credential chaining failed");
136 bool test_SetupCredentials2(struct dcerpc_pipe *p, struct torture_context *tctx,
137 uint32_t negotiate_flags,
138 struct cli_credentials *machine_credentials,
140 struct creds_CredentialState **creds_out)
143 struct netr_ServerReqChallenge r;
144 struct netr_ServerAuthenticate2 a;
145 struct netr_Credential credentials1, credentials2, credentials3;
146 struct creds_CredentialState *creds;
147 const struct samr_Password *mach_password;
148 const char *machine_name;
149 const char *plain_pass;
151 mach_password = cli_credentials_get_nt_hash(machine_credentials, tctx);
152 machine_name = cli_credentials_get_workstation(machine_credentials);
154 torture_comment(tctx, "Testing ServerReqChallenge\n");
156 creds = talloc(tctx, struct creds_CredentialState);
157 torture_assert(tctx, creds != NULL, "memory allocation");
159 r.in.server_name = NULL;
160 r.in.computer_name = machine_name;
161 r.in.credentials = &credentials1;
162 r.out.return_credentials = &credentials2;
164 generate_random_buffer(credentials1.data, sizeof(credentials1.data));
166 status = dcerpc_netr_ServerReqChallenge(p, tctx, &r);
167 torture_assert_ntstatus_ok(tctx, status, "ServerReqChallenge");
169 a.in.server_name = NULL;
170 a.in.account_name = talloc_asprintf(tctx, "%s$", machine_name);
171 a.in.secure_channel_type = sec_chan_type;
172 a.in.computer_name = machine_name;
173 a.in.negotiate_flags = &negotiate_flags;
174 a.out.negotiate_flags = &negotiate_flags;
175 a.in.credentials = &credentials3;
176 a.out.return_credentials = &credentials3;
178 creds_client_init(creds, &credentials1, &credentials2,
179 mach_password, &credentials3,
182 torture_comment(tctx, "Testing ServerAuthenticate2\n");
184 status = dcerpc_netr_ServerAuthenticate2(p, tctx, &a);
185 torture_assert_ntstatus_ok(tctx, status, "ServerAuthenticate2");
187 torture_assert(tctx, creds_client_check(creds, &credentials3),
188 "Credential chaining failed");
190 torture_comment(tctx, "negotiate_flags=0x%08x\n", negotiate_flags);
197 static bool test_SetupCredentials3(struct dcerpc_pipe *p, struct torture_context *tctx,
198 uint32_t negotiate_flags,
199 struct cli_credentials *machine_credentials,
200 struct creds_CredentialState **creds_out)
203 struct netr_ServerReqChallenge r;
204 struct netr_ServerAuthenticate3 a;
205 struct netr_Credential credentials1, credentials2, credentials3;
206 struct creds_CredentialState *creds;
207 struct samr_Password mach_password;
209 const char *machine_name;
210 const char *plain_pass;
212 machine_name = cli_credentials_get_workstation(machine_credentials);
213 plain_pass = cli_credentials_get_password(machine_credentials);
215 torture_comment(tctx, "Testing ServerReqChallenge\n");
217 creds = talloc(tctx, struct creds_CredentialState);
218 torture_assert(tctx, creds != NULL, "memory allocation");
220 r.in.server_name = NULL;
221 r.in.computer_name = machine_name;
222 r.in.credentials = &credentials1;
223 r.out.return_credentials = &credentials2;
225 generate_random_buffer(credentials1.data, sizeof(credentials1.data));
227 status = dcerpc_netr_ServerReqChallenge(p, tctx, &r);
228 torture_assert_ntstatus_ok(tctx, status, "ServerReqChallenge");
230 E_md4hash(plain_pass, mach_password.hash);
232 a.in.server_name = NULL;
233 a.in.account_name = talloc_asprintf(tctx, "%s$", machine_name);
234 a.in.secure_channel_type = SEC_CHAN_BDC;
235 a.in.computer_name = machine_name;
236 a.in.negotiate_flags = &negotiate_flags;
237 a.in.credentials = &credentials3;
238 a.out.return_credentials = &credentials3;
239 a.out.negotiate_flags = &negotiate_flags;
242 creds_client_init(creds, &credentials1, &credentials2,
243 &mach_password, &credentials3,
246 torture_comment(tctx, "Testing ServerAuthenticate3\n");
248 status = dcerpc_netr_ServerAuthenticate3(p, tctx, &a);
249 torture_assert_ntstatus_ok(tctx, status, "ServerAuthenticate3");
250 torture_assert(tctx, creds_client_check(creds, &credentials3), "Credential chaining failed");
252 torture_comment(tctx, "negotiate_flags=0x%08x\n", negotiate_flags);
254 /* Prove that requesting a challenge again won't break it */
255 status = dcerpc_netr_ServerReqChallenge(p, tctx, &r);
256 torture_assert_ntstatus_ok(tctx, status, "ServerReqChallenge");
263 try a change password for our machine account
265 static bool test_SetPassword(struct torture_context *tctx,
266 struct dcerpc_pipe *p,
267 struct cli_credentials *machine_credentials)
270 struct netr_ServerPasswordSet r;
271 const char *password;
272 struct creds_CredentialState *creds;
274 if (!test_SetupCredentials(p, tctx, machine_credentials, &creds)) {
278 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
279 r.in.account_name = talloc_asprintf(tctx, "%s$", TEST_MACHINE_NAME);
280 r.in.secure_channel_type = SEC_CHAN_BDC;
281 r.in.computer_name = TEST_MACHINE_NAME;
283 password = generate_random_str(tctx, 8);
284 E_md4hash(password, r.in.new_password.hash);
286 creds_des_encrypt(creds, &r.in.new_password);
288 torture_comment(tctx, "Testing ServerPasswordSet on machine account\n");
289 torture_comment(tctx, "Changing machine account password to '%s'\n",
292 creds_client_authenticator(creds, &r.in.credential);
294 status = dcerpc_netr_ServerPasswordSet(p, tctx, &r);
295 torture_assert_ntstatus_ok(tctx, status, "ServerPasswordSet");
297 if (!creds_client_check(creds, &r.out.return_authenticator.cred)) {
298 torture_comment(tctx, "Credential chaining failed\n");
301 /* by changing the machine password twice we test the
302 credentials chaining fully, and we verify that the server
303 allows the password to be set to the same value twice in a
304 row (match win2k3) */
305 torture_comment(tctx,
306 "Testing a second ServerPasswordSet on machine account\n");
307 torture_comment(tctx,
308 "Changing machine account password to '%s' (same as previous run)\n", password);
310 creds_client_authenticator(creds, &r.in.credential);
312 status = dcerpc_netr_ServerPasswordSet(p, tctx, &r);
313 torture_assert_ntstatus_ok(tctx, status, "ServerPasswordSet (2)");
315 if (!creds_client_check(creds, &r.out.return_authenticator.cred)) {
316 torture_comment(tctx, "Credential chaining failed\n");
319 cli_credentials_set_password(machine_credentials, password, CRED_SPECIFIED);
322 test_SetupCredentials(p, tctx, machine_credentials, &creds),
323 "ServerPasswordSet failed to actually change the password");
329 generate a random password for password change tests
331 static DATA_BLOB netlogon_very_rand_pass(TALLOC_CTX *mem_ctx, int len)
334 DATA_BLOB password = data_blob_talloc(mem_ctx, NULL, len * 2 /* number of unicode chars */);
335 generate_random_buffer(password.data, password.length);
337 for (i=0; i < len; i++) {
338 if (((uint16_t *)password.data)[i] == 0) {
339 ((uint16_t *)password.data)[i] = 1;
347 try a change password for our machine account
349 static bool test_SetPassword2(struct torture_context *tctx,
350 struct dcerpc_pipe *p,
351 struct cli_credentials *machine_credentials)
354 struct netr_ServerPasswordSet2 r;
355 const char *password;
356 DATA_BLOB new_random_pass;
357 struct creds_CredentialState *creds;
358 struct samr_CryptPassword password_buf;
359 struct samr_Password nt_hash;
361 if (!test_SetupCredentials(p, tctx, machine_credentials, &creds)) {
365 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
366 r.in.account_name = talloc_asprintf(tctx, "%s$", TEST_MACHINE_NAME);
367 r.in.secure_channel_type = SEC_CHAN_BDC;
368 r.in.computer_name = TEST_MACHINE_NAME;
370 password = generate_random_str(tctx, 8);
371 encode_pw_buffer(password_buf.data, password, STR_UNICODE);
372 creds_arcfour_crypt(creds, password_buf.data, 516);
374 memcpy(r.in.new_password.data, password_buf.data, 512);
375 r.in.new_password.length = IVAL(password_buf.data, 512);
377 torture_comment(tctx, "Testing ServerPasswordSet2 on machine account\n");
378 torture_comment(tctx, "Changing machine account password to '%s'\n", password);
380 creds_client_authenticator(creds, &r.in.credential);
382 status = dcerpc_netr_ServerPasswordSet2(p, tctx, &r);
383 torture_assert_ntstatus_ok(tctx, status, "ServerPasswordSet2");
385 if (!creds_client_check(creds, &r.out.return_authenticator.cred)) {
386 torture_comment(tctx, "Credential chaining failed\n");
389 cli_credentials_set_password(machine_credentials, password, CRED_SPECIFIED);
391 if (!torture_setting_bool(tctx, "dangerous", false)) {
392 torture_comment(tctx,
393 "Not testing ability to set password to '', enable dangerous tests to perform this test\n");
395 /* by changing the machine password to ""
396 * we check if the server uses password restrictions
397 * for ServerPasswordSet2
398 * (win2k3 accepts "")
401 encode_pw_buffer(password_buf.data, password, STR_UNICODE);
402 creds_arcfour_crypt(creds, password_buf.data, 516);
404 memcpy(r.in.new_password.data, password_buf.data, 512);
405 r.in.new_password.length = IVAL(password_buf.data, 512);
407 torture_comment(tctx,
408 "Testing ServerPasswordSet2 on machine account\n");
409 torture_comment(tctx,
410 "Changing machine account password to '%s'\n", password);
412 creds_client_authenticator(creds, &r.in.credential);
414 status = dcerpc_netr_ServerPasswordSet2(p, tctx, &r);
415 torture_assert_ntstatus_ok(tctx, status, "ServerPasswordSet2");
417 if (!creds_client_check(creds, &r.out.return_authenticator.cred)) {
418 torture_comment(tctx, "Credential chaining failed\n");
421 cli_credentials_set_password(machine_credentials, password, CRED_SPECIFIED);
424 torture_assert(tctx, test_SetupCredentials(p, tctx, machine_credentials, &creds),
425 "ServerPasswordSet failed to actually change the password");
427 /* now try a random password */
428 password = generate_random_str(tctx, 8);
429 encode_pw_buffer(password_buf.data, password, STR_UNICODE);
430 creds_arcfour_crypt(creds, password_buf.data, 516);
432 memcpy(r.in.new_password.data, password_buf.data, 512);
433 r.in.new_password.length = IVAL(password_buf.data, 512);
435 torture_comment(tctx, "Testing second ServerPasswordSet2 on machine account\n");
436 torture_comment(tctx, "Changing machine account password to '%s'\n", password);
438 creds_client_authenticator(creds, &r.in.credential);
440 status = dcerpc_netr_ServerPasswordSet2(p, tctx, &r);
441 torture_assert_ntstatus_ok(tctx, status, "ServerPasswordSet2 (2)");
443 if (!creds_client_check(creds, &r.out.return_authenticator.cred)) {
444 torture_comment(tctx, "Credential chaining failed\n");
447 /* by changing the machine password twice we test the
448 credentials chaining fully, and we verify that the server
449 allows the password to be set to the same value twice in a
450 row (match win2k3) */
451 torture_comment(tctx,
452 "Testing a second ServerPasswordSet2 on machine account\n");
453 torture_comment(tctx,
454 "Changing machine account password to '%s' (same as previous run)\n", password);
456 creds_client_authenticator(creds, &r.in.credential);
458 status = dcerpc_netr_ServerPasswordSet2(p, tctx, &r);
459 torture_assert_ntstatus_ok(tctx, status, "ServerPasswordSet (3)");
461 if (!creds_client_check(creds, &r.out.return_authenticator.cred)) {
462 torture_comment(tctx, "Credential chaining failed\n");
465 cli_credentials_set_password(machine_credentials, password, CRED_SPECIFIED);
467 torture_assert (tctx,
468 test_SetupCredentials(p, tctx, machine_credentials, &creds),
469 "ServerPasswordSet failed to actually change the password");
471 new_random_pass = netlogon_very_rand_pass(tctx, 128);
473 /* now try a random stream of bytes for a password */
474 set_pw_in_buffer(password_buf.data, &new_random_pass);
476 creds_arcfour_crypt(creds, password_buf.data, 516);
478 memcpy(r.in.new_password.data, password_buf.data, 512);
479 r.in.new_password.length = IVAL(password_buf.data, 512);
481 torture_comment(tctx,
482 "Testing a third ServerPasswordSet2 on machine account, with a compleatly random password\n");
484 creds_client_authenticator(creds, &r.in.credential);
486 status = dcerpc_netr_ServerPasswordSet2(p, tctx, &r);
487 torture_assert_ntstatus_ok(tctx, status, "ServerPasswordSet (3)");
489 if (!creds_client_check(creds, &r.out.return_authenticator.cred)) {
490 torture_comment(tctx, "Credential chaining failed\n");
493 mdfour(nt_hash.hash, new_random_pass.data, new_random_pass.length);
495 cli_credentials_set_password(machine_credentials, NULL, CRED_UNINITIALISED);
496 cli_credentials_set_nt_hash(machine_credentials, &nt_hash, CRED_SPECIFIED);
498 torture_assert (tctx,
499 test_SetupCredentials(p, tctx, machine_credentials, &creds),
500 "ServerPasswordSet failed to actually change the password");
505 static bool test_GetPassword(struct torture_context *tctx,
506 struct dcerpc_pipe *p,
507 struct cli_credentials *machine_credentials)
509 struct netr_ServerPasswordGet r;
510 struct creds_CredentialState *creds;
511 struct netr_Authenticator credential;
513 struct netr_Authenticator return_authenticator;
514 struct samr_Password password;
516 if (!test_SetupCredentials(p, tctx, machine_credentials, &creds)) {
520 creds_client_authenticator(creds, &credential);
522 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
523 r.in.account_name = talloc_asprintf(tctx, "%s$", TEST_MACHINE_NAME);
524 r.in.secure_channel_type = SEC_CHAN_BDC;
525 r.in.computer_name = TEST_MACHINE_NAME;
526 r.in.credential = &credential;
527 r.out.return_authenticator = &return_authenticator;
528 r.out.password = &password;
530 status = dcerpc_netr_ServerPasswordGet(p, tctx, &r);
531 torture_assert_ntstatus_ok(tctx, status, "ServerPasswordGet");
536 static bool test_GetTrustPasswords(struct torture_context *tctx,
537 struct dcerpc_pipe *p,
538 struct cli_credentials *machine_credentials)
540 struct netr_ServerTrustPasswordsGet r;
541 struct creds_CredentialState *creds;
542 struct netr_Authenticator credential;
544 struct netr_Authenticator return_authenticator;
545 struct samr_Password password, password2;
547 if (!test_SetupCredentials(p, tctx, machine_credentials, &creds)) {
551 creds_client_authenticator(creds, &credential);
553 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
554 r.in.account_name = talloc_asprintf(tctx, "%s$", TEST_MACHINE_NAME);
555 r.in.secure_channel_type = SEC_CHAN_BDC;
556 r.in.computer_name = TEST_MACHINE_NAME;
557 r.in.credential = &credential;
558 r.out.return_authenticator = &return_authenticator;
559 r.out.password = &password;
560 r.out.password2 = &password2;
562 status = dcerpc_netr_ServerTrustPasswordsGet(p, tctx, &r);
563 torture_assert_ntstatus_ok(tctx, status, "ServerTrustPasswordsGet");
569 try a netlogon SamLogon
571 bool test_netlogon_ops(struct dcerpc_pipe *p, struct torture_context *tctx,
572 struct cli_credentials *credentials,
573 struct creds_CredentialState *creds)
576 struct netr_LogonSamLogon r;
577 struct netr_Authenticator auth, auth2;
578 union netr_LogonLevel logon;
579 union netr_Validation validation;
580 uint8_t authoritative;
581 struct netr_NetworkInfo ninfo;
582 DATA_BLOB names_blob, chal, lm_resp, nt_resp;
584 int flags = CLI_CRED_NTLM_AUTH;
585 if (lp_client_lanman_auth(tctx->lp_ctx)) {
586 flags |= CLI_CRED_LANMAN_AUTH;
589 if (lp_client_ntlmv2_auth(tctx->lp_ctx)) {
590 flags |= CLI_CRED_NTLMv2_AUTH;
593 cli_credentials_get_ntlm_username_domain(cmdline_credentials, tctx,
594 &ninfo.identity_info.account_name.string,
595 &ninfo.identity_info.domain_name.string);
597 generate_random_buffer(ninfo.challenge,
598 sizeof(ninfo.challenge));
599 chal = data_blob_const(ninfo.challenge,
600 sizeof(ninfo.challenge));
602 names_blob = NTLMv2_generate_names_blob(tctx, cli_credentials_get_workstation(credentials),
603 cli_credentials_get_domain(credentials));
605 status = cli_credentials_get_ntlm_response(cmdline_credentials, tctx,
611 torture_assert_ntstatus_ok(tctx, status, "cli_credentials_get_ntlm_response failed");
613 ninfo.lm.data = lm_resp.data;
614 ninfo.lm.length = lm_resp.length;
616 ninfo.nt.data = nt_resp.data;
617 ninfo.nt.length = nt_resp.length;
619 ninfo.identity_info.parameter_control = 0;
620 ninfo.identity_info.logon_id_low = 0;
621 ninfo.identity_info.logon_id_high = 0;
622 ninfo.identity_info.workstation.string = cli_credentials_get_workstation(credentials);
624 logon.network = &ninfo;
626 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
627 r.in.computer_name = cli_credentials_get_workstation(credentials);
628 r.in.credential = &auth;
629 r.in.return_authenticator = &auth2;
630 r.in.logon_level = 2;
632 r.out.validation = &validation;
633 r.out.authoritative = &authoritative;
635 d_printf("Testing LogonSamLogon with name %s\n", ninfo.identity_info.account_name.string);
639 creds_client_authenticator(creds, &auth);
641 r.in.validation_level = i;
643 status = dcerpc_netr_LogonSamLogon(p, tctx, &r);
644 torture_assert_ntstatus_ok(tctx, status, "LogonSamLogon failed");
646 torture_assert(tctx, creds_client_check(creds, &r.out.return_authenticator->cred),
647 "Credential chaining failed");
650 r.in.credential = NULL;
654 r.in.validation_level = i;
656 torture_comment(tctx, "Testing SamLogon with validation level %d and a NULL credential\n", i);
658 status = dcerpc_netr_LogonSamLogon(p, tctx, &r);
659 torture_assert_ntstatus_equal(tctx, status, NT_STATUS_INVALID_PARAMETER,
660 "LogonSamLogon expected INVALID_PARAMETER");
668 try a netlogon SamLogon
670 static bool test_SamLogon(struct torture_context *tctx,
671 struct dcerpc_pipe *p,
672 struct cli_credentials *credentials)
674 struct creds_CredentialState *creds;
676 if (!test_SetupCredentials(p, tctx, credentials, &creds)) {
680 return test_netlogon_ops(p, tctx, credentials, creds);
683 /* we remember the sequence numbers so we can easily do a DatabaseDelta */
684 static uint64_t sequence_nums[3];
687 try a netlogon DatabaseSync
689 static bool test_DatabaseSync(struct torture_context *tctx,
690 struct dcerpc_pipe *p,
691 struct cli_credentials *machine_credentials)
694 struct netr_DatabaseSync r;
695 struct creds_CredentialState *creds;
696 const uint32_t database_ids[] = {SAM_DATABASE_DOMAIN, SAM_DATABASE_BUILTIN, SAM_DATABASE_PRIVS};
698 struct netr_DELTA_ENUM_ARRAY *delta_enum_array = NULL;
699 struct netr_Authenticator credential, return_authenticator;
701 if (!test_SetupCredentials(p, tctx, machine_credentials, &creds)) {
705 ZERO_STRUCT(return_authenticator);
707 r.in.logon_server = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
708 r.in.computername = TEST_MACHINE_NAME;
709 r.in.preferredmaximumlength = (uint32_t)-1;
710 r.in.return_authenticator = &return_authenticator;
711 r.out.delta_enum_array = &delta_enum_array;
712 r.out.return_authenticator = &return_authenticator;
714 for (i=0;i<ARRAY_SIZE(database_ids);i++) {
716 uint32_t sync_context = 0;
718 r.in.database_id = database_ids[i];
719 r.in.sync_context = &sync_context;
720 r.out.sync_context = &sync_context;
722 torture_comment(tctx, "Testing DatabaseSync of id %d\n", r.in.database_id);
725 creds_client_authenticator(creds, &credential);
727 r.in.credential = &credential;
729 status = dcerpc_netr_DatabaseSync(p, tctx, &r);
730 if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES))
733 /* Native mode servers don't do this */
734 if (NT_STATUS_EQUAL(status, NT_STATUS_NOT_SUPPORTED)) {
737 torture_assert_ntstatus_ok(tctx, status, "DatabaseSync");
739 if (!creds_client_check(creds, &r.out.return_authenticator->cred)) {
740 torture_comment(tctx, "Credential chaining failed\n");
743 if (delta_enum_array &&
744 delta_enum_array->num_deltas > 0 &&
745 delta_enum_array->delta_enum[0].delta_type == NETR_DELTA_DOMAIN &&
746 delta_enum_array->delta_enum[0].delta_union.domain) {
747 sequence_nums[r.in.database_id] =
748 delta_enum_array->delta_enum[0].delta_union.domain->sequence_num;
749 torture_comment(tctx, "\tsequence_nums[%d]=%llu\n",
751 (unsigned long long)sequence_nums[r.in.database_id]);
753 } while (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES));
761 try a netlogon DatabaseDeltas
763 static bool test_DatabaseDeltas(struct torture_context *tctx,
764 struct dcerpc_pipe *p,
765 struct cli_credentials *machine_credentials)
768 struct netr_DatabaseDeltas r;
769 struct creds_CredentialState *creds;
770 struct netr_Authenticator credential;
771 struct netr_Authenticator return_authenticator;
772 struct netr_DELTA_ENUM_ARRAY *delta_enum_array = NULL;
773 const uint32_t database_ids[] = {0, 1, 2};
776 if (!test_SetupCredentials(p, tctx, machine_credentials, &creds)) {
780 r.in.logon_server = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
781 r.in.computername = TEST_MACHINE_NAME;
782 r.in.preferredmaximumlength = (uint32_t)-1;
783 ZERO_STRUCT(r.in.return_authenticator);
784 r.out.return_authenticator = &return_authenticator;
785 r.out.delta_enum_array = &delta_enum_array;
787 for (i=0;i<ARRAY_SIZE(database_ids);i++) {
788 r.in.database_id = database_ids[i];
789 r.in.sequence_num = &sequence_nums[r.in.database_id];
791 if (*r.in.sequence_num == 0) continue;
793 *r.in.sequence_num -= 1;
795 torture_comment(tctx, "Testing DatabaseDeltas of id %d at %llu\n",
796 r.in.database_id, (unsigned long long)*r.in.sequence_num);
799 creds_client_authenticator(creds, &credential);
801 status = dcerpc_netr_DatabaseDeltas(p, tctx, &r);
802 if (NT_STATUS_EQUAL(status,
803 NT_STATUS_SYNCHRONIZATION_REQUIRED)) {
804 torture_comment(tctx, "not considering %s to be an error\n",
808 if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES))
811 torture_assert_ntstatus_ok(tctx, status, "DatabaseDeltas");
813 if (!creds_client_check(creds, &return_authenticator.cred)) {
814 torture_comment(tctx, "Credential chaining failed\n");
817 (*r.in.sequence_num)++;
818 } while (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES));
826 try a netlogon AccountDeltas
828 static bool test_AccountDeltas(struct torture_context *tctx,
829 struct dcerpc_pipe *p,
830 struct cli_credentials *machine_credentials)
833 struct netr_AccountDeltas r;
834 struct creds_CredentialState *creds;
836 struct netr_AccountBuffer buffer;
837 uint32_t count_returned = 0;
838 uint32_t total_entries = 0;
839 struct netr_UAS_INFO_0 recordid;
840 struct netr_Authenticator return_authenticator;
842 if (!test_SetupCredentials(p, tctx, machine_credentials, &creds)) {
846 ZERO_STRUCT(return_authenticator);
848 r.in.logon_server = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
849 r.in.computername = TEST_MACHINE_NAME;
850 r.in.return_authenticator = &return_authenticator;
851 creds_client_authenticator(creds, &r.in.credential);
852 ZERO_STRUCT(r.in.uas);
856 r.out.buffer = &buffer;
857 r.out.count_returned = &count_returned;
858 r.out.total_entries = &total_entries;
859 r.out.recordid = &recordid;
860 r.out.return_authenticator = &return_authenticator;
862 /* w2k3 returns "NOT IMPLEMENTED" for this call */
863 status = dcerpc_netr_AccountDeltas(p, tctx, &r);
864 torture_assert_ntstatus_equal(tctx, status, NT_STATUS_NOT_IMPLEMENTED, "AccountDeltas");
870 try a netlogon AccountSync
872 static bool test_AccountSync(struct torture_context *tctx, struct dcerpc_pipe *p,
873 struct cli_credentials *machine_credentials)
876 struct netr_AccountSync r;
877 struct creds_CredentialState *creds;
879 struct netr_AccountBuffer buffer;
880 uint32_t count_returned = 0;
881 uint32_t total_entries = 0;
882 uint32_t next_reference = 0;
883 struct netr_UAS_INFO_0 recordid;
884 struct netr_Authenticator return_authenticator;
886 ZERO_STRUCT(recordid);
887 ZERO_STRUCT(return_authenticator);
889 if (!test_SetupCredentials(p, tctx, machine_credentials, &creds)) {
893 r.in.logon_server = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
894 r.in.computername = TEST_MACHINE_NAME;
895 r.in.return_authenticator = &return_authenticator;
896 creds_client_authenticator(creds, &r.in.credential);
897 r.in.recordid = &recordid;
901 r.out.buffer = &buffer;
902 r.out.count_returned = &count_returned;
903 r.out.total_entries = &total_entries;
904 r.out.next_reference = &next_reference;
905 r.out.recordid = &recordid;
906 r.out.return_authenticator = &return_authenticator;
908 /* w2k3 returns "NOT IMPLEMENTED" for this call */
909 status = dcerpc_netr_AccountSync(p, tctx, &r);
910 torture_assert_ntstatus_equal(tctx, status, NT_STATUS_NOT_IMPLEMENTED, "AccountSync");
916 try a netlogon GetDcName
918 static bool test_GetDcName(struct torture_context *tctx,
919 struct dcerpc_pipe *p)
922 struct netr_GetDcName r;
923 const char *dcname = NULL;
925 r.in.logon_server = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
926 r.in.domainname = lp_workgroup(tctx->lp_ctx);
927 r.out.dcname = &dcname;
929 status = dcerpc_netr_GetDcName(p, tctx, &r);
930 torture_assert_ntstatus_ok(tctx, status, "GetDcName");
931 torture_assert_werr_ok(tctx, r.out.result, "GetDcName");
933 torture_comment(tctx, "\tDC is at '%s'\n", dcname);
939 try a netlogon LogonControl
941 static bool test_LogonControl(struct torture_context *tctx,
942 struct dcerpc_pipe *p)
945 struct netr_LogonControl r;
946 union netr_CONTROL_QUERY_INFORMATION info;
949 r.in.logon_server = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
950 r.in.function_code = 1;
956 torture_comment(tctx, "Testing LogonControl level %d\n", i);
958 status = dcerpc_netr_LogonControl(p, tctx, &r);
959 torture_assert_ntstatus_ok(tctx, status, "LogonControl");
967 try a netlogon GetAnyDCName
969 static bool test_GetAnyDCName(struct torture_context *tctx,
970 struct dcerpc_pipe *p)
973 struct netr_GetAnyDCName r;
974 const char *dcname = NULL;
976 r.in.logon_server = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
977 r.in.domainname = lp_workgroup(tctx->lp_ctx);
978 r.out.dcname = &dcname;
980 status = dcerpc_netr_GetAnyDCName(p, tctx, &r);
981 torture_assert_ntstatus_ok(tctx, status, "GetAnyDCName");
984 torture_comment(tctx, "\tDC is at '%s'\n", dcname);
992 try a netlogon LogonControl2
994 static bool test_LogonControl2(struct torture_context *tctx,
995 struct dcerpc_pipe *p)
998 struct netr_LogonControl2 r;
999 union netr_CONTROL_DATA_INFORMATION data;
1000 union netr_CONTROL_QUERY_INFORMATION query;
1003 data.domain = lp_workgroup(tctx->lp_ctx);
1005 r.in.logon_server = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1007 r.in.function_code = NETLOGON_CONTROL_REDISCOVER;
1009 r.out.query = &query;
1014 torture_comment(tctx, "Testing LogonControl2 level %d function %d\n",
1015 i, r.in.function_code);
1017 status = dcerpc_netr_LogonControl2(p, tctx, &r);
1018 torture_assert_ntstatus_ok(tctx, status, "LogonControl");
1021 data.domain = lp_workgroup(tctx->lp_ctx);
1023 r.in.function_code = NETLOGON_CONTROL_TC_QUERY;
1029 torture_comment(tctx, "Testing LogonControl2 level %d function %d\n",
1030 i, r.in.function_code);
1032 status = dcerpc_netr_LogonControl2(p, tctx, &r);
1033 torture_assert_ntstatus_ok(tctx, status, "LogonControl");
1036 data.domain = lp_workgroup(tctx->lp_ctx);
1038 r.in.function_code = NETLOGON_CONTROL_TRANSPORT_NOTIFY;
1044 torture_comment(tctx, "Testing LogonControl2 level %d function %d\n",
1045 i, r.in.function_code);
1047 status = dcerpc_netr_LogonControl2(p, tctx, &r);
1048 torture_assert_ntstatus_ok(tctx, status, "LogonControl");
1051 data.debug_level = ~0;
1053 r.in.function_code = NETLOGON_CONTROL_SET_DBFLAG;
1059 torture_comment(tctx, "Testing LogonControl2 level %d function %d\n",
1060 i, r.in.function_code);
1062 status = dcerpc_netr_LogonControl2(p, tctx, &r);
1063 torture_assert_ntstatus_ok(tctx, status, "LogonControl");
1070 try a netlogon DatabaseSync2
1072 static bool test_DatabaseSync2(struct torture_context *tctx,
1073 struct dcerpc_pipe *p,
1074 struct cli_credentials *machine_credentials)
1077 struct netr_DatabaseSync2 r;
1078 struct netr_DELTA_ENUM_ARRAY *delta_enum_array = NULL;
1079 struct netr_Authenticator return_authenticator, credential;
1081 struct creds_CredentialState *creds;
1082 const uint32_t database_ids[] = {0, 1, 2};
1085 if (!test_SetupCredentials2(p, tctx, NETLOGON_NEG_AUTH2_FLAGS,
1086 machine_credentials,
1087 SEC_CHAN_BDC, &creds)) {
1091 ZERO_STRUCT(return_authenticator);
1093 r.in.logon_server = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1094 r.in.computername = TEST_MACHINE_NAME;
1095 r.in.preferredmaximumlength = (uint32_t)-1;
1096 r.in.return_authenticator = &return_authenticator;
1097 r.out.return_authenticator = &return_authenticator;
1098 r.out.delta_enum_array = &delta_enum_array;
1100 for (i=0;i<ARRAY_SIZE(database_ids);i++) {
1102 uint32_t sync_context = 0;
1104 r.in.database_id = database_ids[i];
1105 r.in.sync_context = &sync_context;
1106 r.out.sync_context = &sync_context;
1107 r.in.restart_state = 0;
1109 torture_comment(tctx, "Testing DatabaseSync2 of id %d\n", r.in.database_id);
1112 creds_client_authenticator(creds, &credential);
1114 r.in.credential = &credential;
1116 status = dcerpc_netr_DatabaseSync2(p, tctx, &r);
1117 if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES))
1120 /* Native mode servers don't do this */
1121 if (NT_STATUS_EQUAL(status, NT_STATUS_NOT_SUPPORTED)) {
1125 torture_assert_ntstatus_ok(tctx, status, "DatabaseSync2");
1127 if (!creds_client_check(creds, &r.out.return_authenticator->cred)) {
1128 torture_comment(tctx, "Credential chaining failed\n");
1131 } while (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES));
1139 try a netlogon LogonControl2Ex
1141 static bool test_LogonControl2Ex(struct torture_context *tctx,
1142 struct dcerpc_pipe *p)
1145 struct netr_LogonControl2Ex r;
1146 union netr_CONTROL_QUERY_INFORMATION query;
1149 r.in.logon_server = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1151 r.in.function_code = NETLOGON_CONTROL_REDISCOVER;
1152 r.in.data.domain = lp_workgroup(tctx->lp_ctx);
1153 r.out.query = &query;
1158 torture_comment(tctx, "Testing LogonControl2Ex level %d function %d\n",
1159 i, r.in.function_code);
1161 status = dcerpc_netr_LogonControl2Ex(p, tctx, &r);
1162 torture_assert_ntstatus_ok(tctx, status, "LogonControl");
1165 r.in.function_code = NETLOGON_CONTROL_TC_QUERY;
1166 r.in.data.domain = lp_workgroup(tctx->lp_ctx);
1171 torture_comment(tctx, "Testing LogonControl2Ex level %d function %d\n",
1172 i, r.in.function_code);
1174 status = dcerpc_netr_LogonControl2Ex(p, tctx, &r);
1175 torture_assert_ntstatus_ok(tctx, status, "LogonControl");
1178 r.in.function_code = NETLOGON_CONTROL_TRANSPORT_NOTIFY;
1179 r.in.data.domain = lp_workgroup(tctx->lp_ctx);
1184 torture_comment(tctx, "Testing LogonControl2Ex level %d function %d\n",
1185 i, r.in.function_code);
1187 status = dcerpc_netr_LogonControl2Ex(p, tctx, &r);
1188 torture_assert_ntstatus_ok(tctx, status, "LogonControl");
1191 r.in.function_code = NETLOGON_CONTROL_SET_DBFLAG;
1192 r.in.data.debug_level = ~0;
1197 torture_comment(tctx, "Testing LogonControl2Ex level %d function %d\n",
1198 i, r.in.function_code);
1200 status = dcerpc_netr_LogonControl2Ex(p, tctx, &r);
1201 torture_assert_ntstatus_ok(tctx, status, "LogonControl");
1207 static bool test_netr_DsRGetForestTrustInformation(struct torture_context *tctx,
1208 struct dcerpc_pipe *p, const char *trusted_domain_name)
1211 struct netr_DsRGetForestTrustInformation r;
1212 struct lsa_ForestTrustInformation info, *info_ptr;
1216 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1217 r.in.trusted_domain_name = trusted_domain_name;
1219 r.out.forest_trust_info = &info_ptr;
1221 torture_comment(tctx ,"Testing netr_DsRGetForestTrustInformation\n");
1223 status = dcerpc_netr_DsRGetForestTrustInformation(p, tctx, &r);
1224 torture_assert_ntstatus_ok(tctx, status, "DsRGetForestTrustInformation");
1225 torture_assert_werr_ok(tctx, r.out.result, "DsRGetForestTrustInformation");
1231 try a netlogon netr_DsrEnumerateDomainTrusts
1233 static bool test_DsrEnumerateDomainTrusts(struct torture_context *tctx,
1234 struct dcerpc_pipe *p)
1237 struct netr_DsrEnumerateDomainTrusts r;
1238 struct netr_DomainTrustList trusts;
1241 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1242 r.in.trust_flags = 0x3f;
1243 r.out.trusts = &trusts;
1245 status = dcerpc_netr_DsrEnumerateDomainTrusts(p, tctx, &r);
1246 torture_assert_ntstatus_ok(tctx, status, "DsrEnumerateDomaintrusts");
1247 torture_assert_werr_ok(tctx, r.out.result, "DsrEnumerateDomaintrusts");
1249 /* when trusted_domain_name is NULL, netr_DsRGetForestTrustInformation
1250 * will show non-forest trusts and all UPN suffixes of the own forest
1251 * as LSA_FOREST_TRUST_TOP_LEVEL_NAME types */
1253 if (r.out.trusts->count) {
1254 if (!test_netr_DsRGetForestTrustInformation(tctx, p, NULL)) {
1259 for (i=0; i<r.out.trusts->count; i++) {
1261 /* get info for transitive forest trusts */
1263 if (r.out.trusts->array[i].trust_attributes & NETR_TRUST_ATTRIBUTE_FOREST_TRANSITIVE) {
1264 if (!test_netr_DsRGetForestTrustInformation(tctx, p,
1265 r.out.trusts->array[i].dns_name)) {
1274 static bool test_netr_NetrEnumerateTrustedDomains(struct torture_context *tctx,
1275 struct dcerpc_pipe *p)
1278 struct netr_NetrEnumerateTrustedDomains r;
1279 struct netr_Blob trusted_domains_blob;
1281 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1282 r.out.trusted_domains_blob = &trusted_domains_blob;
1284 status = dcerpc_netr_NetrEnumerateTrustedDomains(p, tctx, &r);
1285 torture_assert_ntstatus_ok(tctx, status, "netr_NetrEnumerateTrustedDomains");
1286 torture_assert_werr_ok(tctx, r.out.result, "NetrEnumerateTrustedDomains");
1291 static bool test_netr_NetrEnumerateTrustedDomainsEx(struct torture_context *tctx,
1292 struct dcerpc_pipe *p)
1295 struct netr_NetrEnumerateTrustedDomainsEx r;
1296 struct netr_DomainTrustList dom_trust_list;
1298 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1299 r.out.dom_trust_list = &dom_trust_list;
1301 status = dcerpc_netr_NetrEnumerateTrustedDomainsEx(p, tctx, &r);
1302 torture_assert_ntstatus_ok(tctx, status, "netr_NetrEnumerateTrustedDomainsEx");
1303 torture_assert_werr_ok(tctx, r.out.result, "NetrEnumerateTrustedDomainsEx");
1309 static bool test_netr_DsRGetSiteName(struct dcerpc_pipe *p, struct torture_context *tctx,
1310 const char *computer_name,
1311 const char *expected_site)
1314 struct netr_DsRGetSiteName r;
1315 const char *site = NULL;
1317 if (torture_setting_bool(tctx, "samba4", false))
1318 torture_skip(tctx, "skipping DsRGetSiteName test against Samba4");
1320 r.in.computer_name = computer_name;
1322 torture_comment(tctx, "Testing netr_DsRGetSiteName\n");
1324 status = dcerpc_netr_DsRGetSiteName(p, tctx, &r);
1325 torture_assert_ntstatus_ok(tctx, status, "DsRGetSiteName");
1326 torture_assert_werr_ok(tctx, r.out.result, "DsRGetSiteName");
1327 torture_assert_str_equal(tctx, expected_site, site, "netr_DsRGetSiteName");
1329 r.in.computer_name = talloc_asprintf(tctx, "\\\\%s", computer_name);
1330 torture_comment(tctx,
1331 "Testing netr_DsRGetSiteName with broken computer name: %s\n", r.in.computer_name);
1333 status = dcerpc_netr_DsRGetSiteName(p, tctx, &r);
1334 torture_assert_ntstatus_ok(tctx, status, "DsRGetSiteName");
1335 torture_assert_werr_equal(tctx, r.out.result, WERR_INVALID_COMPUTERNAME, "netr_DsRGetSiteName");
1341 try a netlogon netr_DsRGetDCName
1343 static bool test_netr_DsRGetDCName(struct torture_context *tctx,
1344 struct dcerpc_pipe *p)
1347 struct netr_DsRGetDCName r;
1348 struct netr_DsRGetDCNameInfo *info = NULL;
1350 r.in.server_unc = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1351 r.in.domain_name = talloc_asprintf(tctx, "%s", lp_realm(tctx->lp_ctx));
1352 r.in.domain_guid = NULL;
1353 r.in.site_guid = NULL;
1354 r.in.flags = DS_RETURN_DNS_NAME;
1357 status = dcerpc_netr_DsRGetDCName(p, tctx, &r);
1358 torture_assert_ntstatus_ok(tctx, status, "DsRGetDCName");
1359 torture_assert_werr_ok(tctx, r.out.result, "DsRGetDCName");
1360 return test_netr_DsRGetSiteName(p, tctx,
1362 info->dc_site_name);
1366 try a netlogon netr_DsRGetDCNameEx
1368 static bool test_netr_DsRGetDCNameEx(struct torture_context *tctx,
1369 struct dcerpc_pipe *p)
1372 struct netr_DsRGetDCNameEx r;
1373 struct netr_DsRGetDCNameInfo *info = NULL;
1375 r.in.server_unc = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1376 r.in.domain_name = talloc_asprintf(tctx, "%s", lp_realm(tctx->lp_ctx));
1377 r.in.domain_guid = NULL;
1378 r.in.site_name = NULL;
1379 r.in.flags = DS_RETURN_DNS_NAME;
1382 status = dcerpc_netr_DsRGetDCNameEx(p, tctx, &r);
1383 torture_assert_ntstatus_ok(tctx, status, "netr_DsRGetDCNameEx");
1384 torture_assert_werr_ok(tctx, r.out.result, "netr_DsRGetDCNameEx");
1386 return test_netr_DsRGetSiteName(p, tctx, info->dc_unc,
1387 info->dc_site_name);
1391 try a netlogon netr_DsRGetDCNameEx2
1393 static bool test_netr_DsRGetDCNameEx2(struct torture_context *tctx,
1394 struct dcerpc_pipe *p)
1397 struct netr_DsRGetDCNameEx2 r;
1398 struct netr_DsRGetDCNameInfo *info = NULL;
1400 r.in.server_unc = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1401 r.in.client_account = NULL;
1402 r.in.mask = 0x00000000;
1403 r.in.domain_name = talloc_asprintf(tctx, "%s", lp_realm(tctx->lp_ctx));
1404 r.in.domain_guid = NULL;
1405 r.in.site_name = NULL;
1406 r.in.flags = DS_RETURN_DNS_NAME;
1409 torture_comment(tctx, "Testing netr_DsRGetDCNameEx2 without client account\n");
1411 status = dcerpc_netr_DsRGetDCNameEx2(p, tctx, &r);
1412 torture_assert_ntstatus_ok(tctx, status, "netr_DsRGetDCNameEx2");
1413 torture_assert_werr_ok(tctx, r.out.result, "netr_DsRGetDCNameEx2");
1415 torture_comment(tctx, "Testing netr_DsRGetDCNameEx2 with client acount\n");
1416 r.in.client_account = TEST_MACHINE_NAME"$";
1417 r.in.mask = ACB_SVRTRUST;
1418 r.in.flags = DS_RETURN_FLAT_NAME;
1421 status = dcerpc_netr_DsRGetDCNameEx2(p, tctx, &r);
1422 torture_assert_ntstatus_ok(tctx, status, "netr_DsRGetDCNameEx2");
1423 torture_assert_werr_ok(tctx, r.out.result, "netr_DsRGetDCNameEx2");
1424 return test_netr_DsRGetSiteName(p, tctx, info->dc_unc,
1425 info->dc_site_name);
1428 static bool test_netr_DsrGetDcSiteCoverageW(struct torture_context *tctx,
1429 struct dcerpc_pipe *p)
1432 struct netr_DsrGetDcSiteCoverageW r;
1433 struct DcSitesCtr *ctr = NULL;
1435 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1438 status = dcerpc_netr_DsrGetDcSiteCoverageW(p, tctx, &r);
1439 torture_assert_ntstatus_ok(tctx, status, "failed");
1440 torture_assert_werr_ok(tctx, r.out.result, "failed");
1445 static bool test_netr_DsRAddressToSitenamesW(struct torture_context *tctx,
1446 struct dcerpc_pipe *p)
1449 struct netr_DsRAddressToSitenamesW r;
1450 struct netr_DsRAddress addr;
1451 struct netr_DsRAddressToSitenamesWCtr *ctr;
1453 ctr = talloc(tctx, struct netr_DsRAddressToSitenamesWCtr);
1456 addr.buffer = talloc_zero_array(tctx, uint8_t, addr.size);
1458 addr.buffer[0] = 2; /* AF_INET */
1459 addr.buffer[4] = 127;
1464 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1466 r.in.addresses = talloc_zero_array(tctx, struct netr_DsRAddress, r.in.count);
1467 r.in.addresses[0] = addr;
1470 status = dcerpc_netr_DsRAddressToSitenamesW(p, tctx, &r);
1471 torture_assert_ntstatus_ok(tctx, status, "failed");
1472 torture_assert_werr_ok(tctx, r.out.result, "failed");
1477 static bool test_netr_DsRAddressToSitenamesExW(struct torture_context *tctx,
1478 struct dcerpc_pipe *p)
1481 struct netr_DsRAddressToSitenamesExW r;
1482 struct netr_DsRAddress addr;
1483 struct netr_DsRAddressToSitenamesExWCtr *ctr;
1485 ctr = talloc(tctx, struct netr_DsRAddressToSitenamesExWCtr);
1488 addr.buffer = talloc_zero_array(tctx, uint8_t, addr.size);
1490 addr.buffer[0] = 2; /* AF_INET */
1491 addr.buffer[4] = 127;
1496 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1498 r.in.addresses = talloc_zero_array(tctx, struct netr_DsRAddress, r.in.count);
1499 r.in.addresses[0] = addr;
1502 status = dcerpc_netr_DsRAddressToSitenamesExW(p, tctx, &r);
1503 torture_assert_ntstatus_ok(tctx, status, "failed");
1504 torture_assert_werr_ok(tctx, r.out.result, "failed");
1509 static bool test_GetDomainInfo(struct torture_context *tctx,
1510 struct dcerpc_pipe *p,
1511 struct cli_credentials *machine_credentials)
1514 struct netr_LogonGetDomainInfo r;
1515 struct netr_DomainQuery1 q1;
1516 struct netr_Authenticator a;
1517 struct creds_CredentialState *creds;
1518 union netr_DomainInfo info;
1520 if (!test_SetupCredentials3(p, tctx, NETLOGON_NEG_AUTH2_ADS_FLAGS,
1521 machine_credentials, &creds)) {
1527 creds_client_authenticator(creds, &a);
1529 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1530 r.in.computer_name = TEST_MACHINE_NAME;
1532 r.in.credential = &a;
1533 r.in.return_authenticator = &a;
1534 r.out.return_authenticator = &a;
1537 r.in.query.query1 = &q1;
1540 /* this should really be the fully qualified name */
1541 q1.workstation_domain = TEST_MACHINE_NAME;
1542 q1.workstation_site = "Default-First-Site-Name";
1543 q1.blob2.length = 0;
1545 q1.blob2.data = NULL;
1546 q1.product.string = "product string";
1548 torture_comment(tctx, "Testing netr_LogonGetDomainInfo\n");
1550 status = dcerpc_netr_LogonGetDomainInfo(p, tctx, &r);
1551 torture_assert_ntstatus_ok(tctx, status, "netr_LogonGetDomainInfo");
1552 torture_assert(tctx, creds_client_check(creds, &a.cred), "Credential chaining failed");
1554 torture_comment(tctx, "Testing netr_LogonGetDomainInfo 2nd call\n");
1555 creds_client_authenticator(creds, &a);
1557 status = dcerpc_netr_LogonGetDomainInfo(p, tctx, &r);
1558 torture_assert_ntstatus_ok(tctx, status, "netr_LogonGetDomainInfo");
1559 torture_assert(tctx, creds_client_check(creds, &a.cred), "Credential chaining failed");
1565 static void async_callback(struct rpc_request *req)
1567 int *counter = (int *)req->async.private_data;
1568 if (NT_STATUS_IS_OK(req->status)) {
1573 static bool test_GetDomainInfo_async(struct torture_context *tctx,
1574 struct dcerpc_pipe *p,
1575 struct cli_credentials *machine_credentials)
1578 struct netr_LogonGetDomainInfo r;
1579 struct netr_DomainQuery1 q1;
1580 struct netr_Authenticator a;
1581 #define ASYNC_COUNT 100
1582 struct creds_CredentialState *creds;
1583 struct creds_CredentialState *creds_async[ASYNC_COUNT];
1584 struct rpc_request *req[ASYNC_COUNT];
1586 int *async_counter = talloc(tctx, int);
1587 union netr_DomainInfo info;
1589 if (!test_SetupCredentials3(p, tctx, NETLOGON_NEG_AUTH2_ADS_FLAGS,
1590 machine_credentials, &creds)) {
1595 r.in.server_name = talloc_asprintf(tctx, "\\\\%s", dcerpc_server_name(p));
1596 r.in.computer_name = TEST_MACHINE_NAME;
1598 r.in.credential = &a;
1599 r.in.return_authenticator = &a;
1600 r.out.return_authenticator = &a;
1603 r.in.query.query1 = &q1;
1606 /* this should really be the fully qualified name */
1607 q1.workstation_domain = TEST_MACHINE_NAME;
1608 q1.workstation_site = "Default-First-Site-Name";
1609 q1.blob2.length = 0;
1611 q1.blob2.data = NULL;
1612 q1.product.string = "product string";
1614 torture_comment(tctx, "Testing netr_LogonGetDomainInfo - async count %d\n", ASYNC_COUNT);
1618 for (i=0;i<ASYNC_COUNT;i++) {
1619 creds_client_authenticator(creds, &a);
1621 creds_async[i] = (struct creds_CredentialState *)talloc_memdup(creds, creds, sizeof(*creds));
1622 req[i] = dcerpc_netr_LogonGetDomainInfo_send(p, tctx, &r);
1624 req[i]->async.callback = async_callback;
1625 req[i]->async.private_data = async_counter;
1627 /* even with this flush per request a w2k3 server seems to
1628 clag with multiple outstanding requests. bleergh. */
1629 torture_assert_int_equal(tctx, event_loop_once(dcerpc_event_context(p)), 0,
1630 "event_loop_once failed");
1633 for (i=0;i<ASYNC_COUNT;i++) {
1634 status = dcerpc_ndr_request_recv(req[i]);
1636 torture_assert_ntstatus_ok(tctx, status, "netr_LogonGetDomainInfo_async");
1637 torture_assert_ntstatus_ok(tctx, r.out.result, "netr_LogonGetDomainInfo_async");
1639 torture_assert(tctx, creds_client_check(creds_async[i], &a.cred),
1640 "Credential chaining failed at async");
1643 torture_comment(tctx,
1644 "Testing netr_LogonGetDomainInfo - async count %d OK\n", *async_counter);
1646 torture_assert_int_equal(tctx, (*async_counter), ASYNC_COUNT, "int");
1651 static bool test_ManyGetDCName(struct torture_context *tctx,
1652 struct dcerpc_pipe *p)
1655 struct dcerpc_pipe *p2;
1656 struct lsa_ObjectAttribute attr;
1657 struct lsa_QosInfo qos;
1658 struct lsa_OpenPolicy2 o;
1659 struct policy_handle lsa_handle;
1660 struct lsa_DomainList domains;
1662 struct lsa_EnumTrustDom t;
1663 uint32_t resume_handle = 0;
1664 struct netr_GetAnyDCName d;
1665 const char *dcname = NULL;
1669 if (p->conn->transport.transport != NCACN_NP) {
1673 torture_comment(tctx, "Torturing GetDCName\n");
1675 status = dcerpc_secondary_connection(p, &p2, p->binding);
1676 torture_assert_ntstatus_ok(tctx, status, "Failed to create secondary connection");
1678 status = dcerpc_bind_auth_none(p2, &ndr_table_lsarpc);
1679 torture_assert_ntstatus_ok(tctx, status, "Failed to create bind on secondary connection");
1682 qos.impersonation_level = 2;
1683 qos.context_mode = 1;
1684 qos.effective_only = 0;
1687 attr.root_dir = NULL;
1688 attr.object_name = NULL;
1689 attr.attributes = 0;
1690 attr.sec_desc = NULL;
1691 attr.sec_qos = &qos;
1693 o.in.system_name = "\\";
1695 o.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
1696 o.out.handle = &lsa_handle;
1698 status = dcerpc_lsa_OpenPolicy2(p2, tctx, &o);
1699 torture_assert_ntstatus_ok(tctx, status, "OpenPolicy2 failed");
1701 t.in.handle = &lsa_handle;
1702 t.in.resume_handle = &resume_handle;
1703 t.in.max_size = 1000;
1704 t.out.domains = &domains;
1705 t.out.resume_handle = &resume_handle;
1707 status = dcerpc_lsa_EnumTrustDom(p2, tctx, &t);
1709 if ((!NT_STATUS_IS_OK(status) &&
1710 (!NT_STATUS_EQUAL(status, NT_STATUS_NO_MORE_ENTRIES))))
1711 torture_fail(tctx, "Could not list domains");
1715 d.in.logon_server = talloc_asprintf(tctx, "\\\\%s",
1716 dcerpc_server_name(p));
1717 d.out.dcname = &dcname;
1719 for (i=0; i<domains.count * 4; i++) {
1720 struct lsa_DomainInfo *info =
1721 &domains.domains[rand()%domains.count];
1723 d.in.domainname = info->name.string;
1725 status = dcerpc_netr_GetAnyDCName(p, tctx, &d);
1726 torture_assert_ntstatus_ok(tctx, status, "GetAnyDCName");
1728 torture_comment(tctx, "\tDC for domain %s is %s\n", info->name.string,
1729 dcname ? dcname : "unknown");
1735 struct torture_suite *torture_rpc_netlogon(TALLOC_CTX *mem_ctx)
1737 struct torture_suite *suite = torture_suite_create(mem_ctx, "NETLOGON");
1738 struct torture_rpc_tcase *tcase;
1739 struct torture_test *test;
1741 tcase = torture_suite_add_machine_rpc_iface_tcase(suite, "netlogon",
1742 &ndr_table_netlogon, TEST_MACHINE_NAME);
1744 torture_rpc_tcase_add_test(tcase, "LogonUasLogon", test_LogonUasLogon);
1745 torture_rpc_tcase_add_test(tcase, "LogonUasLogoff", test_LogonUasLogoff);
1746 torture_rpc_tcase_add_test_creds(tcase, "SamLogon", test_SamLogon);
1747 torture_rpc_tcase_add_test_creds(tcase, "SetPassword", test_SetPassword);
1748 torture_rpc_tcase_add_test_creds(tcase, "SetPassword2", test_SetPassword2);
1749 torture_rpc_tcase_add_test_creds(tcase, "GetPassword", test_GetPassword);
1750 torture_rpc_tcase_add_test_creds(tcase, "GetTrustPasswords", test_GetTrustPasswords);
1751 torture_rpc_tcase_add_test_creds(tcase, "GetDomainInfo", test_GetDomainInfo);
1752 torture_rpc_tcase_add_test_creds(tcase, "DatabaseSync", test_DatabaseSync);
1753 torture_rpc_tcase_add_test_creds(tcase, "DatabaseDeltas", test_DatabaseDeltas);
1754 torture_rpc_tcase_add_test_creds(tcase, "AccountDeltas", test_AccountDeltas);
1755 torture_rpc_tcase_add_test_creds(tcase, "AccountSync", test_AccountSync);
1756 torture_rpc_tcase_add_test(tcase, "GetDcName", test_GetDcName);
1757 torture_rpc_tcase_add_test(tcase, "ManyGetDCName", test_ManyGetDCName);
1758 torture_rpc_tcase_add_test(tcase, "LogonControl", test_LogonControl);
1759 torture_rpc_tcase_add_test(tcase, "GetAnyDCName", test_GetAnyDCName);
1760 torture_rpc_tcase_add_test(tcase, "LogonControl2", test_LogonControl2);
1761 torture_rpc_tcase_add_test_creds(tcase, "DatabaseSync2", test_DatabaseSync2);
1762 torture_rpc_tcase_add_test(tcase, "LogonControl2Ex", test_LogonControl2Ex);
1763 torture_rpc_tcase_add_test(tcase, "DsrEnumerateDomainTrusts", test_DsrEnumerateDomainTrusts);
1764 torture_rpc_tcase_add_test(tcase, "NetrEnumerateTrustedDomains", test_netr_NetrEnumerateTrustedDomains);
1765 torture_rpc_tcase_add_test(tcase, "NetrEnumerateTrustedDomainsEx", test_netr_NetrEnumerateTrustedDomainsEx);
1766 test = torture_rpc_tcase_add_test_creds(tcase, "GetDomainInfo_async", test_GetDomainInfo_async);
1767 test->dangerous = true;
1768 torture_rpc_tcase_add_test(tcase, "DsRGetDCName", test_netr_DsRGetDCName);
1769 torture_rpc_tcase_add_test(tcase, "DsRGetDCNameEx", test_netr_DsRGetDCNameEx);
1770 torture_rpc_tcase_add_test(tcase, "DsRGetDCNameEx2", test_netr_DsRGetDCNameEx2);
1771 torture_rpc_tcase_add_test(tcase, "DsrGetDcSiteCoverageW", test_netr_DsrGetDcSiteCoverageW);
1772 torture_rpc_tcase_add_test(tcase, "DsRAddressToSitenamesW", test_netr_DsRAddressToSitenamesW);
1773 torture_rpc_tcase_add_test(tcase, "DsRAddressToSitenamesExW", test_netr_DsRAddressToSitenamesExW);