2 Unix SMB/CIFS implementation.
4 endpoint server for the netlogon pipe
6 Copyright (C) Andrew Bartlett <abartlet@samba.org> 2004-2008
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"
37 #include "lib/messaging/irpc.h"
38 #include "librpc/gen_ndr/ndr_irpc.h"
40 struct server_pipe_state {
41 struct netr_Credential client_challenge;
42 struct netr_Credential server_challenge;
46 static NTSTATUS dcesrv_netr_ServerReqChallenge(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
47 struct netr_ServerReqChallenge *r)
49 struct server_pipe_state *pipe_state = dce_call->context->private;
51 ZERO_STRUCTP(r->out.credentials);
53 /* destroyed on pipe shutdown */
56 talloc_free(pipe_state);
57 dce_call->context->private = NULL;
60 pipe_state = talloc(dce_call->context, struct server_pipe_state);
61 NT_STATUS_HAVE_NO_MEMORY(pipe_state);
63 pipe_state->client_challenge = *r->in.credentials;
65 generate_random_buffer(pipe_state->server_challenge.data,
66 sizeof(pipe_state->server_challenge.data));
68 *r->out.credentials = pipe_state->server_challenge;
70 dce_call->context->private = pipe_state;
75 static NTSTATUS dcesrv_netr_ServerAuthenticate3(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
76 struct netr_ServerAuthenticate3 *r)
78 struct server_pipe_state *pipe_state = dce_call->context->private;
79 struct creds_CredentialState *creds;
81 struct samr_Password *mach_pwd;
82 uint32_t user_account_control;
84 struct ldb_message **msgs;
86 const char *attrs[] = {"unicodePwd", "userAccountControl",
89 ZERO_STRUCTP(r->out.credentials);
91 *r->out.negotiate_flags = *r->in.negotiate_flags;
94 DEBUG(1, ("No challenge requested by client, cannot authenticate\n"));
95 return NT_STATUS_ACCESS_DENIED;
98 sam_ctx = samdb_connect(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx,
99 system_session(mem_ctx, dce_call->conn->dce_ctx->lp_ctx));
100 if (sam_ctx == NULL) {
101 return NT_STATUS_INVALID_SYSTEM_SERVICE;
103 /* pull the user attributes */
104 num_records = gendb_search(sam_ctx, mem_ctx, NULL, &msgs, attrs,
105 "(&(sAMAccountName=%s)(objectclass=user))",
108 if (num_records == 0) {
109 DEBUG(3,("Couldn't find user [%s] in samdb.\n",
110 r->in.account_name));
111 return NT_STATUS_ACCESS_DENIED;
114 if (num_records > 1) {
115 DEBUG(0,("Found %d records matching user [%s]\n", num_records, r->in.account_name));
116 return NT_STATUS_INTERNAL_DB_CORRUPTION;
120 user_account_control = ldb_msg_find_attr_as_uint(msgs[0], "userAccountControl", 0);
122 if (user_account_control & UF_ACCOUNTDISABLE) {
123 DEBUG(1, ("Account [%s] is disabled\n", r->in.account_name));
124 return NT_STATUS_ACCESS_DENIED;
127 if (r->in.secure_channel_type == SEC_CHAN_WKSTA) {
128 if (!(user_account_control & UF_WORKSTATION_TRUST_ACCOUNT)) {
129 DEBUG(1, ("Client asked for a workstation secure channel, but is not a workstation (member server) acb flags: 0x%x\n", user_account_control));
130 return NT_STATUS_ACCESS_DENIED;
132 } else if (r->in.secure_channel_type == SEC_CHAN_DOMAIN) {
133 if (!(user_account_control & UF_INTERDOMAIN_TRUST_ACCOUNT)) {
134 DEBUG(1, ("Client asked for a trusted domain secure channel, but is not a trusted domain: acb flags: 0x%x\n", user_account_control));
136 return NT_STATUS_ACCESS_DENIED;
138 } else if (r->in.secure_channel_type == SEC_CHAN_BDC) {
139 if (!(user_account_control & UF_SERVER_TRUST_ACCOUNT)) {
140 DEBUG(1, ("Client asked for a server secure channel, but is not a server (domain controller): acb flags: 0x%x\n", user_account_control));
141 return NT_STATUS_ACCESS_DENIED;
144 DEBUG(1, ("Client asked for an invalid secure channel type: %d\n",
145 r->in.secure_channel_type));
146 return NT_STATUS_ACCESS_DENIED;
149 *r->out.rid = samdb_result_rid_from_sid(mem_ctx, msgs[0],
152 mach_pwd = samdb_result_hash(mem_ctx, msgs[0], "unicodePwd");
153 if (mach_pwd == NULL) {
154 return NT_STATUS_ACCESS_DENIED;
157 creds = talloc(mem_ctx, struct creds_CredentialState);
158 NT_STATUS_HAVE_NO_MEMORY(creds);
160 creds_server_init(creds, &pipe_state->client_challenge,
161 &pipe_state->server_challenge, mach_pwd,
163 *r->in.negotiate_flags);
165 if (!creds_server_check(creds, r->in.credentials)) {
167 return NT_STATUS_ACCESS_DENIED;
170 creds->account_name = talloc_steal(creds, r->in.account_name);
172 creds->computer_name = talloc_steal(creds, r->in.computer_name);
173 creds->domain = talloc_strdup(creds, lp_workgroup(dce_call->conn->dce_ctx->lp_ctx));
175 creds->secure_channel_type = r->in.secure_channel_type;
177 creds->sid = samdb_result_dom_sid(creds, msgs[0], "objectSid");
180 /* remember this session key state */
181 nt_status = schannel_store_session_key(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx, creds);
186 static NTSTATUS dcesrv_netr_ServerAuthenticate(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
187 struct netr_ServerAuthenticate *r)
189 struct netr_ServerAuthenticate3 r3;
192 * negotiate_flags is used as an [in] parameter
193 * so it need to be initialised.
195 * (I think ... = 0; seems wrong here --metze)
197 uint32_t negotiate_flags = 0;
199 r3.in.server_name = r->in.server_name;
200 r3.in.account_name = r->in.account_name;
201 r3.in.secure_channel_type = r->in.secure_channel_type;
202 r3.in.computer_name = r->in.computer_name;
203 r3.in.credentials = r->in.credentials;
204 r3.out.credentials = r->out.credentials;
205 r3.in.negotiate_flags = &negotiate_flags;
206 r3.out.negotiate_flags = &negotiate_flags;
209 return dcesrv_netr_ServerAuthenticate3(dce_call, mem_ctx, &r3);
212 static NTSTATUS dcesrv_netr_ServerAuthenticate2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
213 struct netr_ServerAuthenticate2 *r)
215 struct netr_ServerAuthenticate3 r3;
218 r3.in.server_name = r->in.server_name;
219 r3.in.account_name = r->in.account_name;
220 r3.in.secure_channel_type = r->in.secure_channel_type;
221 r3.in.computer_name = r->in.computer_name;
222 r3.in.credentials = r->in.credentials;
223 r3.out.credentials = r->out.credentials;
224 r3.in.negotiate_flags = r->in.negotiate_flags;
225 r3.out.negotiate_flags = r->out.negotiate_flags;
228 return dcesrv_netr_ServerAuthenticate3(dce_call, mem_ctx, &r3);
232 Validate an incoming authenticator against the credentials for the remote machine.
234 The credentials are (re)read and from the schannel database, and
235 written back after the caclulations are performed.
237 The creds_out parameter (if not NULL) returns the credentials, if
238 the caller needs some of that information.
241 static NTSTATUS dcesrv_netr_creds_server_step_check(struct event_context *event_ctx,
242 struct loadparm_context *lp_ctx,
243 const char *computer_name,
245 struct netr_Authenticator *received_authenticator,
246 struct netr_Authenticator *return_authenticator,
247 struct creds_CredentialState **creds_out)
249 struct creds_CredentialState *creds;
251 struct ldb_context *ldb;
254 ldb = schannel_db_connect(mem_ctx, event_ctx, lp_ctx);
256 return NT_STATUS_ACCESS_DENIED;
259 ret = ldb_transaction_start(ldb);
262 return NT_STATUS_INTERNAL_DB_CORRUPTION;
265 /* Because this is a shared structure (even across
266 * disconnects) we must update the database every time we
267 * update the structure */
269 nt_status = schannel_fetch_session_key_ldb(ldb, ldb, computer_name,
270 lp_workgroup(lp_ctx),
272 if (NT_STATUS_IS_OK(nt_status)) {
273 nt_status = creds_server_step_check(creds,
274 received_authenticator,
275 return_authenticator);
277 if (NT_STATUS_IS_OK(nt_status)) {
278 nt_status = schannel_store_session_key_ldb(ldb, ldb, creds);
281 if (NT_STATUS_IS_OK(nt_status)) {
282 ldb_transaction_commit(ldb);
285 talloc_steal(mem_ctx, creds);
288 ldb_transaction_cancel(ldb);
295 Change the machine account password for the currently connected
296 client. Supplies only the NT#.
299 static NTSTATUS dcesrv_netr_ServerPasswordSet(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
300 struct netr_ServerPasswordSet *r)
302 struct creds_CredentialState *creds;
303 struct ldb_context *sam_ctx;
306 nt_status = dcesrv_netr_creds_server_step_check(dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx,
307 r->in.computer_name, mem_ctx,
308 &r->in.credential, &r->out.return_authenticator,
310 NT_STATUS_NOT_OK_RETURN(nt_status);
312 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));
313 if (sam_ctx == NULL) {
314 return NT_STATUS_INVALID_SYSTEM_SERVICE;
317 creds_des_decrypt(creds, &r->in.new_password);
319 /* Using the sid for the account as the key, set the password */
320 nt_status = samdb_set_password_sid(sam_ctx, mem_ctx,
322 NULL, /* Don't have plaintext */
323 NULL, &r->in.new_password,
324 false, /* This is not considered a password change */
330 Change the machine account password for the currently connected
331 client. Supplies new plaintext.
333 static NTSTATUS dcesrv_netr_ServerPasswordSet2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
334 struct netr_ServerPasswordSet2 *r)
336 struct creds_CredentialState *creds;
337 struct ldb_context *sam_ctx;
342 struct samr_CryptPassword password_buf;
344 nt_status = dcesrv_netr_creds_server_step_check(dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx,
345 r->in.computer_name, mem_ctx,
346 &r->in.credential, &r->out.return_authenticator,
348 NT_STATUS_NOT_OK_RETURN(nt_status);
350 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));
351 if (sam_ctx == NULL) {
352 return NT_STATUS_INVALID_SYSTEM_SERVICE;
355 memcpy(password_buf.data, r->in.new_password.data, 512);
356 SIVAL(password_buf.data,512,r->in.new_password.length);
357 creds_arcfour_crypt(creds, password_buf.data, 516);
359 ret = decode_pw_buffer(password_buf.data, new_pass, sizeof(new_pass),
362 DEBUG(3,("netr_ServerPasswordSet2: failed to decode password buffer\n"));
363 return NT_STATUS_ACCESS_DENIED;
366 /* Using the sid for the account as the key, set the password */
367 nt_status = samdb_set_password_sid(sam_ctx, mem_ctx,
369 new_pass, /* we have plaintext */
371 false, /* This is not considered a password change */
380 static WERROR dcesrv_netr_LogonUasLogon(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
381 struct netr_LogonUasLogon *r)
383 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
390 static WERROR dcesrv_netr_LogonUasLogoff(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
391 struct netr_LogonUasLogoff *r)
393 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
398 netr_LogonSamLogon_base
400 This version of the function allows other wrappers to say 'do not check the credentials'
402 We can't do the traditional 'wrapping' format completly, as this function must only run under schannel
404 static NTSTATUS dcesrv_netr_LogonSamLogon_base(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
405 struct netr_LogonSamLogonEx *r, struct creds_CredentialState *creds)
407 struct auth_context *auth_context;
408 struct auth_usersupplied_info *user_info;
409 struct auth_serversupplied_info *server_info;
411 static const char zeros[16];
412 struct netr_SamBaseInfo *sam;
413 struct netr_SamInfo2 *sam2;
414 struct netr_SamInfo3 *sam3;
415 struct netr_SamInfo6 *sam6;
417 user_info = talloc(mem_ctx, struct auth_usersupplied_info);
418 NT_STATUS_HAVE_NO_MEMORY(user_info);
420 user_info->flags = 0;
421 user_info->mapped_state = false;
422 user_info->remote_host = NULL;
424 switch (r->in.logon_level) {
425 case NetlogonInteractiveInformation:
426 case NetlogonServiceInformation:
427 case NetlogonInteractiveTransitiveInformation:
428 case NetlogonServiceTransitiveInformation:
429 if (creds->negotiate_flags & NETLOGON_NEG_ARCFOUR) {
430 creds_arcfour_crypt(creds,
431 r->in.logon.password->lmpassword.hash,
432 sizeof(r->in.logon.password->lmpassword.hash));
433 creds_arcfour_crypt(creds,
434 r->in.logon.password->ntpassword.hash,
435 sizeof(r->in.logon.password->ntpassword.hash));
437 creds_des_decrypt(creds, &r->in.logon.password->lmpassword);
438 creds_des_decrypt(creds, &r->in.logon.password->ntpassword);
441 /* TODO: we need to deny anonymous access here */
442 nt_status = auth_context_create(mem_ctx,
443 dce_call->event_ctx, dce_call->msg_ctx,
444 dce_call->conn->dce_ctx->lp_ctx,
446 NT_STATUS_NOT_OK_RETURN(nt_status);
448 user_info->logon_parameters = r->in.logon.password->identity_info.parameter_control;
449 user_info->client.account_name = r->in.logon.password->identity_info.account_name.string;
450 user_info->client.domain_name = r->in.logon.password->identity_info.domain_name.string;
451 user_info->workstation_name = r->in.logon.password->identity_info.workstation.string;
453 user_info->flags |= USER_INFO_INTERACTIVE_LOGON;
454 user_info->password_state = AUTH_PASSWORD_HASH;
456 user_info->password.hash.lanman = talloc(user_info, struct samr_Password);
457 NT_STATUS_HAVE_NO_MEMORY(user_info->password.hash.lanman);
458 *user_info->password.hash.lanman = r->in.logon.password->lmpassword;
460 user_info->password.hash.nt = talloc(user_info, struct samr_Password);
461 NT_STATUS_HAVE_NO_MEMORY(user_info->password.hash.nt);
462 *user_info->password.hash.nt = r->in.logon.password->ntpassword;
465 case NetlogonNetworkInformation:
466 case NetlogonNetworkTransitiveInformation:
468 /* TODO: we need to deny anonymous access here */
469 nt_status = auth_context_create(mem_ctx,
470 dce_call->event_ctx, dce_call->msg_ctx,
471 dce_call->conn->dce_ctx->lp_ctx,
473 NT_STATUS_NOT_OK_RETURN(nt_status);
475 nt_status = auth_context_set_challenge(auth_context, r->in.logon.network->challenge, "netr_LogonSamLogonWithFlags");
476 NT_STATUS_NOT_OK_RETURN(nt_status);
478 user_info->logon_parameters = r->in.logon.network->identity_info.parameter_control;
479 user_info->client.account_name = r->in.logon.network->identity_info.account_name.string;
480 user_info->client.domain_name = r->in.logon.network->identity_info.domain_name.string;
481 user_info->workstation_name = r->in.logon.network->identity_info.workstation.string;
483 user_info->password_state = AUTH_PASSWORD_RESPONSE;
484 user_info->password.response.lanman = data_blob_talloc(mem_ctx, r->in.logon.network->lm.data, r->in.logon.network->lm.length);
485 user_info->password.response.nt = data_blob_talloc(mem_ctx, r->in.logon.network->nt.data, r->in.logon.network->nt.length);
490 case NetlogonGenericInformation:
492 if (creds->negotiate_flags & NETLOGON_NEG_ARCFOUR) {
493 creds_arcfour_crypt(creds,
494 r->in.logon.generic->data, r->in.logon.generic->length);
496 /* Using DES to verify kerberos tickets makes no sense */
497 return NT_STATUS_INVALID_PARAMETER;
500 if (strcmp(r->in.logon.generic->package_name.string, "Kerberos") == 0) {
502 struct server_id *kdc;
503 struct kdc_check_generic_kerberos check;
504 struct netr_GenericInfo2 *generic = talloc_zero(mem_ctx, struct netr_GenericInfo2);
505 NT_STATUS_HAVE_NO_MEMORY(generic);
506 r->out.authoritative = 1;
508 /* TODO: Describe and deal with these flags */
511 r->out.validation.generic = generic;
513 kdc = irpc_servers_byname(dce_call->msg_ctx, mem_ctx, "kdc_server");
514 if ((kdc == NULL) || (kdc[0].id == 0)) {
515 return NT_STATUS_NO_LOGON_SERVERS;
518 check.in.generic_request =
519 data_blob_const(r->in.logon.generic->data,
520 r->in.logon.generic->length);
522 status = irpc_call(dce_call->msg_ctx, kdc[0],
523 &ndr_table_irpc, NDR_KDC_CHECK_GENERIC_KERBEROS,
525 if (!NT_STATUS_IS_OK(status)) {
528 generic->length = check.out.generic_reply.length;
529 generic->data = check.out.generic_reply.data;
533 /* Until we get an implemetnation of these other packages */
534 return NT_STATUS_INVALID_PARAMETER;
537 return NT_STATUS_INVALID_PARAMETER;
540 nt_status = auth_check_password(auth_context, mem_ctx, user_info, &server_info);
541 NT_STATUS_NOT_OK_RETURN(nt_status);
543 nt_status = auth_convert_server_info_sambaseinfo(mem_ctx, server_info, &sam);
544 NT_STATUS_NOT_OK_RETURN(nt_status);
546 /* Don't crypt an all-zero key, it would give away the NETLOGON pipe session key */
547 /* It appears that level 6 is not individually encrypted */
548 if ((r->in.validation_level != 6) &&
549 memcmp(sam->key.key, zeros, sizeof(sam->key.key)) != 0) {
550 /* This key is sent unencrypted without the ARCFOUR flag set */
551 if (creds->negotiate_flags & NETLOGON_NEG_ARCFOUR) {
552 creds_arcfour_crypt(creds,
554 sizeof(sam->key.key));
558 /* Don't crypt an all-zero key, it would give away the NETLOGON pipe session key */
559 /* It appears that level 6 is not individually encrypted */
560 if ((r->in.validation_level != 6) &&
561 memcmp(sam->LMSessKey.key, zeros, sizeof(sam->LMSessKey.key)) != 0) {
562 if (creds->negotiate_flags & NETLOGON_NEG_ARCFOUR) {
563 creds_arcfour_crypt(creds,
565 sizeof(sam->LMSessKey.key));
567 creds_des_encrypt_LMKey(creds,
572 switch (r->in.validation_level) {
574 sam2 = talloc_zero(mem_ctx, struct netr_SamInfo2);
575 NT_STATUS_HAVE_NO_MEMORY(sam2);
577 r->out.validation.sam2 = sam2;
581 sam3 = talloc_zero(mem_ctx, struct netr_SamInfo3);
582 NT_STATUS_HAVE_NO_MEMORY(sam3);
584 r->out.validation.sam3 = sam3;
588 sam6 = talloc_zero(mem_ctx, struct netr_SamInfo6);
589 NT_STATUS_HAVE_NO_MEMORY(sam6);
591 sam6->forest.string = lp_realm(dce_call->conn->dce_ctx->lp_ctx);
592 sam6->principle.string = talloc_asprintf(mem_ctx, "%s@%s",
593 sam->account_name.string, sam6->forest.string);
594 NT_STATUS_HAVE_NO_MEMORY(sam6->principle.string);
595 r->out.validation.sam6 = sam6;
602 r->out.authoritative = 1;
604 /* TODO: Describe and deal with these flags */
610 static NTSTATUS dcesrv_netr_LogonSamLogonEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
611 struct netr_LogonSamLogonEx *r)
614 struct creds_CredentialState *creds;
615 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);
616 if (!NT_STATUS_IS_OK(nt_status)) {
620 if (!dce_call->conn->auth_state.auth_info ||
621 dce_call->conn->auth_state.auth_info->auth_type != DCERPC_AUTH_TYPE_SCHANNEL) {
622 return NT_STATUS_INTERNAL_ERROR;
624 return dcesrv_netr_LogonSamLogon_base(dce_call, mem_ctx, r, creds);
628 netr_LogonSamLogonWithFlags
631 static NTSTATUS dcesrv_netr_LogonSamLogonWithFlags(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
632 struct netr_LogonSamLogonWithFlags *r)
635 struct creds_CredentialState *creds;
636 struct netr_LogonSamLogonEx r2;
638 struct netr_Authenticator *return_authenticator;
640 return_authenticator = talloc(mem_ctx, struct netr_Authenticator);
641 NT_STATUS_HAVE_NO_MEMORY(return_authenticator);
643 nt_status = dcesrv_netr_creds_server_step_check(dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx,
644 r->in.computer_name, mem_ctx,
645 r->in.credential, return_authenticator,
647 NT_STATUS_NOT_OK_RETURN(nt_status);
651 r2.in.server_name = r->in.server_name;
652 r2.in.computer_name = r->in.computer_name;
653 r2.in.logon_level = r->in.logon_level;
654 r2.in.logon = r->in.logon;
655 r2.in.validation_level = r->in.validation_level;
656 r2.in.flags = r->in.flags;
658 nt_status = dcesrv_netr_LogonSamLogon_base(dce_call, mem_ctx, &r2, creds);
660 r->out.return_authenticator = return_authenticator;
661 r->out.validation = r2.out.validation;
662 r->out.authoritative = r2.out.authoritative;
663 r->out.flags = r2.out.flags;
671 static NTSTATUS dcesrv_netr_LogonSamLogon(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
672 struct netr_LogonSamLogon *r)
674 struct netr_LogonSamLogonWithFlags r2;
679 r2.in.server_name = r->in.server_name;
680 r2.in.computer_name = r->in.computer_name;
681 r2.in.credential = r->in.credential;
682 r2.in.return_authenticator = r->in.return_authenticator;
683 r2.in.logon_level = r->in.logon_level;
684 r2.in.logon = r->in.logon;
685 r2.in.validation_level = r->in.validation_level;
688 status = dcesrv_netr_LogonSamLogonWithFlags(dce_call, mem_ctx, &r2);
690 r->out.return_authenticator = r2.out.return_authenticator;
691 r->out.validation = r2.out.validation;
692 r->out.authoritative = r2.out.authoritative;
701 static NTSTATUS dcesrv_netr_LogonSamLogoff(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
702 struct netr_LogonSamLogoff *r)
704 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
712 static NTSTATUS dcesrv_netr_DatabaseDeltas(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
713 struct netr_DatabaseDeltas *r)
715 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
722 static NTSTATUS dcesrv_netr_DatabaseSync(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
723 struct netr_DatabaseSync *r)
725 /* win2k3 native mode returns "NOT IMPLEMENTED" for this call */
726 return NT_STATUS_NOT_IMPLEMENTED;
733 static NTSTATUS dcesrv_netr_AccountDeltas(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
734 struct netr_AccountDeltas *r)
736 /* w2k3 returns "NOT IMPLEMENTED" for this call */
737 return NT_STATUS_NOT_IMPLEMENTED;
744 static NTSTATUS dcesrv_netr_AccountSync(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
745 struct netr_AccountSync *r)
747 /* w2k3 returns "NOT IMPLEMENTED" for this call */
748 return NT_STATUS_NOT_IMPLEMENTED;
755 static WERROR dcesrv_netr_GetDcName(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
756 struct netr_GetDcName *r)
758 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
765 static WERROR dcesrv_netr_LogonControl(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
766 struct netr_LogonControl *r)
768 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
775 static WERROR dcesrv_netr_GetAnyDCName(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
776 struct netr_GetAnyDCName *r)
778 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
785 static WERROR dcesrv_netr_LogonControl2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
786 struct netr_LogonControl2 *r)
788 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
795 static NTSTATUS dcesrv_netr_DatabaseSync2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
796 struct netr_DatabaseSync2 *r)
798 /* win2k3 native mode returns "NOT IMPLEMENTED" for this call */
799 return NT_STATUS_NOT_IMPLEMENTED;
806 static NTSTATUS dcesrv_netr_DatabaseRedo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
807 struct netr_DatabaseRedo *r)
809 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
816 static WERROR dcesrv_netr_LogonControl2Ex(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
817 struct netr_LogonControl2Ex *r)
819 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
824 netr_NetrEnumerateTurstedDomains
826 static WERROR dcesrv_netr_NetrEnumerateTrustedDomains(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
827 struct netr_NetrEnumerateTrustedDomains *r)
829 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
834 netr_NETRLOGONDUMMYROUTINE1
836 static WERROR dcesrv_netr_NETRLOGONDUMMYROUTINE1(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
837 struct netr_NETRLOGONDUMMYROUTINE1 *r)
839 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
844 netr_NETRLOGONSETSERVICEBITS
846 static WERROR dcesrv_netr_NETRLOGONSETSERVICEBITS(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
847 struct netr_NETRLOGONSETSERVICEBITS *r)
849 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
854 netr_LogonGetTrustRid
856 static WERROR dcesrv_netr_LogonGetTrustRid(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
857 struct netr_LogonGetTrustRid *r)
859 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
864 netr_NETRLOGONCOMPUTESERVERDIGEST
866 static WERROR dcesrv_netr_NETRLOGONCOMPUTESERVERDIGEST(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
867 struct netr_NETRLOGONCOMPUTESERVERDIGEST *r)
869 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
874 netr_NETRLOGONCOMPUTECLIENTDIGEST
876 static WERROR dcesrv_netr_NETRLOGONCOMPUTECLIENTDIGEST(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
877 struct netr_NETRLOGONCOMPUTECLIENTDIGEST *r)
879 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
887 static WERROR dcesrv_netr_DsRGetSiteName(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
888 struct netr_DsRGetSiteName *r)
890 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
895 fill in a netr_DomainTrustInfo from a ldb search result
897 static NTSTATUS fill_domain_trust_info(TALLOC_CTX *mem_ctx,
898 struct ldb_message *res,
899 struct ldb_message *ref_res,
900 struct netr_DomainTrustInfo *info,
906 info->domainname.string = samdb_result_string(ref_res, "nETBIOSName", NULL);
907 info->fulldomainname.string = samdb_result_string(ref_res, "dnsRoot", NULL);
908 info->forest.string = NULL;
909 info->guid = samdb_result_guid(res, "objectGUID");
910 info->sid = samdb_result_dom_sid(mem_ctx, res, "objectSid");
912 info->domainname.string = samdb_result_string(res, "flatName", NULL);
913 info->fulldomainname.string = samdb_result_string(res, "trustPartner", NULL);
914 info->forest.string = NULL;
915 info->guid = samdb_result_guid(res, "objectGUID");
916 info->sid = samdb_result_dom_sid(mem_ctx, res, "securityIdentifier");
923 netr_LogonGetDomainInfo
924 this is called as part of the ADS domain logon procedure.
926 It has an important role in convaying details about the client, such
927 as Operating System, Version, Service Pack etc.
929 static NTSTATUS dcesrv_netr_LogonGetDomainInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
930 struct netr_LogonGetDomainInfo *r)
932 const char * const attrs[] = { "objectSid",
933 "objectGUID", "flatName", "securityIdentifier",
934 "trustPartner", NULL };
935 const char * const ref_attrs[] = { "nETBIOSName", "dnsRoot", NULL };
936 struct ldb_context *sam_ctx;
937 struct ldb_message **res1, **res2, **ref_res;
938 struct netr_DomainInfo1 *info1;
939 int ret, ret1, ret2, i;
941 struct ldb_dn *partitions_basedn;
943 const char *local_domain;
945 status = dcesrv_netr_creds_server_step_check(dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx,
946 r->in.computer_name, mem_ctx,
948 r->out.return_authenticator,
950 NT_STATUS_NOT_OK_RETURN(status);
952 sam_ctx = samdb_connect(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx, dce_call->conn->auth_state.session_info);
953 if (sam_ctx == NULL) {
954 return NT_STATUS_INVALID_SYSTEM_SERVICE;
957 partitions_basedn = samdb_partitions_dn(sam_ctx, mem_ctx);
959 /* we need to do two searches. The first will pull our primary
960 domain and the second will pull any trusted domains. Our
961 primary domain is also a "trusted" domain, so we need to
962 put the primary domain into the lists of returned trusts as
964 ret1 = gendb_search_dn(sam_ctx, mem_ctx, samdb_base_dn(sam_ctx), &res1, attrs);
966 return NT_STATUS_INTERNAL_DB_CORRUPTION;
969 /* try and find the domain */
970 ret = gendb_search(sam_ctx, mem_ctx, partitions_basedn,
972 "(&(objectClass=crossRef)(ncName=%s))",
973 ldb_dn_get_linearized(res1[0]->dn));
975 return NT_STATUS_INTERNAL_DB_CORRUPTION;
978 local_domain = samdb_result_string(ref_res[0], "nETBIOSName", NULL);
980 ret2 = gendb_search(sam_ctx, mem_ctx, NULL, &res2, attrs, "(objectClass=trustedDomain)");
982 return NT_STATUS_INTERNAL_DB_CORRUPTION;
985 info1 = talloc(mem_ctx, struct netr_DomainInfo1);
986 NT_STATUS_HAVE_NO_MEMORY(info1);
990 info1->num_trusts = ret2 + 1;
991 info1->trusts = talloc_array(mem_ctx, struct netr_DomainTrustInfo,
993 NT_STATUS_HAVE_NO_MEMORY(info1->trusts);
995 status = fill_domain_trust_info(mem_ctx, res1[0], ref_res[0], &info1->domaininfo, true);
996 NT_STATUS_NOT_OK_RETURN(status);
998 for (i=0;i<ret2;i++) {
999 status = fill_domain_trust_info(mem_ctx, res2[i], NULL, &info1->trusts[i], false);
1000 NT_STATUS_NOT_OK_RETURN(status);
1003 status = fill_domain_trust_info(mem_ctx, res1[0], ref_res[0], &info1->trusts[i], true);
1004 NT_STATUS_NOT_OK_RETURN(status);
1006 r->out.info.info1 = info1;
1008 return NT_STATUS_OK;
1014 netr_ServerPasswordGet
1016 static WERROR dcesrv_netr_ServerPasswordGet(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1017 struct netr_ServerPasswordGet *r)
1019 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1024 netr_NETRLOGONSENDTOSAM
1026 static WERROR dcesrv_netr_NETRLOGONSENDTOSAM(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1027 struct netr_NETRLOGONSENDTOSAM *r)
1029 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1034 netr_DsRAddressToSitenamesW
1036 static WERROR dcesrv_netr_DsRAddressToSitenamesW(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1037 struct netr_DsRAddressToSitenamesW *r)
1039 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1044 netr_DsRGetDCNameEx2
1046 static WERROR dcesrv_netr_DsRGetDCNameEx2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1047 struct netr_DsRGetDCNameEx2 *r)
1049 const char * const attrs[] = { "dnsDomain", "objectGUID", NULL };
1051 struct ldb_message **res;
1052 struct ldb_dn *domain_dn;
1055 ZERO_STRUCT(r->out);
1057 sam_ctx = samdb_connect(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx, dce_call->conn->auth_state.session_info);
1058 if (sam_ctx == NULL) {
1059 return WERR_DS_SERVICE_UNAVAILABLE;
1062 domain_dn = samdb_dns_domain_to_dn(sam_ctx, mem_ctx,
1064 if (domain_dn == NULL) {
1065 return WERR_DS_SERVICE_UNAVAILABLE;
1068 ret = gendb_search_dn(sam_ctx, mem_ctx, domain_dn, &res, attrs);
1070 return WERR_NO_SUCH_DOMAIN;
1073 r->out.info = talloc(mem_ctx, struct netr_DsRGetDCNameInfo);
1074 W_ERROR_HAVE_NO_MEMORY(r->out.info);
1076 /* TODO: - return real IP address
1077 * - check all r->in.* parameters (server_unc is ignored by w2k3!)
1079 r->out.info->dc_unc = talloc_asprintf(mem_ctx, "\\\\%s.%s",
1080 lp_netbios_name(dce_call->conn->dce_ctx->lp_ctx),
1081 lp_realm(dce_call->conn->dce_ctx->lp_ctx));
1082 W_ERROR_HAVE_NO_MEMORY(r->out.info->dc_unc);
1083 r->out.info->dc_address = talloc_strdup(mem_ctx, "\\\\0.0.0.0");
1084 W_ERROR_HAVE_NO_MEMORY(r->out.info->dc_address);
1085 r->out.info->dc_address_type = DS_ADDRESS_TYPE_INET;
1086 r->out.info->domain_guid = samdb_result_guid(res[0], "objectGUID");
1087 r->out.info->domain_name = samdb_result_string(res[0], "dnsDomain", NULL);
1088 r->out.info->forest_name = samdb_result_string(res[0], "dnsDomain", NULL);
1089 r->out.info->dc_flags = DS_DNS_FOREST |
1092 DS_SERVER_WRITABLE |
1094 DS_SERVER_TIMESERV |
1100 r->out.info->dc_site_name = talloc_strdup(mem_ctx, "Default-First-Site-Name");
1101 W_ERROR_HAVE_NO_MEMORY(r->out.info->dc_site_name);
1102 r->out.info->client_site_name = talloc_strdup(mem_ctx, "Default-First-Site-Name");
1103 W_ERROR_HAVE_NO_MEMORY(r->out.info->client_site_name);
1111 static WERROR dcesrv_netr_DsRGetDCNameEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1112 struct netr_DsRGetDCNameEx *r)
1114 struct netr_DsRGetDCNameEx2 r2;
1119 r2.in.server_unc = r->in.server_unc;
1120 r2.in.client_account = NULL;
1122 r2.in.domain_guid = r->in.domain_guid;
1123 r2.in.domain_name = r->in.domain_name;
1124 r2.in.site_name = r->in.site_name;
1125 r2.in.flags = r->in.flags;
1128 werr = dcesrv_netr_DsRGetDCNameEx2(dce_call, mem_ctx, &r2);
1130 r->out.info = r2.out.info;
1138 static WERROR dcesrv_netr_DsRGetDCName(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1139 struct netr_DsRGetDCName *r)
1141 struct netr_DsRGetDCNameEx2 r2;
1146 r2.in.server_unc = r->in.server_unc;
1147 r2.in.client_account = NULL;
1149 r2.in.domain_name = r->in.domain_name;
1150 r2.in.domain_guid = r->in.domain_guid;
1152 r2.in.site_name = NULL; /* should fill in from site GUID */
1153 r2.in.flags = r->in.flags;
1156 werr = dcesrv_netr_DsRGetDCNameEx2(dce_call, mem_ctx, &r2);
1158 r->out.info = r2.out.info;
1164 netr_NETRLOGONGETTIMESERVICEPARENTDOMAIN
1166 static WERROR dcesrv_netr_NETRLOGONGETTIMESERVICEPARENTDOMAIN(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1167 struct netr_NETRLOGONGETTIMESERVICEPARENTDOMAIN *r)
1169 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1174 netr_NetrEnumerateTrustedDomainsEx
1176 static WERROR dcesrv_netr_NetrEnumerateTrustedDomainsEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1177 struct netr_NetrEnumerateTrustedDomainsEx *r)
1179 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1184 netr_DsRAddressToSitenamesExW
1186 static WERROR dcesrv_netr_DsRAddressToSitenamesExW(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1187 struct netr_DsRAddressToSitenamesExW *r)
1189 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1194 netr_DsrGetDcSiteCoverageW
1196 static WERROR dcesrv_netr_DsrGetDcSiteCoverageW(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1197 struct netr_DsrGetDcSiteCoverageW *r)
1199 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1204 netr_DsrEnumerateDomainTrusts
1206 static WERROR dcesrv_netr_DsrEnumerateDomainTrusts(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1207 struct netr_DsrEnumerateDomainTrusts *r)
1209 struct netr_DomainTrust *trusts;
1212 struct ldb_message **dom_res, **ref_res;
1213 const char * const dom_attrs[] = { "objectSid", "objectGUID", NULL };
1214 const char * const ref_attrs[] = { "nETBIOSName", "dnsRoot", NULL };
1215 struct ldb_dn *partitions_basedn;
1217 ZERO_STRUCT(r->out);
1219 sam_ctx = samdb_connect(mem_ctx, dce_call->event_ctx, dce_call->conn->dce_ctx->lp_ctx, dce_call->conn->auth_state.session_info);
1220 if (sam_ctx == NULL) {
1221 return WERR_GENERAL_FAILURE;
1224 partitions_basedn = samdb_partitions_dn(sam_ctx, mem_ctx);
1226 ret = gendb_search_dn(sam_ctx, mem_ctx, NULL, &dom_res, dom_attrs);
1228 return WERR_GENERAL_FAILURE;
1231 return WERR_GENERAL_FAILURE;
1234 ret = gendb_search(sam_ctx, mem_ctx, partitions_basedn, &ref_res, ref_attrs,
1235 "(&(objectClass=crossRef)(ncName=%s))",
1236 ldb_dn_get_linearized(dom_res[0]->dn));
1238 return WERR_GENERAL_FAILURE;
1241 return WERR_GENERAL_FAILURE;
1244 trusts = talloc_array(mem_ctx, struct netr_DomainTrust, ret);
1245 W_ERROR_HAVE_NO_MEMORY(trusts);
1248 r->out.trusts = trusts;
1250 /* TODO: add filtering by trust_flags, and correct trust_type
1252 trusts[0].netbios_name = samdb_result_string(ref_res[0], "nETBIOSName", NULL);
1253 trusts[0].dns_name = samdb_result_string(ref_res[0], "dnsRoot", NULL);
1254 trusts[0].trust_flags =
1255 NETR_TRUST_FLAG_TREEROOT |
1256 NETR_TRUST_FLAG_IN_FOREST |
1257 NETR_TRUST_FLAG_PRIMARY;
1258 trusts[0].parent_index = 0;
1259 trusts[0].trust_type = 2;
1260 trusts[0].trust_attributes = 0;
1261 trusts[0].sid = samdb_result_dom_sid(mem_ctx, dom_res[0], "objectSid");
1262 trusts[0].guid = samdb_result_guid(dom_res[0], "objectGUID");
1269 netr_DsrDeregisterDNSHostRecords
1271 static WERROR dcesrv_netr_DsrDeregisterDNSHostRecords(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1272 struct netr_DsrDeregisterDNSHostRecords *r)
1274 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1279 netr_ServerTrustPasswordsGet
1281 static NTSTATUS dcesrv_netr_ServerTrustPasswordsGet(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1282 struct netr_ServerTrustPasswordsGet *r)
1284 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1289 netr_DsRGetForestTrustInformation
1291 static WERROR dcesrv_netr_DsRGetForestTrustInformation(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1292 struct netr_DsRGetForestTrustInformation *r)
1294 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1299 netr_GetForestTrustInformation
1301 static WERROR dcesrv_netr_GetForestTrustInformation(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1302 struct netr_GetForestTrustInformation *r)
1304 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1309 netr_NETRSERVERGETTRUSTINFO
1311 static WERROR dcesrv_netr_NETRSERVERGETTRUSTINFO(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1312 struct netr_NETRSERVERGETTRUSTINFO *r)
1314 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1318 /* include the generated boilerplate */
1319 #include "librpc/gen_ndr/ndr_netlogon_s.c"