2 Unix SMB/CIFS implementation.
4 endpoint server for the netlogon pipe
6 Copyright (C) Andrew Bartlett <abartlet@samba.org> 2004
7 Copyright (C) Stefan Metzmacher <metze@samba.org> 2005
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 3 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program. If not, see <http://www.gnu.org/licenses/>.
24 #include "rpc_server/dcerpc_server.h"
25 #include "rpc_server/common/common.h"
26 #include "lib/ldb/include/ldb.h"
27 #include "auth/auth.h"
28 #include "auth/auth_sam_reply.h"
29 #include "dsdb/samdb/samdb.h"
30 #include "dsdb/common/flags.h"
31 #include "rpc_server/samr/proto.h"
32 #include "util/util_ldb.h"
33 #include "libcli/auth/libcli_auth.h"
34 #include "auth/gensec/schannel_state.h"
35 #include "libcli/security/security.h"
36 #include "param/param.h"
38 struct server_pipe_state {
39 struct netr_Credential client_challenge;
40 struct netr_Credential server_challenge;
44 static NTSTATUS dcesrv_netr_ServerReqChallenge(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
45 struct netr_ServerReqChallenge *r)
47 struct server_pipe_state *pipe_state = dce_call->context->private;
49 ZERO_STRUCTP(r->out.credentials);
51 /* destroyed on pipe shutdown */
54 talloc_free(pipe_state);
55 dce_call->context->private = NULL;
58 pipe_state = talloc(dce_call->context, struct server_pipe_state);
59 NT_STATUS_HAVE_NO_MEMORY(pipe_state);
61 pipe_state->client_challenge = *r->in.credentials;
63 generate_random_buffer(pipe_state->server_challenge.data,
64 sizeof(pipe_state->server_challenge.data));
66 *r->out.credentials = pipe_state->server_challenge;
68 dce_call->context->private = pipe_state;
73 static NTSTATUS dcesrv_netr_ServerAuthenticate3(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
74 struct netr_ServerAuthenticate3 *r)
76 struct server_pipe_state *pipe_state = dce_call->context->private;
77 struct creds_CredentialState *creds;
79 struct samr_Password *mach_pwd;
80 uint32_t user_account_control;
82 struct ldb_message **msgs;
84 const char *attrs[] = {"unicodePwd", "userAccountControl",
87 ZERO_STRUCTP(r->out.credentials);
89 *r->out.negotiate_flags = *r->in.negotiate_flags;
92 DEBUG(1, ("No challenge requested by client, cannot authenticate\n"));
93 return NT_STATUS_ACCESS_DENIED;
96 sam_ctx = samdb_connect(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx,
97 system_session(mem_ctx, dce_call->conn->dce_ctx->lp_ctx));
98 if (sam_ctx == NULL) {
99 return NT_STATUS_INVALID_SYSTEM_SERVICE;
101 /* pull the user attributes */
102 num_records = gendb_search(sam_ctx, mem_ctx, NULL, &msgs, attrs,
103 "(&(sAMAccountName=%s)(objectclass=user))",
106 if (num_records == 0) {
107 DEBUG(3,("Couldn't find user [%s] in samdb.\n",
108 r->in.account_name));
109 return NT_STATUS_ACCESS_DENIED;
112 if (num_records > 1) {
113 DEBUG(0,("Found %d records matching user [%s]\n", num_records, r->in.account_name));
114 return NT_STATUS_INTERNAL_DB_CORRUPTION;
118 user_account_control = ldb_msg_find_attr_as_uint(msgs[0], "userAccountControl", 0);
120 if (user_account_control & UF_ACCOUNTDISABLE) {
121 DEBUG(1, ("Account [%s] is disabled\n", r->in.account_name));
122 return NT_STATUS_ACCESS_DENIED;
125 if (r->in.secure_channel_type == SEC_CHAN_WKSTA) {
126 if (!(user_account_control & UF_WORKSTATION_TRUST_ACCOUNT)) {
127 DEBUG(1, ("Client asked for a workstation secure channel, but is not a workstation (member server) acb flags: 0x%x\n", user_account_control));
128 return NT_STATUS_ACCESS_DENIED;
130 } else if (r->in.secure_channel_type == SEC_CHAN_DOMAIN) {
131 if (!(user_account_control & UF_INTERDOMAIN_TRUST_ACCOUNT)) {
132 DEBUG(1, ("Client asked for a trusted domain secure channel, but is not a trusted domain: acb flags: 0x%x\n", user_account_control));
134 return NT_STATUS_ACCESS_DENIED;
136 } else if (r->in.secure_channel_type == SEC_CHAN_BDC) {
137 if (!(user_account_control & UF_SERVER_TRUST_ACCOUNT)) {
138 DEBUG(1, ("Client asked for a server secure channel, but is not a server (domain controller): acb flags: 0x%x\n", user_account_control));
139 return NT_STATUS_ACCESS_DENIED;
142 DEBUG(1, ("Client asked for an invalid secure channel type: %d\n",
143 r->in.secure_channel_type));
144 return NT_STATUS_ACCESS_DENIED;
147 *r->out.rid = samdb_result_rid_from_sid(mem_ctx, msgs[0],
150 mach_pwd = samdb_result_hash(mem_ctx, msgs[0], "unicodePwd");
151 if (mach_pwd == NULL) {
152 return NT_STATUS_ACCESS_DENIED;
155 creds = talloc(mem_ctx, struct creds_CredentialState);
156 NT_STATUS_HAVE_NO_MEMORY(creds);
158 creds_server_init(creds, &pipe_state->client_challenge,
159 &pipe_state->server_challenge, mach_pwd,
161 *r->in.negotiate_flags);
163 if (!creds_server_check(creds, r->in.credentials)) {
165 return NT_STATUS_ACCESS_DENIED;
168 creds->account_name = talloc_steal(creds, r->in.account_name);
170 creds->computer_name = talloc_steal(creds, r->in.computer_name);
171 creds->domain = talloc_strdup(creds, lp_workgroup(dce_call->conn->dce_ctx->lp_ctx));
173 creds->secure_channel_type = r->in.secure_channel_type;
175 creds->sid = samdb_result_dom_sid(creds, msgs[0], "objectSid");
178 /* remember this session key state */
179 nt_status = schannel_store_session_key(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx, creds);
184 static NTSTATUS dcesrv_netr_ServerAuthenticate(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
185 struct netr_ServerAuthenticate *r)
187 struct netr_ServerAuthenticate3 r3;
190 * negotiate_flags is used as an [in] parameter
191 * so it need to be initialised.
193 * (I think ... = 0; seems wrong here --metze)
195 uint32_t negotiate_flags = 0;
197 r3.in.server_name = r->in.server_name;
198 r3.in.account_name = r->in.account_name;
199 r3.in.secure_channel_type = r->in.secure_channel_type;
200 r3.in.computer_name = r->in.computer_name;
201 r3.in.credentials = r->in.credentials;
202 r3.out.credentials = r->out.credentials;
203 r3.in.negotiate_flags = &negotiate_flags;
204 r3.out.negotiate_flags = &negotiate_flags;
207 return dcesrv_netr_ServerAuthenticate3(dce_call, mem_ctx, &r3);
210 static NTSTATUS dcesrv_netr_ServerAuthenticate2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
211 struct netr_ServerAuthenticate2 *r)
213 struct netr_ServerAuthenticate3 r3;
216 r3.in.server_name = r->in.server_name;
217 r3.in.account_name = r->in.account_name;
218 r3.in.secure_channel_type = r->in.secure_channel_type;
219 r3.in.computer_name = r->in.computer_name;
220 r3.in.credentials = r->in.credentials;
221 r3.out.credentials = r->out.credentials;
222 r3.in.negotiate_flags = r->in.negotiate_flags;
223 r3.out.negotiate_flags = r->out.negotiate_flags;
226 return dcesrv_netr_ServerAuthenticate3(dce_call, mem_ctx, &r3);
230 Validate an incoming authenticator against the credentials for the remote machine.
232 The credentials are (re)read and from the schannel database, and
233 written back after the caclulations are performed.
235 The creds_out parameter (if not NULL) returns the credentials, if
236 the caller needs some of that information.
239 static NTSTATUS dcesrv_netr_creds_server_step_check(struct event_context *event_ctx,
240 struct loadparm_context *lp_ctx,
241 const char *computer_name,
243 struct netr_Authenticator *received_authenticator,
244 struct netr_Authenticator *return_authenticator,
245 struct creds_CredentialState **creds_out)
247 struct creds_CredentialState *creds;
249 struct ldb_context *ldb;
252 ldb = schannel_db_connect(mem_ctx, event_ctx, lp_ctx);
254 return NT_STATUS_ACCESS_DENIED;
257 ret = ldb_transaction_start(ldb);
260 return NT_STATUS_INTERNAL_DB_CORRUPTION;
263 /* Because this is a shared structure (even across
264 * disconnects) we must update the database every time we
265 * update the structure */
267 nt_status = schannel_fetch_session_key_ldb(ldb, ldb, computer_name,
268 lp_workgroup(lp_ctx),
270 if (NT_STATUS_IS_OK(nt_status)) {
271 nt_status = creds_server_step_check(creds,
272 received_authenticator,
273 return_authenticator);
275 if (NT_STATUS_IS_OK(nt_status)) {
276 nt_status = schannel_store_session_key_ldb(ldb, ldb, creds);
279 if (NT_STATUS_IS_OK(nt_status)) {
280 ldb_transaction_commit(ldb);
283 talloc_steal(mem_ctx, creds);
286 ldb_transaction_cancel(ldb);
293 Change the machine account password for the currently connected
294 client. Supplies only the NT#.
297 static NTSTATUS dcesrv_netr_ServerPasswordSet(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
298 struct netr_ServerPasswordSet *r)
300 struct creds_CredentialState *creds;
301 struct ldb_context *sam_ctx;
304 nt_status = dcesrv_netr_creds_server_step_check(dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx,
305 r->in.computer_name, mem_ctx,
306 &r->in.credential, &r->out.return_authenticator,
308 NT_STATUS_NOT_OK_RETURN(nt_status);
310 sam_ctx = samdb_connect(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx, system_session(mem_ctx, dce_call->conn->dce_ctx->lp_ctx));
311 if (sam_ctx == NULL) {
312 return NT_STATUS_INVALID_SYSTEM_SERVICE;
315 creds_des_decrypt(creds, &r->in.new_password);
317 /* Using the sid for the account as the key, set the password */
318 nt_status = samdb_set_password_sid(sam_ctx, mem_ctx,
320 NULL, /* Don't have plaintext */
321 NULL, &r->in.new_password,
322 false, /* This is not considered a password change */
328 Change the machine account password for the currently connected
329 client. Supplies new plaintext.
331 static NTSTATUS dcesrv_netr_ServerPasswordSet2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
332 struct netr_ServerPasswordSet2 *r)
334 struct creds_CredentialState *creds;
335 struct ldb_context *sam_ctx;
338 uint32_t new_pass_len;
341 struct samr_CryptPassword password_buf;
343 nt_status = dcesrv_netr_creds_server_step_check(dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx,
344 r->in.computer_name, mem_ctx,
345 &r->in.credential, &r->out.return_authenticator,
347 NT_STATUS_NOT_OK_RETURN(nt_status);
349 sam_ctx = samdb_connect(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx, system_session(mem_ctx, dce_call->conn->dce_ctx->lp_ctx));
350 if (sam_ctx == NULL) {
351 return NT_STATUS_INVALID_SYSTEM_SERVICE;
354 memcpy(password_buf.data, r->in.new_password.data, 512);
355 SIVAL(password_buf.data,512,r->in.new_password.length);
356 creds_arcfour_crypt(creds, password_buf.data, 516);
358 ret = decode_pw_buffer(password_buf.data, new_pass, sizeof(new_pass),
359 &new_pass_len, STR_UNICODE);
361 DEBUG(3,("netr_ServerPasswordSet2: failed to decode password buffer\n"));
362 return NT_STATUS_ACCESS_DENIED;
365 /* Using the sid for the account as the key, set the password */
366 nt_status = samdb_set_password_sid(sam_ctx, mem_ctx,
368 new_pass, /* we have plaintext */
370 false, /* This is not considered a password change */
379 static WERROR dcesrv_netr_LogonUasLogon(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
380 struct netr_LogonUasLogon *r)
382 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
389 static WERROR dcesrv_netr_LogonUasLogoff(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
390 struct netr_LogonUasLogoff *r)
392 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
397 netr_LogonSamLogon_base
399 This version of the function allows other wrappers to say 'do not check the credentials'
401 We can't do the traditional 'wrapping' format completly, as this function must only run under schannel
403 static NTSTATUS dcesrv_netr_LogonSamLogon_base(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
404 struct netr_LogonSamLogonEx *r, struct creds_CredentialState *creds)
406 struct auth_context *auth_context;
407 struct auth_usersupplied_info *user_info;
408 struct auth_serversupplied_info *server_info;
410 static const char zeros[16];
411 struct netr_SamBaseInfo *sam;
412 struct netr_SamInfo2 *sam2;
413 struct netr_SamInfo3 *sam3;
414 struct netr_SamInfo6 *sam6;
416 user_info = talloc(mem_ctx, struct auth_usersupplied_info);
417 NT_STATUS_HAVE_NO_MEMORY(user_info);
419 user_info->flags = 0;
420 user_info->mapped_state = false;
421 user_info->remote_host = NULL;
423 switch (r->in.logon_level) {
424 case NetlogonInteractiveInformation:
425 case NetlogonServiceInformation:
426 case NetlogonInteractiveTransitiveInformation:
427 case NetlogonServiceTransitiveInformation:
428 if (creds->negotiate_flags & NETLOGON_NEG_ARCFOUR) {
429 creds_arcfour_crypt(creds,
430 r->in.logon.password->lmpassword.hash,
431 sizeof(r->in.logon.password->lmpassword.hash));
432 creds_arcfour_crypt(creds,
433 r->in.logon.password->ntpassword.hash,
434 sizeof(r->in.logon.password->ntpassword.hash));
436 creds_des_decrypt(creds, &r->in.logon.password->lmpassword);
437 creds_des_decrypt(creds, &r->in.logon.password->ntpassword);
440 /* TODO: we need to deny anonymous access here */
441 nt_status = auth_context_create(mem_ctx,
442 dce_call->event_ctx, dce_call->msg_ctx,
443 dce_call->conn->dce_ctx->lp_ctx,
445 NT_STATUS_NOT_OK_RETURN(nt_status);
447 user_info->logon_parameters = r->in.logon.password->identity_info.parameter_control;
448 user_info->client.account_name = r->in.logon.password->identity_info.account_name.string;
449 user_info->client.domain_name = r->in.logon.password->identity_info.domain_name.string;
450 user_info->workstation_name = r->in.logon.password->identity_info.workstation.string;
452 user_info->flags |= USER_INFO_INTERACTIVE_LOGON;
453 user_info->password_state = AUTH_PASSWORD_HASH;
455 user_info->password.hash.lanman = talloc(user_info, struct samr_Password);
456 NT_STATUS_HAVE_NO_MEMORY(user_info->password.hash.lanman);
457 *user_info->password.hash.lanman = r->in.logon.password->lmpassword;
459 user_info->password.hash.nt = talloc(user_info, struct samr_Password);
460 NT_STATUS_HAVE_NO_MEMORY(user_info->password.hash.nt);
461 *user_info->password.hash.nt = r->in.logon.password->ntpassword;
464 case NetlogonNetworkInformation:
465 case NetlogonNetworkTransitiveInformation:
467 /* TODO: we need to deny anonymous access here */
468 nt_status = auth_context_create(mem_ctx,
469 dce_call->event_ctx, dce_call->msg_ctx,
470 dce_call->conn->dce_ctx->lp_ctx,
472 NT_STATUS_NOT_OK_RETURN(nt_status);
474 nt_status = auth_context_set_challenge(auth_context, r->in.logon.network->challenge, "netr_LogonSamLogonWithFlags");
475 NT_STATUS_NOT_OK_RETURN(nt_status);
477 user_info->logon_parameters = r->in.logon.network->identity_info.parameter_control;
478 user_info->client.account_name = r->in.logon.network->identity_info.account_name.string;
479 user_info->client.domain_name = r->in.logon.network->identity_info.domain_name.string;
480 user_info->workstation_name = r->in.logon.network->identity_info.workstation.string;
482 user_info->password_state = AUTH_PASSWORD_RESPONSE;
483 user_info->password.response.lanman = data_blob_talloc(mem_ctx, r->in.logon.network->lm.data, r->in.logon.network->lm.length);
484 user_info->password.response.nt = data_blob_talloc(mem_ctx, r->in.logon.network->nt.data, r->in.logon.network->nt.length);
489 case NetlogonGenericInformation:
491 /* Until we get enough information for an implemetnation */
492 return NT_STATUS_INVALID_PARAMETER;
495 return NT_STATUS_INVALID_PARAMETER;
498 nt_status = auth_check_password(auth_context, mem_ctx, user_info, &server_info);
499 NT_STATUS_NOT_OK_RETURN(nt_status);
501 nt_status = auth_convert_server_info_sambaseinfo(mem_ctx, server_info, &sam);
502 NT_STATUS_NOT_OK_RETURN(nt_status);
504 /* Don't crypt an all-zero key, it would give away the NETLOGON pipe session key */
505 /* It appears that level 6 is not individually encrypted */
506 if ((r->in.validation_level != 6) &&
507 memcmp(sam->key.key, zeros, sizeof(sam->key.key)) != 0) {
508 /* This key is sent unencrypted without the ARCFOUR flag set */
509 if (creds->negotiate_flags & NETLOGON_NEG_ARCFOUR) {
510 creds_arcfour_crypt(creds,
512 sizeof(sam->key.key));
516 /* Don't crypt an all-zero key, it would give away the NETLOGON pipe session key */
517 /* It appears that level 6 is not individually encrypted */
518 if ((r->in.validation_level != 6) &&
519 memcmp(sam->LMSessKey.key, zeros, sizeof(sam->LMSessKey.key)) != 0) {
520 if (creds->negotiate_flags & NETLOGON_NEG_ARCFOUR) {
521 creds_arcfour_crypt(creds,
523 sizeof(sam->LMSessKey.key));
525 creds_des_encrypt_LMKey(creds,
530 switch (r->in.validation_level) {
532 sam2 = talloc_zero(mem_ctx, struct netr_SamInfo2);
533 NT_STATUS_HAVE_NO_MEMORY(sam2);
535 r->out.validation.sam2 = sam2;
539 sam3 = talloc_zero(mem_ctx, struct netr_SamInfo3);
540 NT_STATUS_HAVE_NO_MEMORY(sam3);
542 r->out.validation.sam3 = sam3;
546 sam6 = talloc_zero(mem_ctx, struct netr_SamInfo6);
547 NT_STATUS_HAVE_NO_MEMORY(sam6);
549 sam6->forest.string = lp_realm(dce_call->conn->dce_ctx->lp_ctx);
550 sam6->principle.string = talloc_asprintf(mem_ctx, "%s@%s",
551 sam->account_name.string, sam6->forest.string);
552 NT_STATUS_HAVE_NO_MEMORY(sam6->principle.string);
553 r->out.validation.sam6 = sam6;
560 r->out.authoritative = 1;
562 /* TODO: Describe and deal with these flags */
568 static NTSTATUS dcesrv_netr_LogonSamLogonEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
569 struct netr_LogonSamLogonEx *r)
572 struct creds_CredentialState *creds;
573 nt_status = schannel_fetch_session_key(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx, r->in.computer_name, lp_workgroup(dce_call->conn->dce_ctx->lp_ctx), &creds);
574 if (!NT_STATUS_IS_OK(nt_status)) {
578 if (!dce_call->conn->auth_state.auth_info ||
579 dce_call->conn->auth_state.auth_info->auth_type != DCERPC_AUTH_TYPE_SCHANNEL) {
580 return NT_STATUS_INTERNAL_ERROR;
582 return dcesrv_netr_LogonSamLogon_base(dce_call, mem_ctx, r, creds);
586 netr_LogonSamLogonWithFlags
589 static NTSTATUS dcesrv_netr_LogonSamLogonWithFlags(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
590 struct netr_LogonSamLogonWithFlags *r)
593 struct creds_CredentialState *creds;
594 struct netr_LogonSamLogonEx r2;
596 struct netr_Authenticator *return_authenticator;
598 return_authenticator = talloc(mem_ctx, struct netr_Authenticator);
599 NT_STATUS_HAVE_NO_MEMORY(return_authenticator);
601 nt_status = dcesrv_netr_creds_server_step_check(dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx,
602 r->in.computer_name, mem_ctx,
603 r->in.credential, return_authenticator,
605 NT_STATUS_NOT_OK_RETURN(nt_status);
609 r2.in.server_name = r->in.server_name;
610 r2.in.computer_name = r->in.computer_name;
611 r2.in.logon_level = r->in.logon_level;
612 r2.in.logon = r->in.logon;
613 r2.in.validation_level = r->in.validation_level;
614 r2.in.flags = r->in.flags;
616 nt_status = dcesrv_netr_LogonSamLogon_base(dce_call, mem_ctx, &r2, creds);
618 r->out.return_authenticator = return_authenticator;
619 r->out.validation = r2.out.validation;
620 r->out.authoritative = r2.out.authoritative;
621 r->out.flags = r2.out.flags;
629 static NTSTATUS dcesrv_netr_LogonSamLogon(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
630 struct netr_LogonSamLogon *r)
632 struct netr_LogonSamLogonWithFlags r2;
637 r2.in.server_name = r->in.server_name;
638 r2.in.computer_name = r->in.computer_name;
639 r2.in.credential = r->in.credential;
640 r2.in.return_authenticator = r->in.return_authenticator;
641 r2.in.logon_level = r->in.logon_level;
642 r2.in.logon = r->in.logon;
643 r2.in.validation_level = r->in.validation_level;
646 status = dcesrv_netr_LogonSamLogonWithFlags(dce_call, mem_ctx, &r2);
648 r->out.return_authenticator = r2.out.return_authenticator;
649 r->out.validation = r2.out.validation;
650 r->out.authoritative = r2.out.authoritative;
659 static NTSTATUS dcesrv_netr_LogonSamLogoff(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
660 struct netr_LogonSamLogoff *r)
662 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
670 static NTSTATUS dcesrv_netr_DatabaseDeltas(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
671 struct netr_DatabaseDeltas *r)
673 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
680 static NTSTATUS dcesrv_netr_DatabaseSync(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
681 struct netr_DatabaseSync *r)
683 /* win2k3 native mode returns "NOT IMPLEMENTED" for this call */
684 return NT_STATUS_NOT_IMPLEMENTED;
691 static NTSTATUS dcesrv_netr_AccountDeltas(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
692 struct netr_AccountDeltas *r)
694 /* w2k3 returns "NOT IMPLEMENTED" for this call */
695 return NT_STATUS_NOT_IMPLEMENTED;
702 static NTSTATUS dcesrv_netr_AccountSync(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
703 struct netr_AccountSync *r)
705 /* w2k3 returns "NOT IMPLEMENTED" for this call */
706 return NT_STATUS_NOT_IMPLEMENTED;
713 static WERROR dcesrv_netr_GetDcName(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
714 struct netr_GetDcName *r)
716 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
723 static WERROR dcesrv_netr_LogonControl(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
724 struct netr_LogonControl *r)
726 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
733 static WERROR dcesrv_netr_GetAnyDCName(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
734 struct netr_GetAnyDCName *r)
736 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
743 static WERROR dcesrv_netr_LogonControl2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
744 struct netr_LogonControl2 *r)
746 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
753 static NTSTATUS dcesrv_netr_DatabaseSync2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
754 struct netr_DatabaseSync2 *r)
756 /* win2k3 native mode returns "NOT IMPLEMENTED" for this call */
757 return NT_STATUS_NOT_IMPLEMENTED;
764 static NTSTATUS dcesrv_netr_DatabaseRedo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
765 struct netr_DatabaseRedo *r)
767 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
774 static WERROR dcesrv_netr_LogonControl2Ex(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
775 struct netr_LogonControl2Ex *r)
777 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
782 netr_NetrEnumerateTurstedDomains
784 static WERROR dcesrv_netr_NetrEnumerateTrustedDomains(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
785 struct netr_NetrEnumerateTrustedDomains *r)
787 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
792 netr_NETRLOGONDUMMYROUTINE1
794 static WERROR dcesrv_netr_NETRLOGONDUMMYROUTINE1(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
795 struct netr_NETRLOGONDUMMYROUTINE1 *r)
797 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
802 netr_NETRLOGONSETSERVICEBITS
804 static WERROR dcesrv_netr_NETRLOGONSETSERVICEBITS(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
805 struct netr_NETRLOGONSETSERVICEBITS *r)
807 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
812 netr_LogonGetTrustRid
814 static WERROR dcesrv_netr_LogonGetTrustRid(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
815 struct netr_LogonGetTrustRid *r)
817 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
822 netr_NETRLOGONCOMPUTESERVERDIGEST
824 static WERROR dcesrv_netr_NETRLOGONCOMPUTESERVERDIGEST(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
825 struct netr_NETRLOGONCOMPUTESERVERDIGEST *r)
827 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
832 netr_NETRLOGONCOMPUTECLIENTDIGEST
834 static WERROR dcesrv_netr_NETRLOGONCOMPUTECLIENTDIGEST(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
835 struct netr_NETRLOGONCOMPUTECLIENTDIGEST *r)
837 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
845 static WERROR dcesrv_netr_DsRGetSiteName(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
846 struct netr_DsRGetSiteName *r)
848 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
853 fill in a netr_DomainTrustInfo from a ldb search result
855 static NTSTATUS fill_domain_trust_info(TALLOC_CTX *mem_ctx,
856 struct ldb_message *res,
857 struct ldb_message *ref_res,
858 struct netr_DomainTrustInfo *info,
864 info->domainname.string = samdb_result_string(ref_res, "nETBIOSName", NULL);
865 info->fulldomainname.string = samdb_result_string(ref_res, "dnsRoot", NULL);
866 info->forest.string = NULL;
867 info->guid = samdb_result_guid(res, "objectGUID");
868 info->sid = samdb_result_dom_sid(mem_ctx, res, "objectSid");
870 info->domainname.string = samdb_result_string(res, "flatName", NULL);
871 info->fulldomainname.string = samdb_result_string(res, "trustPartner", NULL);
872 info->forest.string = NULL;
873 info->guid = samdb_result_guid(res, "objectGUID");
874 info->sid = samdb_result_dom_sid(mem_ctx, res, "securityIdentifier");
881 netr_LogonGetDomainInfo
882 this is called as part of the ADS domain logon procedure.
884 It has an important role in convaying details about the client, such
885 as Operating System, Version, Service Pack etc.
887 static NTSTATUS dcesrv_netr_LogonGetDomainInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
888 struct netr_LogonGetDomainInfo *r)
890 const char * const attrs[] = { "objectSid",
891 "objectGUID", "flatName", "securityIdentifier",
892 "trustPartner", NULL };
893 const char * const ref_attrs[] = { "nETBIOSName", "dnsRoot", NULL };
894 struct ldb_context *sam_ctx;
895 struct ldb_message **res1, **res2, **ref_res;
896 struct netr_DomainInfo1 *info1;
897 int ret, ret1, ret2, i;
899 struct ldb_dn *partitions_basedn;
901 const char *local_domain;
903 status = dcesrv_netr_creds_server_step_check(dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx,
904 r->in.computer_name, mem_ctx,
906 r->out.return_authenticator,
908 NT_STATUS_NOT_OK_RETURN(status);
910 sam_ctx = samdb_connect(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx, dce_call->conn->auth_state.session_info);
911 if (sam_ctx == NULL) {
912 return NT_STATUS_INVALID_SYSTEM_SERVICE;
915 partitions_basedn = samdb_partitions_dn(sam_ctx, mem_ctx);
917 /* we need to do two searches. The first will pull our primary
918 domain and the second will pull any trusted domains. Our
919 primary domain is also a "trusted" domain, so we need to
920 put the primary domain into the lists of returned trusts as
922 ret1 = gendb_search_dn(sam_ctx, mem_ctx, samdb_base_dn(sam_ctx), &res1, attrs);
924 return NT_STATUS_INTERNAL_DB_CORRUPTION;
927 /* try and find the domain */
928 ret = gendb_search(sam_ctx, mem_ctx, partitions_basedn,
930 "(&(objectClass=crossRef)(ncName=%s))",
931 ldb_dn_get_linearized(res1[0]->dn));
933 return NT_STATUS_INTERNAL_DB_CORRUPTION;
936 local_domain = samdb_result_string(ref_res[0], "nETBIOSName", NULL);
938 ret2 = gendb_search(sam_ctx, mem_ctx, NULL, &res2, attrs, "(objectClass=trustedDomain)");
940 return NT_STATUS_INTERNAL_DB_CORRUPTION;
943 info1 = talloc(mem_ctx, struct netr_DomainInfo1);
944 NT_STATUS_HAVE_NO_MEMORY(info1);
948 info1->num_trusts = ret2 + 1;
949 info1->trusts = talloc_array(mem_ctx, struct netr_DomainTrustInfo,
951 NT_STATUS_HAVE_NO_MEMORY(info1->trusts);
953 status = fill_domain_trust_info(mem_ctx, res1[0], ref_res[0], &info1->domaininfo, true);
954 NT_STATUS_NOT_OK_RETURN(status);
956 for (i=0;i<ret2;i++) {
957 status = fill_domain_trust_info(mem_ctx, res2[i], NULL, &info1->trusts[i], false);
958 NT_STATUS_NOT_OK_RETURN(status);
961 status = fill_domain_trust_info(mem_ctx, res1[0], ref_res[0], &info1->trusts[i], true);
962 NT_STATUS_NOT_OK_RETURN(status);
964 r->out.info.info1 = info1;
972 netr_ServerPasswordGet
974 static WERROR dcesrv_netr_ServerPasswordGet(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
975 struct netr_ServerPasswordGet *r)
977 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
982 netr_NETRLOGONSENDTOSAM
984 static WERROR dcesrv_netr_NETRLOGONSENDTOSAM(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
985 struct netr_NETRLOGONSENDTOSAM *r)
987 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
992 netr_DsRAddressToSitenamesW
994 static WERROR dcesrv_netr_DsRAddressToSitenamesW(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
995 struct netr_DsRAddressToSitenamesW *r)
997 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1002 netr_DsRGetDCNameEx2
1004 static WERROR dcesrv_netr_DsRGetDCNameEx2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1005 struct netr_DsRGetDCNameEx2 *r)
1007 const char * const attrs[] = { "dnsDomain", "objectGUID", NULL };
1009 struct ldb_message **res;
1010 struct ldb_dn *domain_dn;
1013 ZERO_STRUCT(r->out);
1015 sam_ctx = samdb_connect(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx, dce_call->conn->auth_state.session_info);
1016 if (sam_ctx == NULL) {
1017 return WERR_DS_SERVICE_UNAVAILABLE;
1020 domain_dn = samdb_dns_domain_to_dn(sam_ctx, mem_ctx,
1022 if (domain_dn == NULL) {
1023 return WERR_DS_SERVICE_UNAVAILABLE;
1026 ret = gendb_search_dn(sam_ctx, mem_ctx, domain_dn, &res, attrs);
1028 return WERR_NO_SUCH_DOMAIN;
1031 r->out.info = talloc(mem_ctx, struct netr_DsRGetDCNameInfo);
1032 W_ERROR_HAVE_NO_MEMORY(r->out.info);
1034 /* TODO: - return real IP address
1035 * - check all r->in.* parameters (server_unc is ignored by w2k3!)
1037 r->out.info->dc_unc = talloc_asprintf(mem_ctx, "\\\\%s.%s",
1038 lp_netbios_name(dce_call->conn->dce_ctx->lp_ctx),
1039 lp_realm(dce_call->conn->dce_ctx->lp_ctx));
1040 W_ERROR_HAVE_NO_MEMORY(r->out.info->dc_unc);
1041 r->out.info->dc_address = talloc_strdup(mem_ctx, "\\\\0.0.0.0");
1042 W_ERROR_HAVE_NO_MEMORY(r->out.info->dc_address);
1043 r->out.info->dc_address_type = DS_ADDRESS_TYPE_INET;
1044 r->out.info->domain_guid = samdb_result_guid(res[0], "objectGUID");
1045 r->out.info->domain_name = samdb_result_string(res[0], "dnsDomain", NULL);
1046 r->out.info->forest_name = samdb_result_string(res[0], "dnsDomain", NULL);
1047 r->out.info->dc_flags = DS_DNS_FOREST |
1050 DS_SERVER_WRITABLE |
1052 DS_SERVER_TIMESERV |
1058 r->out.info->dc_site_name = talloc_strdup(mem_ctx, "Default-First-Site-Name");
1059 W_ERROR_HAVE_NO_MEMORY(r->out.info->dc_site_name);
1060 r->out.info->client_site_name = talloc_strdup(mem_ctx, "Default-First-Site-Name");
1061 W_ERROR_HAVE_NO_MEMORY(r->out.info->client_site_name);
1069 static WERROR dcesrv_netr_DsRGetDCNameEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1070 struct netr_DsRGetDCNameEx *r)
1072 struct netr_DsRGetDCNameEx2 r2;
1077 r2.in.server_unc = r->in.server_unc;
1078 r2.in.client_account = NULL;
1080 r2.in.domain_guid = r->in.domain_guid;
1081 r2.in.domain_name = r->in.domain_name;
1082 r2.in.site_name = r->in.site_name;
1083 r2.in.flags = r->in.flags;
1086 werr = dcesrv_netr_DsRGetDCNameEx2(dce_call, mem_ctx, &r2);
1088 r->out.info = r2.out.info;
1096 static WERROR dcesrv_netr_DsRGetDCName(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1097 struct netr_DsRGetDCName *r)
1099 struct netr_DsRGetDCNameEx2 r2;
1104 r2.in.server_unc = r->in.server_unc;
1105 r2.in.client_account = NULL;
1107 r2.in.domain_name = r->in.domain_name;
1108 r2.in.domain_guid = r->in.domain_guid;
1110 r2.in.site_name = NULL; /* should fill in from site GUID */
1111 r2.in.flags = r->in.flags;
1114 werr = dcesrv_netr_DsRGetDCNameEx2(dce_call, mem_ctx, &r2);
1116 r->out.info = r2.out.info;
1122 netr_NETRLOGONGETTIMESERVICEPARENTDOMAIN
1124 static WERROR dcesrv_netr_NETRLOGONGETTIMESERVICEPARENTDOMAIN(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1125 struct netr_NETRLOGONGETTIMESERVICEPARENTDOMAIN *r)
1127 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1132 netr_NetrEnumerateTrustedDomainsEx
1134 static WERROR dcesrv_netr_NetrEnumerateTrustedDomainsEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1135 struct netr_NetrEnumerateTrustedDomainsEx *r)
1137 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1142 netr_DsRAddressToSitenamesExW
1144 static WERROR dcesrv_netr_DsRAddressToSitenamesExW(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1145 struct netr_DsRAddressToSitenamesExW *r)
1147 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1152 netr_DsrGetDcSiteCoverageW
1154 static WERROR dcesrv_netr_DsrGetDcSiteCoverageW(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1155 struct netr_DsrGetDcSiteCoverageW *r)
1157 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1162 netr_DsrEnumerateDomainTrusts
1164 static WERROR dcesrv_netr_DsrEnumerateDomainTrusts(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1165 struct netr_DsrEnumerateDomainTrusts *r)
1167 struct netr_DomainTrust *trusts;
1170 struct ldb_message **dom_res, **ref_res;
1171 const char * const dom_attrs[] = { "objectSid", "objectGUID", NULL };
1172 const char * const ref_attrs[] = { "nETBIOSName", "dnsRoot", NULL };
1173 struct ldb_dn *partitions_basedn;
1175 ZERO_STRUCT(r->out);
1177 sam_ctx = samdb_connect(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx, dce_call->conn->auth_state.session_info);
1178 if (sam_ctx == NULL) {
1179 return WERR_GENERAL_FAILURE;
1182 partitions_basedn = samdb_partitions_dn(sam_ctx, mem_ctx);
1184 ret = gendb_search_dn(sam_ctx, mem_ctx, NULL, &dom_res, dom_attrs);
1186 return WERR_GENERAL_FAILURE;
1189 return WERR_GENERAL_FAILURE;
1192 ret = gendb_search(sam_ctx, mem_ctx, partitions_basedn, &ref_res, ref_attrs,
1193 "(&(objectClass=crossRef)(ncName=%s))",
1194 ldb_dn_get_linearized(dom_res[0]->dn));
1196 return WERR_GENERAL_FAILURE;
1199 return WERR_GENERAL_FAILURE;
1202 trusts = talloc_array(mem_ctx, struct netr_DomainTrust, ret);
1203 W_ERROR_HAVE_NO_MEMORY(trusts);
1206 r->out.trusts = trusts;
1208 /* TODO: add filtering by trust_flags, and correct trust_type
1210 trusts[0].netbios_name = samdb_result_string(ref_res[0], "nETBIOSName", NULL);
1211 trusts[0].dns_name = samdb_result_string(ref_res[0], "dnsRoot", NULL);
1212 trusts[0].trust_flags =
1213 NETR_TRUST_FLAG_TREEROOT |
1214 NETR_TRUST_FLAG_IN_FOREST |
1215 NETR_TRUST_FLAG_PRIMARY;
1216 trusts[0].parent_index = 0;
1217 trusts[0].trust_type = 2;
1218 trusts[0].trust_attributes = 0;
1219 trusts[0].sid = samdb_result_dom_sid(mem_ctx, dom_res[0], "objectSid");
1220 trusts[0].guid = samdb_result_guid(dom_res[0], "objectGUID");
1227 netr_DsrDeregisterDNSHostRecords
1229 static WERROR dcesrv_netr_DsrDeregisterDNSHostRecords(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1230 struct netr_DsrDeregisterDNSHostRecords *r)
1232 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1237 netr_ServerTrustPasswordsGet
1239 static NTSTATUS dcesrv_netr_ServerTrustPasswordsGet(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1240 struct netr_ServerTrustPasswordsGet *r)
1242 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1247 netr_DsRGetForestTrustInformation
1249 static WERROR dcesrv_netr_DsRGetForestTrustInformation(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1250 struct netr_DsRGetForestTrustInformation *r)
1252 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1257 netr_GetForestTrustInformation
1259 static WERROR dcesrv_netr_GetForestTrustInformation(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1260 struct netr_GetForestTrustInformation *r)
1262 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1267 netr_NETRSERVERGETTRUSTINFO
1269 static WERROR dcesrv_netr_NETRSERVERGETTRUSTINFO(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1270 struct netr_NETRSERVERGETTRUSTINFO *r)
1272 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1276 /* include the generated boilerplate */
1277 #include "librpc/gen_ndr/ndr_netlogon_s.c"