Line data Source code
1 : /*
2 : * Unix SMB/CIFS implementation.
3 : * RPC Pipe client / server routines
4 : * Copyright (C) Andrew Tridgell 1992-1997,
5 : * Copyright (C) Luke Kenneth Casson Leighton 1996-1997,
6 : * Copyright (C) Paul Ashton 1997,
7 : * Copyright (C) Jeremy Allison 2001, 2006.
8 : * Copyright (C) Rafal Szczesniak 2002,
9 : * Copyright (C) Jim McDonough <jmcd@us.ibm.com> 2002,
10 : * Copyright (C) Simo Sorce 2003.
11 : * Copyright (C) Gerald (Jerry) Carter 2005.
12 : * Copyright (C) Volker Lendecke 2005.
13 : * Copyright (C) Guenther Deschner 2008.
14 : * Copyright (C) Andrew Bartlett 2010.
15 : *
16 : * This program is free software; you can redistribute it and/or modify
17 : * it under the terms of the GNU General Public License as published by
18 : * the Free Software Foundation; either version 3 of the License, or
19 : * (at your option) any later version.
20 : *
21 : * This program is distributed in the hope that it will be useful,
22 : * but WITHOUT ANY WARRANTY; without even the implied warranty of
23 : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24 : * GNU General Public License for more details.
25 : *
26 : * You should have received a copy of the GNU General Public License
27 : * along with this program; if not, see <http://www.gnu.org/licenses/>.
28 : */
29 :
30 : /* This is the implementation of the lsa server code. */
31 :
32 : #include "includes.h"
33 : #include "ntdomain.h"
34 : #include "librpc/gen_ndr/ndr_lsa.h"
35 : #include "librpc/gen_ndr/ndr_lsa_scompat.h"
36 : #include "secrets.h"
37 : #include "../librpc/gen_ndr/netlogon.h"
38 : #include "rpc_client/init_lsa.h"
39 : #include "../libcli/security/security.h"
40 : #include "../libcli/security/dom_sid.h"
41 : #include "../librpc/gen_ndr/drsblobs.h"
42 : #include "../librpc/gen_ndr/ndr_drsblobs.h"
43 : #include "../libcli/security/dom_sid.h"
44 : #include "../librpc/gen_ndr/ndr_security.h"
45 : #include "passdb.h"
46 : #include "auth.h"
47 : #include "lib/privileges.h"
48 : #include "rpc_server/srv_access_check.h"
49 : #include "../librpc/gen_ndr/ndr_wkssvc.h"
50 : #include "../libcli/auth/libcli_auth.h"
51 : #include "../libcli/lsarpc/util_lsarpc.h"
52 : #include "lsa.h"
53 : #include "librpc/rpc/dcesrv_core.h"
54 : #include "librpc/rpc/dcerpc_helper.h"
55 : #include "lib/param/loadparm.h"
56 : #include "source3/lib/substitute.h"
57 : #include "librpc/rpc/dcerpc_lsa.h"
58 :
59 : #include "lib/crypto/gnutls_helpers.h"
60 : #include <gnutls/gnutls.h>
61 : #include <gnutls/crypto.h>
62 :
63 : #undef strcasecmp
64 :
65 : #undef DBGC_CLASS
66 : #define DBGC_CLASS DBGC_RPC_SRV
67 :
68 : #define MAX_LOOKUP_SIDS 0x5000 /* 20480 */
69 :
70 : enum lsa_handle_type {
71 : LSA_HANDLE_POLICY_TYPE = 1,
72 : LSA_HANDLE_ACCOUNT_TYPE = 2,
73 : LSA_HANDLE_TRUST_TYPE = 3,
74 : LSA_HANDLE_SECRET_TYPE = 4};
75 :
76 : struct lsa_info {
77 : struct dom_sid sid;
78 : const char *name;
79 : uint32_t access;
80 : enum lsa_handle_type type;
81 : struct security_descriptor *sd;
82 : };
83 :
84 : const struct generic_mapping lsa_account_mapping = {
85 : LSA_ACCOUNT_READ,
86 : LSA_ACCOUNT_WRITE,
87 : LSA_ACCOUNT_EXECUTE,
88 : LSA_ACCOUNT_ALL_ACCESS
89 : };
90 :
91 : const struct generic_mapping lsa_policy_mapping = {
92 : LSA_POLICY_READ,
93 : LSA_POLICY_WRITE,
94 : LSA_POLICY_EXECUTE,
95 : LSA_POLICY_ALL_ACCESS
96 : };
97 :
98 : const struct generic_mapping lsa_secret_mapping = {
99 : LSA_SECRET_READ,
100 : LSA_SECRET_WRITE,
101 : LSA_SECRET_EXECUTE,
102 : LSA_SECRET_ALL_ACCESS
103 : };
104 :
105 : const struct generic_mapping lsa_trusted_domain_mapping = {
106 : LSA_TRUSTED_DOMAIN_READ,
107 : LSA_TRUSTED_DOMAIN_WRITE,
108 : LSA_TRUSTED_DOMAIN_EXECUTE,
109 : LSA_TRUSTED_DOMAIN_ALL_ACCESS
110 : };
111 :
112 : /***************************************************************************
113 : initialize a lsa_DomainInfo structure.
114 : ***************************************************************************/
115 :
116 60 : static void init_dom_query_3(struct lsa_DomainInfo *r,
117 : const char *name,
118 : struct dom_sid *sid)
119 : {
120 60 : init_lsa_StringLarge(&r->name, name);
121 60 : r->sid = sid;
122 60 : }
123 :
124 : /***************************************************************************
125 : initialize a lsa_DomainInfo structure.
126 : ***************************************************************************/
127 :
128 774 : static void init_dom_query_5(struct lsa_DomainInfo *r,
129 : const char *name,
130 : struct dom_sid *sid)
131 : {
132 774 : init_lsa_StringLarge(&r->name, name);
133 774 : r->sid = sid;
134 774 : }
135 :
136 : /***************************************************************************
137 : lookup_lsa_rids. Must be called as root for lookup_name to work.
138 : ***************************************************************************/
139 :
140 322 : static NTSTATUS lookup_lsa_rids(TALLOC_CTX *mem_ctx,
141 : struct lsa_RefDomainList *ref,
142 : struct lsa_TranslatedSid *prid,
143 : uint32_t num_entries,
144 : struct lsa_String *name,
145 : int flags,
146 : uint32_t *pmapped_count)
147 : {
148 0 : uint32_t mapped_count, i;
149 :
150 322 : SMB_ASSERT(num_entries <= MAX_LOOKUP_SIDS);
151 :
152 322 : mapped_count = 0;
153 322 : *pmapped_count = 0;
154 :
155 862 : for (i = 0; i < num_entries; i++) {
156 0 : struct dom_sid sid;
157 0 : uint32_t rid;
158 0 : int dom_idx;
159 0 : const char *full_name;
160 0 : const char *domain;
161 0 : enum lsa_SidType type;
162 :
163 : /* Split name into domain and user component */
164 :
165 : /* follow w2k8 behavior and return the builtin domain when no
166 : * input has been passed in */
167 :
168 540 : if (name[i].string) {
169 538 : full_name = name[i].string;
170 : } else {
171 2 : full_name = "BUILTIN";
172 : }
173 :
174 540 : DEBUG(5, ("lookup_lsa_rids: looking up name %s\n", full_name));
175 :
176 540 : if (!lookup_name(mem_ctx, full_name, flags, &domain, NULL,
177 : &sid, &type)) {
178 18 : type = SID_NAME_UNKNOWN;
179 : }
180 :
181 540 : switch (type) {
182 522 : case SID_NAME_USER:
183 : case SID_NAME_DOM_GRP:
184 : case SID_NAME_DOMAIN:
185 : case SID_NAME_ALIAS:
186 : case SID_NAME_WKN_GRP:
187 522 : DEBUG(5, ("init_lsa_rids: %s found\n", full_name));
188 : /* Leave these unchanged */
189 522 : break;
190 18 : default:
191 : /* Don't hand out anything but the list above */
192 18 : DEBUG(5, ("init_lsa_rids: %s not found\n", full_name));
193 18 : type = SID_NAME_UNKNOWN;
194 18 : break;
195 : }
196 :
197 540 : rid = 0;
198 540 : dom_idx = -1;
199 :
200 540 : if (type != SID_NAME_UNKNOWN) {
201 522 : if (type == SID_NAME_DOMAIN) {
202 24 : rid = (uint32_t)-1;
203 : } else {
204 498 : sid_split_rid(&sid, &rid);
205 : }
206 522 : dom_idx = init_lsa_ref_domain_list(mem_ctx, ref, domain, &sid);
207 522 : mapped_count++;
208 : }
209 :
210 540 : prid[i].sid_type = type;
211 540 : prid[i].rid = rid;
212 540 : prid[i].sid_index = dom_idx;
213 : }
214 :
215 322 : *pmapped_count = mapped_count;
216 322 : return NT_STATUS_OK;
217 : }
218 :
219 : /***************************************************************************
220 : lookup_lsa_sids. Must be called as root for lookup_name to work.
221 : ***************************************************************************/
222 :
223 52 : static NTSTATUS lookup_lsa_sids(TALLOC_CTX *mem_ctx,
224 : struct lsa_RefDomainList *ref,
225 : struct lsa_TranslatedSid3 *trans_sids,
226 : uint32_t num_entries,
227 : struct lsa_String *name,
228 : int flags,
229 : uint32_t *pmapped_count)
230 : {
231 0 : uint32_t mapped_count, i;
232 :
233 52 : SMB_ASSERT(num_entries <= MAX_LOOKUP_SIDS);
234 :
235 52 : mapped_count = 0;
236 52 : *pmapped_count = 0;
237 :
238 2466 : for (i = 0; i < num_entries; i++) {
239 0 : struct dom_sid sid;
240 0 : uint32_t rid;
241 0 : int dom_idx;
242 0 : const char *full_name;
243 0 : const char *domain;
244 0 : enum lsa_SidType type;
245 :
246 2414 : ZERO_STRUCT(sid);
247 :
248 : /* Split name into domain and user component */
249 :
250 2414 : full_name = name[i].string;
251 2414 : if (full_name == NULL) {
252 0 : return NT_STATUS_NO_MEMORY;
253 : }
254 :
255 2414 : DEBUG(5, ("lookup_lsa_sids: looking up name %s\n", full_name));
256 :
257 2414 : if (!lookup_name(mem_ctx, full_name, flags, &domain, NULL,
258 : &sid, &type)) {
259 0 : type = SID_NAME_UNKNOWN;
260 : }
261 :
262 2414 : switch (type) {
263 2414 : case SID_NAME_USER:
264 : case SID_NAME_DOM_GRP:
265 : case SID_NAME_DOMAIN:
266 : case SID_NAME_ALIAS:
267 : case SID_NAME_WKN_GRP:
268 2414 : DEBUG(5, ("lookup_lsa_sids: %s found\n", full_name));
269 : /* Leave these unchanged */
270 2414 : break;
271 0 : default:
272 : /* Don't hand out anything but the list above */
273 0 : DEBUG(5, ("lookup_lsa_sids: %s not found\n", full_name));
274 0 : type = SID_NAME_UNKNOWN;
275 0 : break;
276 : }
277 :
278 2414 : rid = 0;
279 2414 : dom_idx = -1;
280 :
281 2414 : if (type != SID_NAME_UNKNOWN) {
282 0 : struct dom_sid domain_sid;
283 2414 : sid_copy(&domain_sid, &sid);
284 2414 : sid_split_rid(&domain_sid, &rid);
285 2414 : dom_idx = init_lsa_ref_domain_list(mem_ctx, ref, domain, &domain_sid);
286 2414 : mapped_count++;
287 : }
288 :
289 : /* Initialize the lsa_TranslatedSid3 return. */
290 2414 : trans_sids[i].sid_type = type;
291 2414 : trans_sids[i].sid = dom_sid_dup(mem_ctx, &sid);
292 2414 : trans_sids[i].sid_index = dom_idx;
293 : }
294 :
295 52 : *pmapped_count = mapped_count;
296 52 : return NT_STATUS_OK;
297 : }
298 :
299 3188 : static NTSTATUS make_lsa_object_sd(TALLOC_CTX *mem_ctx, struct security_descriptor **sd, size_t *sd_size,
300 : const struct generic_mapping *map,
301 : struct dom_sid *sid, uint32_t sid_access)
302 : {
303 0 : struct dom_sid adm_sid;
304 0 : struct security_ace ace[5];
305 3188 : size_t i = 0;
306 :
307 3188 : struct security_acl *psa = NULL;
308 :
309 : /* READ|EXECUTE access for Everyone */
310 :
311 3188 : init_sec_ace(&ace[i++], &global_sid_World, SEC_ACE_TYPE_ACCESS_ALLOWED,
312 3188 : map->generic_execute | map->generic_read, 0);
313 :
314 : /* Add Full Access 'BUILTIN\Administrators' and 'BUILTIN\Account Operators */
315 :
316 3188 : init_sec_ace(&ace[i++], &global_sid_Builtin_Administrators,
317 3188 : SEC_ACE_TYPE_ACCESS_ALLOWED, map->generic_all, 0);
318 3188 : init_sec_ace(&ace[i++], &global_sid_Builtin_Account_Operators,
319 3188 : SEC_ACE_TYPE_ACCESS_ALLOWED, map->generic_all, 0);
320 :
321 : /* Add Full Access for Domain Admins */
322 3188 : sid_compose(&adm_sid, get_global_sam_sid(), DOMAIN_RID_ADMINS);
323 3188 : init_sec_ace(&ace[i++], &adm_sid, SEC_ACE_TYPE_ACCESS_ALLOWED,
324 3188 : map->generic_all, 0);
325 :
326 : /* If we have a sid, give it some special access */
327 :
328 3188 : if (sid) {
329 18 : init_sec_ace(&ace[i++], sid, SEC_ACE_TYPE_ACCESS_ALLOWED,
330 : sid_access, 0);
331 : }
332 :
333 3188 : if((psa = make_sec_acl(mem_ctx, NT4_ACL_REVISION, i, ace)) == NULL)
334 0 : return NT_STATUS_NO_MEMORY;
335 :
336 3188 : if((*sd = make_sec_desc(mem_ctx, SECURITY_DESCRIPTOR_REVISION_1,
337 : SEC_DESC_SELF_RELATIVE, &adm_sid, NULL, NULL,
338 : psa, sd_size)) == NULL)
339 0 : return NT_STATUS_NO_MEMORY;
340 :
341 3188 : return NT_STATUS_OK;
342 : }
343 :
344 : /***************************************************************************
345 : ***************************************************************************/
346 :
347 3142 : static NTSTATUS create_lsa_policy_handle(TALLOC_CTX *mem_ctx,
348 : struct pipes_struct *p,
349 : enum lsa_handle_type type,
350 : uint32_t acc_granted,
351 : struct dom_sid *sid,
352 : const char *name,
353 : const struct security_descriptor *sd,
354 : struct policy_handle *handle)
355 : {
356 0 : struct lsa_info *info;
357 :
358 3142 : ZERO_STRUCTP(handle);
359 :
360 3142 : info = talloc_zero(mem_ctx, struct lsa_info);
361 3142 : if (!info) {
362 0 : return NT_STATUS_NO_MEMORY;
363 : }
364 :
365 3142 : info->type = type;
366 3142 : info->access = acc_granted;
367 :
368 3142 : if (sid) {
369 2510 : sid_copy(&info->sid, sid);
370 : }
371 :
372 3142 : info->name = talloc_strdup(info, name);
373 :
374 3142 : if (sd != NULL) {
375 3142 : info->sd = security_descriptor_copy(info, sd);
376 3142 : if (info->sd == NULL) {
377 0 : talloc_free(info);
378 0 : return NT_STATUS_NO_MEMORY;
379 : }
380 : }
381 :
382 3142 : if (!create_policy_hnd(p, handle, type, info)) {
383 0 : talloc_free(info);
384 0 : ZERO_STRUCTP(handle);
385 0 : return NT_STATUS_NO_MEMORY;
386 : }
387 :
388 3142 : return NT_STATUS_OK;
389 : }
390 :
391 : /***************************************************************************
392 : _lsa_OpenPolicy2
393 : ***************************************************************************/
394 :
395 2430 : NTSTATUS _lsa_OpenPolicy2(struct pipes_struct *p,
396 : struct lsa_OpenPolicy2 *r)
397 : {
398 2430 : struct dcesrv_call_state *dce_call = p->dce_call;
399 0 : struct auth_session_info *session_info =
400 2430 : dcesrv_call_session_info(dce_call);
401 2430 : struct security_descriptor *psd = NULL;
402 0 : size_t sd_size;
403 2430 : uint32_t des_access = r->in.access_mask;
404 0 : uint32_t acc_granted;
405 0 : NTSTATUS status;
406 :
407 2430 : if (p->transport != NCACN_NP && p->transport != NCALRPC) {
408 4 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
409 4 : return NT_STATUS_ACCESS_DENIED;
410 : }
411 :
412 : /* Work out max allowed. */
413 2426 : map_max_allowed_access(session_info->security_token,
414 2426 : session_info->unix_token,
415 : &des_access);
416 :
417 : /* map the generic bits to the lsa policy ones */
418 2426 : se_map_generic(&des_access, &lsa_policy_mapping);
419 :
420 : /* get the generic lsa policy SD until we store it */
421 2426 : status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size, &lsa_policy_mapping,
422 : NULL, 0);
423 2426 : if (!NT_STATUS_IS_OK(status)) {
424 0 : return status;
425 : }
426 :
427 2426 : status = access_check_object(psd, session_info->security_token,
428 : SEC_PRIV_INVALID, SEC_PRIV_INVALID, 0, des_access,
429 : &acc_granted, "_lsa_OpenPolicy2" );
430 2426 : if (!NT_STATUS_IS_OK(status)) {
431 0 : return status;
432 : }
433 :
434 2426 : status = create_lsa_policy_handle(p->mem_ctx, p,
435 : LSA_HANDLE_POLICY_TYPE,
436 : acc_granted,
437 : get_global_sam_sid(),
438 : NULL,
439 : psd,
440 : r->out.handle);
441 2426 : if (!NT_STATUS_IS_OK(status)) {
442 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
443 : }
444 :
445 2426 : return NT_STATUS_OK;
446 : }
447 :
448 : /***************************************************************************
449 : _lsa_OpenPolicy
450 : ***************************************************************************/
451 :
452 1550 : NTSTATUS _lsa_OpenPolicy(struct pipes_struct *p,
453 : struct lsa_OpenPolicy *r)
454 : {
455 0 : struct lsa_OpenPolicy2 o;
456 :
457 : /* _lsa_OpenPolicy2 will check if this is a NCACN_NP connection */
458 :
459 1550 : o.in.system_name = NULL; /* should be ignored */
460 1550 : o.in.attr = r->in.attr;
461 1550 : o.in.access_mask = r->in.access_mask;
462 :
463 1550 : o.out.handle = r->out.handle;
464 :
465 1550 : return _lsa_OpenPolicy2(p, &o);
466 : }
467 :
468 : /***************************************************************************
469 : _lsa_EnumTrustDom - this needs fixing to do more than return NULL ! JRA.
470 : ufff, done :) mimir
471 : ***************************************************************************/
472 :
473 0 : NTSTATUS _lsa_EnumTrustDom(struct pipes_struct *p,
474 : struct lsa_EnumTrustDom *r)
475 : {
476 0 : struct lsa_info *info;
477 0 : uint32_t i, count;
478 0 : struct trustdom_info **domains;
479 0 : struct lsa_DomainInfo *entries;
480 0 : NTSTATUS nt_status;
481 :
482 0 : info = find_policy_by_hnd(p,
483 : r->in.handle,
484 : LSA_HANDLE_POLICY_TYPE,
485 : struct lsa_info,
486 0 : &nt_status);
487 0 : if (!NT_STATUS_IS_OK(nt_status)) {
488 0 : return NT_STATUS_INVALID_HANDLE;
489 : }
490 :
491 : /* check if the user has enough rights */
492 0 : if (!(info->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
493 0 : return NT_STATUS_ACCESS_DENIED;
494 :
495 0 : become_root();
496 0 : nt_status = pdb_enum_trusteddoms(p->mem_ctx, &count, &domains);
497 0 : unbecome_root();
498 :
499 0 : if (!NT_STATUS_IS_OK(nt_status)) {
500 0 : return nt_status;
501 : }
502 :
503 0 : entries = talloc_zero_array(p->mem_ctx, struct lsa_DomainInfo, count);
504 0 : if (!entries) {
505 0 : return NT_STATUS_NO_MEMORY;
506 : }
507 :
508 0 : for (i=0; i<count; i++) {
509 0 : init_lsa_StringLarge(&entries[i].name, domains[i]->name);
510 0 : entries[i].sid = &domains[i]->sid;
511 : }
512 :
513 0 : if (*r->in.resume_handle >= count) {
514 0 : *r->out.resume_handle = -1;
515 0 : TALLOC_FREE(entries);
516 0 : return NT_STATUS_NO_MORE_ENTRIES;
517 : }
518 :
519 : /* return the rest, limit by max_size. Note that we
520 : use the w2k3 element size value of 60 */
521 0 : r->out.domains->count = count - *r->in.resume_handle;
522 0 : r->out.domains->count = MIN(r->out.domains->count,
523 : 1+(r->in.max_size/LSA_ENUM_TRUST_DOMAIN_MULTIPLIER));
524 :
525 0 : r->out.domains->domains = entries + *r->in.resume_handle;
526 :
527 0 : if (r->out.domains->count < count - *r->in.resume_handle) {
528 0 : *r->out.resume_handle = *r->in.resume_handle + r->out.domains->count;
529 0 : return STATUS_MORE_ENTRIES;
530 : }
531 :
532 : /* according to MS-LSAD 3.1.4.7.8 output resume handle MUST
533 : * always be larger than the previous input resume handle, in
534 : * particular when hitting the last query it is vital to set the
535 : * resume handle correctly to avoid infinite client loops, as
536 : * seen e.g. with Windows XP SP3 when resume handle is 0 and
537 : * status is NT_STATUS_OK - gd */
538 :
539 0 : *r->out.resume_handle = (uint32_t)-1;
540 :
541 0 : return NT_STATUS_OK;
542 : }
543 :
544 : #define LSA_AUDIT_NUM_CATEGORIES_NT4 7
545 : #define LSA_AUDIT_NUM_CATEGORIES_WIN2K 9
546 : #define LSA_AUDIT_NUM_CATEGORIES LSA_AUDIT_NUM_CATEGORIES_NT4
547 :
548 : /***************************************************************************
549 : _lsa_QueryInfoPolicy
550 : ***************************************************************************/
551 :
552 860 : NTSTATUS _lsa_QueryInfoPolicy(struct pipes_struct *p,
553 : struct lsa_QueryInfoPolicy *r)
554 : {
555 860 : NTSTATUS status = NT_STATUS_OK;
556 0 : struct lsa_info *handle;
557 0 : struct dom_sid domain_sid;
558 0 : const char *name;
559 860 : struct dom_sid *sid = NULL;
560 860 : union lsa_PolicyInformation *info = NULL;
561 860 : uint32_t acc_required = 0;
562 :
563 860 : handle = find_policy_by_hnd(p,
564 : r->in.handle,
565 : LSA_HANDLE_POLICY_TYPE,
566 : struct lsa_info,
567 0 : &status);
568 860 : if (!NT_STATUS_IS_OK(status)) {
569 0 : return NT_STATUS_INVALID_HANDLE;
570 : }
571 :
572 860 : switch (r->in.level) {
573 4 : case LSA_POLICY_INFO_AUDIT_LOG:
574 : case LSA_POLICY_INFO_AUDIT_EVENTS:
575 4 : acc_required = LSA_POLICY_VIEW_AUDIT_INFORMATION;
576 4 : break;
577 60 : case LSA_POLICY_INFO_DOMAIN:
578 60 : acc_required = LSA_POLICY_VIEW_LOCAL_INFORMATION;
579 60 : break;
580 2 : case LSA_POLICY_INFO_PD:
581 2 : acc_required = LSA_POLICY_GET_PRIVATE_INFORMATION;
582 2 : break;
583 774 : case LSA_POLICY_INFO_ACCOUNT_DOMAIN:
584 774 : acc_required = LSA_POLICY_VIEW_LOCAL_INFORMATION;
585 774 : break;
586 4 : case LSA_POLICY_INFO_ROLE:
587 : case LSA_POLICY_INFO_REPLICA:
588 4 : acc_required = LSA_POLICY_VIEW_LOCAL_INFORMATION;
589 4 : break;
590 2 : case LSA_POLICY_INFO_QUOTA:
591 2 : acc_required = LSA_POLICY_VIEW_LOCAL_INFORMATION;
592 2 : break;
593 4 : case LSA_POLICY_INFO_MOD:
594 : case LSA_POLICY_INFO_AUDIT_FULL_SET:
595 : /* according to MS-LSAD 3.1.4.4.3 */
596 4 : return NT_STATUS_INVALID_PARAMETER;
597 2 : case LSA_POLICY_INFO_AUDIT_FULL_QUERY:
598 2 : acc_required = LSA_POLICY_VIEW_AUDIT_INFORMATION;
599 2 : break;
600 8 : case LSA_POLICY_INFO_DNS:
601 : case LSA_POLICY_INFO_DNS_INT:
602 : case LSA_POLICY_INFO_L_ACCOUNT_DOMAIN:
603 8 : acc_required = LSA_POLICY_VIEW_LOCAL_INFORMATION;
604 8 : break;
605 0 : default:
606 0 : break;
607 : }
608 :
609 856 : if (!(handle->access & acc_required)) {
610 : /* return NT_STATUS_ACCESS_DENIED; */
611 0 : }
612 :
613 856 : info = talloc_zero(p->mem_ctx, union lsa_PolicyInformation);
614 856 : if (!info) {
615 0 : return NT_STATUS_NO_MEMORY;
616 : }
617 :
618 856 : switch (r->in.level) {
619 : /* according to MS-LSAD 3.1.4.4.3 */
620 2 : case LSA_POLICY_INFO_MOD:
621 : case LSA_POLICY_INFO_AUDIT_FULL_SET:
622 : case LSA_POLICY_INFO_AUDIT_FULL_QUERY:
623 2 : return NT_STATUS_INVALID_PARAMETER;
624 2 : case LSA_POLICY_INFO_AUDIT_LOG:
625 2 : info->audit_log.percent_full = 0;
626 2 : info->audit_log.maximum_log_size = 0;
627 2 : info->audit_log.retention_time = 0;
628 2 : info->audit_log.shutdown_in_progress = 0;
629 2 : info->audit_log.time_to_shutdown = 0;
630 2 : info->audit_log.next_audit_record = 0;
631 2 : status = NT_STATUS_OK;
632 2 : break;
633 2 : case LSA_POLICY_INFO_PD:
634 2 : info->pd.name.string = NULL;
635 2 : status = NT_STATUS_OK;
636 2 : break;
637 2 : case LSA_POLICY_INFO_REPLICA:
638 2 : info->replica.source.string = NULL;
639 2 : info->replica.account.string = NULL;
640 2 : status = NT_STATUS_OK;
641 2 : break;
642 2 : case LSA_POLICY_INFO_QUOTA:
643 2 : info->quota.paged_pool = 0;
644 2 : info->quota.non_paged_pool = 0;
645 2 : info->quota.min_wss = 0;
646 2 : info->quota.max_wss = 0;
647 2 : info->quota.pagefile = 0;
648 2 : info->quota.unknown = 0;
649 2 : status = NT_STATUS_OK;
650 2 : break;
651 2 : case LSA_POLICY_INFO_AUDIT_EVENTS:
652 : {
653 :
654 2 : uint32_t policy_def = LSA_AUDIT_POLICY_ALL;
655 :
656 : /* check if the user has enough rights */
657 2 : if (!(handle->access & LSA_POLICY_VIEW_AUDIT_INFORMATION)) {
658 0 : DEBUG(10,("_lsa_QueryInfoPolicy: insufficient access rights\n"));
659 0 : return NT_STATUS_ACCESS_DENIED;
660 : }
661 :
662 : /* fake info: We audit everything. ;) */
663 :
664 2 : info->audit_events.auditing_mode = true;
665 2 : info->audit_events.count = LSA_AUDIT_NUM_CATEGORIES;
666 2 : info->audit_events.settings = talloc_zero_array(p->mem_ctx,
667 : enum lsa_PolicyAuditPolicy,
668 : info->audit_events.count);
669 2 : if (!info->audit_events.settings) {
670 0 : return NT_STATUS_NO_MEMORY;
671 : }
672 :
673 2 : info->audit_events.settings[LSA_AUDIT_CATEGORY_ACCOUNT_MANAGEMENT] = policy_def;
674 2 : info->audit_events.settings[LSA_AUDIT_CATEGORY_FILE_AND_OBJECT_ACCESS] = policy_def;
675 2 : info->audit_events.settings[LSA_AUDIT_CATEGORY_LOGON] = policy_def;
676 2 : info->audit_events.settings[LSA_AUDIT_CATEGORY_PROCCESS_TRACKING] = policy_def;
677 2 : info->audit_events.settings[LSA_AUDIT_CATEGORY_SECURITY_POLICY_CHANGES] = policy_def;
678 2 : info->audit_events.settings[LSA_AUDIT_CATEGORY_SYSTEM] = policy_def;
679 2 : info->audit_events.settings[LSA_AUDIT_CATEGORY_USE_OF_USER_RIGHTS] = policy_def;
680 :
681 2 : break;
682 : }
683 60 : case LSA_POLICY_INFO_DOMAIN:
684 : /* check if the user has enough rights */
685 60 : if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
686 0 : return NT_STATUS_ACCESS_DENIED;
687 :
688 : /* Request PolicyPrimaryDomainInformation. */
689 60 : switch (lp_server_role()) {
690 60 : case ROLE_DOMAIN_PDC:
691 : case ROLE_DOMAIN_BDC:
692 : case ROLE_IPA_DC:
693 60 : name = get_global_sam_name();
694 60 : sid = dom_sid_dup(p->mem_ctx, get_global_sam_sid());
695 60 : if (!sid) {
696 0 : return NT_STATUS_NO_MEMORY;
697 : }
698 60 : break;
699 0 : case ROLE_DOMAIN_MEMBER:
700 0 : name = lp_workgroup();
701 : /* We need to return the Domain SID here. */
702 0 : if (secrets_fetch_domain_sid(lp_workgroup(), &domain_sid)) {
703 0 : sid = dom_sid_dup(p->mem_ctx, &domain_sid);
704 0 : if (!sid) {
705 0 : return NT_STATUS_NO_MEMORY;
706 : }
707 : } else {
708 0 : return NT_STATUS_CANT_ACCESS_DOMAIN_INFO;
709 : }
710 0 : break;
711 0 : case ROLE_STANDALONE:
712 0 : name = lp_workgroup();
713 0 : sid = NULL;
714 0 : break;
715 0 : default:
716 0 : return NT_STATUS_CANT_ACCESS_DOMAIN_INFO;
717 : }
718 60 : init_dom_query_3(&info->domain, name, sid);
719 60 : break;
720 774 : case LSA_POLICY_INFO_ACCOUNT_DOMAIN:
721 : /* check if the user has enough rights */
722 774 : if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
723 0 : return NT_STATUS_ACCESS_DENIED;
724 :
725 : /* Request PolicyAccountDomainInformation. */
726 774 : name = get_global_sam_name();
727 774 : sid = get_global_sam_sid();
728 :
729 774 : init_dom_query_5(&info->account_domain, name, sid);
730 774 : break;
731 2 : case LSA_POLICY_INFO_ROLE:
732 : /* check if the user has enough rights */
733 2 : if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
734 0 : return NT_STATUS_ACCESS_DENIED;
735 :
736 2 : switch (lp_server_role()) {
737 0 : case ROLE_DOMAIN_BDC:
738 : /*
739 : * only a BDC is a backup controller
740 : * of the domain, it controls.
741 : */
742 0 : info->role.role = LSA_ROLE_BACKUP;
743 0 : break;
744 2 : default:
745 : /*
746 : * any other role is a primary
747 : * of the domain, it controls.
748 : */
749 2 : info->role.role = LSA_ROLE_PRIMARY;
750 2 : break;
751 : }
752 2 : break;
753 6 : case LSA_POLICY_INFO_DNS:
754 : case LSA_POLICY_INFO_DNS_INT: {
755 0 : struct pdb_domain_info *dominfo;
756 :
757 6 : if ((pdb_capabilities() & PDB_CAP_ADS) == 0) {
758 4 : DEBUG(10, ("Not replying to LSA_POLICY_INFO_DNS "
759 : "without ADS passdb backend\n"));
760 4 : status = NT_STATUS_INVALID_INFO_CLASS;
761 4 : break;
762 : }
763 :
764 2 : dominfo = pdb_get_domain_info(info);
765 2 : if (dominfo == NULL) {
766 0 : status = NT_STATUS_NO_MEMORY;
767 0 : break;
768 : }
769 :
770 2 : init_lsa_StringLarge(&info->dns.name,
771 2 : dominfo->name);
772 2 : init_lsa_StringLarge(&info->dns.dns_domain,
773 2 : dominfo->dns_domain);
774 2 : init_lsa_StringLarge(&info->dns.dns_forest,
775 2 : dominfo->dns_forest);
776 2 : info->dns.domain_guid = dominfo->guid;
777 2 : info->dns.sid = &dominfo->sid;
778 2 : break;
779 : }
780 2 : default:
781 2 : DEBUG(0,("_lsa_QueryInfoPolicy: unknown info level in Lsa Query: %d\n",
782 : r->in.level));
783 2 : status = NT_STATUS_INVALID_INFO_CLASS;
784 2 : break;
785 : }
786 :
787 854 : *r->out.info = info;
788 :
789 854 : return status;
790 : }
791 :
792 : /***************************************************************************
793 : _lsa_QueryInfoPolicy2
794 : ***************************************************************************/
795 :
796 158 : NTSTATUS _lsa_QueryInfoPolicy2(struct pipes_struct *p,
797 : struct lsa_QueryInfoPolicy2 *r2)
798 : {
799 0 : struct lsa_QueryInfoPolicy r;
800 :
801 158 : if ((pdb_capabilities() & PDB_CAP_ADS) == 0) {
802 156 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
803 156 : return NT_STATUS_NOT_IMPLEMENTED;
804 : }
805 :
806 2 : ZERO_STRUCT(r);
807 2 : r.in.handle = r2->in.handle;
808 2 : r.in.level = r2->in.level;
809 2 : r.out.info = r2->out.info;
810 :
811 2 : return _lsa_QueryInfoPolicy(p, &r);
812 : }
813 :
814 : /***************************************************************************
815 : _lsa_lookup_sids_internal
816 : ***************************************************************************/
817 :
818 3140 : static NTSTATUS _lsa_lookup_sids_internal(struct pipes_struct *p,
819 : TALLOC_CTX *mem_ctx,
820 : uint16_t level, /* input */
821 : int num_sids, /* input */
822 : struct lsa_SidPtr *sid, /* input */
823 : struct lsa_RefDomainList **pp_ref, /* input/output */
824 : struct lsa_TranslatedName2 **pp_names,/* input/output */
825 : uint32_t *pp_mapped_count) /* input/output */
826 : {
827 0 : NTSTATUS status;
828 0 : int i;
829 3140 : const struct dom_sid **sids = NULL;
830 3140 : struct lsa_RefDomainList *ref = NULL;
831 3140 : uint32_t mapped_count = 0;
832 3140 : struct lsa_dom_info *dom_infos = NULL;
833 3140 : struct lsa_name_info *name_infos = NULL;
834 3140 : struct lsa_TranslatedName2 *names = NULL;
835 :
836 3140 : *pp_mapped_count = 0;
837 3140 : *pp_names = NULL;
838 3140 : *pp_ref = NULL;
839 :
840 3140 : if (num_sids == 0) {
841 0 : return NT_STATUS_OK;
842 : }
843 :
844 3140 : sids = talloc_array(p->mem_ctx, const struct dom_sid *, num_sids);
845 3140 : ref = talloc_zero(p->mem_ctx, struct lsa_RefDomainList);
846 :
847 3140 : if (sids == NULL || ref == NULL) {
848 0 : return NT_STATUS_NO_MEMORY;
849 : }
850 :
851 8884 : for (i=0; i<num_sids; i++) {
852 5744 : sids[i] = sid[i].sid;
853 : }
854 :
855 3140 : status = lookup_sids(p->mem_ctx, num_sids, sids, level,
856 : &dom_infos, &name_infos);
857 :
858 3140 : if (!NT_STATUS_IS_OK(status)) {
859 0 : return status;
860 : }
861 :
862 3140 : names = talloc_array(p->mem_ctx, struct lsa_TranslatedName2, num_sids);
863 3140 : if (names == NULL) {
864 0 : return NT_STATUS_NO_MEMORY;
865 : }
866 :
867 6284 : for (i=0; i<LSA_REF_DOMAIN_LIST_MULTIPLIER; i++) {
868 :
869 6284 : if (!dom_infos[i].valid) {
870 3140 : break;
871 : }
872 :
873 3144 : if (init_lsa_ref_domain_list(mem_ctx, ref,
874 3144 : dom_infos[i].name,
875 3144 : &dom_infos[i].sid) != i) {
876 0 : DEBUG(0, ("Domain %s mentioned twice??\n",
877 : dom_infos[i].name));
878 0 : return NT_STATUS_INTERNAL_ERROR;
879 : }
880 : }
881 :
882 8884 : for (i=0; i<num_sids; i++) {
883 5744 : struct lsa_name_info *name = &name_infos[i];
884 :
885 5744 : if (name->type == SID_NAME_UNKNOWN) {
886 164 : name->dom_idx = -1;
887 : /* Unknown sids should return the string
888 : * representation of the SID. Windows 2003 behaves
889 : * rather erratic here, in many cases it returns the
890 : * RID as 8 bytes hex, in others it returns the full
891 : * SID. We (Jerry/VL) could not figure out which the
892 : * hard cases are, so leave it with the SID. */
893 164 : name->name = dom_sid_string(p->mem_ctx, sids[i]);
894 164 : if (name->name == NULL) {
895 0 : return NT_STATUS_NO_MEMORY;
896 : }
897 : } else {
898 5580 : mapped_count += 1;
899 : }
900 :
901 5744 : names[i].sid_type = name->type;
902 5744 : names[i].name.string = name->name;
903 5744 : names[i].sid_index = name->dom_idx;
904 5744 : names[i].unknown = 0;
905 : }
906 :
907 3140 : status = NT_STATUS_NONE_MAPPED;
908 3140 : if (mapped_count > 0) {
909 2986 : status = (mapped_count < num_sids) ?
910 0 : STATUS_SOME_UNMAPPED : NT_STATUS_OK;
911 : }
912 :
913 3140 : DEBUG(10, ("num_sids %d, mapped_count %d, status %s\n",
914 : num_sids, mapped_count, nt_errstr(status)));
915 :
916 3140 : *pp_mapped_count = mapped_count;
917 3140 : *pp_names = names;
918 3140 : *pp_ref = ref;
919 :
920 3140 : return status;
921 : }
922 :
923 : /***************************************************************************
924 : _lsa_LookupSids
925 : ***************************************************************************/
926 :
927 3114 : NTSTATUS _lsa_LookupSids(struct pipes_struct *p,
928 : struct lsa_LookupSids *r)
929 : {
930 0 : NTSTATUS status;
931 0 : struct lsa_info *handle;
932 3114 : int num_sids = r->in.sids->num_sids;
933 3114 : uint32_t mapped_count = 0;
934 3114 : struct lsa_RefDomainList *domains = NULL;
935 3114 : struct lsa_TranslatedName *names_out = NULL;
936 3114 : struct lsa_TranslatedName2 *names = NULL;
937 0 : int i;
938 :
939 3114 : if (p->transport != NCACN_NP && p->transport != NCALRPC) {
940 0 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
941 0 : return NT_STATUS_ACCESS_DENIED;
942 : }
943 :
944 3114 : if ((r->in.level < 1) || (r->in.level > 6)) {
945 0 : return NT_STATUS_INVALID_PARAMETER;
946 : }
947 :
948 3114 : handle = find_policy_by_hnd(p,
949 : r->in.handle,
950 : LSA_HANDLE_POLICY_TYPE,
951 : struct lsa_info,
952 0 : &status);
953 3114 : if (!NT_STATUS_IS_OK(status)) {
954 0 : return NT_STATUS_INVALID_HANDLE;
955 : }
956 :
957 : /* check if the user has enough rights */
958 3114 : if (!(handle->access & LSA_POLICY_LOOKUP_NAMES)) {
959 0 : return NT_STATUS_ACCESS_DENIED;
960 : }
961 :
962 3114 : if (num_sids > MAX_LOOKUP_SIDS) {
963 0 : DEBUG(5,("_lsa_LookupSids: limit of %d exceeded, requested %d\n",
964 : MAX_LOOKUP_SIDS, num_sids));
965 0 : return NT_STATUS_NONE_MAPPED;
966 : }
967 :
968 3114 : status = _lsa_lookup_sids_internal(p,
969 : p->mem_ctx,
970 3114 : r->in.level,
971 : num_sids,
972 3114 : r->in.sids->sids,
973 : &domains,
974 : &names,
975 : &mapped_count);
976 :
977 : /* Only return here when there is a real error.
978 : NT_STATUS_NONE_MAPPED is a special case as it indicates that none of
979 : the requested sids could be resolved. Older versions of XP (pre SP3)
980 : rely that we return with the string representations of those SIDs in
981 : that case. If we don't, XP crashes - Guenther
982 : */
983 :
984 3114 : if (NT_STATUS_IS_ERR(status) &&
985 154 : !NT_STATUS_EQUAL(status, NT_STATUS_NONE_MAPPED)) {
986 0 : return status;
987 : }
988 :
989 : /* Convert from lsa_TranslatedName2 to lsa_TranslatedName */
990 3114 : names_out = talloc_array(p->mem_ctx, struct lsa_TranslatedName,
991 : num_sids);
992 3114 : if (!names_out) {
993 0 : return NT_STATUS_NO_MEMORY;
994 : }
995 :
996 6446 : for (i=0; i<num_sids; i++) {
997 3332 : names_out[i].sid_type = names[i].sid_type;
998 3332 : names_out[i].name = names[i].name;
999 3332 : names_out[i].sid_index = names[i].sid_index;
1000 : }
1001 :
1002 3114 : *r->out.domains = domains;
1003 3114 : r->out.names->count = num_sids;
1004 3114 : r->out.names->names = names_out;
1005 3114 : *r->out.count = mapped_count;
1006 :
1007 3114 : return status;
1008 : }
1009 :
1010 26 : static NTSTATUS _lsa_LookupSids_common(struct pipes_struct *p,
1011 : struct lsa_LookupSids2 *r)
1012 : {
1013 26 : struct dcesrv_call_state *dce_call = p->dce_call;
1014 0 : NTSTATUS status;
1015 0 : struct lsa_info *handle;
1016 26 : int num_sids = r->in.sids->num_sids;
1017 26 : uint32_t mapped_count = 0;
1018 26 : struct lsa_RefDomainList *domains = NULL;
1019 26 : struct lsa_TranslatedName2 *names = NULL;
1020 26 : bool check_policy = true;
1021 :
1022 26 : switch (dce_call->pkt.u.request.opnum) {
1023 24 : case NDR_LSA_LOOKUPSIDS3:
1024 24 : check_policy = false;
1025 24 : break;
1026 2 : case NDR_LSA_LOOKUPSIDS2:
1027 : default:
1028 2 : check_policy = true;
1029 : }
1030 :
1031 26 : if ((r->in.level < 1) || (r->in.level > 6)) {
1032 0 : return NT_STATUS_INVALID_PARAMETER;
1033 : }
1034 :
1035 26 : if (check_policy) {
1036 2 : handle = find_policy_by_hnd(p,
1037 : r->in.handle,
1038 : LSA_HANDLE_POLICY_TYPE,
1039 : struct lsa_info,
1040 0 : &status);
1041 2 : if (!NT_STATUS_IS_OK(status)) {
1042 0 : return NT_STATUS_INVALID_HANDLE;
1043 : }
1044 :
1045 : /* check if the user has enough rights */
1046 2 : if (!(handle->access & LSA_POLICY_LOOKUP_NAMES)) {
1047 0 : return NT_STATUS_ACCESS_DENIED;
1048 : }
1049 : }
1050 :
1051 26 : if (num_sids > MAX_LOOKUP_SIDS) {
1052 0 : DEBUG(5,("_lsa_LookupSids2: limit of %d exceeded, requested %d\n",
1053 : MAX_LOOKUP_SIDS, num_sids));
1054 0 : return NT_STATUS_NONE_MAPPED;
1055 : }
1056 :
1057 26 : status = _lsa_lookup_sids_internal(p,
1058 : p->mem_ctx,
1059 26 : r->in.level,
1060 : num_sids,
1061 26 : r->in.sids->sids,
1062 : &domains,
1063 : &names,
1064 : &mapped_count);
1065 :
1066 26 : *r->out.domains = domains;
1067 26 : r->out.names->count = num_sids;
1068 26 : r->out.names->names = names;
1069 26 : *r->out.count = mapped_count;
1070 :
1071 26 : return status;
1072 : }
1073 :
1074 : /***************************************************************************
1075 : _lsa_LookupSids2
1076 : ***************************************************************************/
1077 :
1078 2 : NTSTATUS _lsa_LookupSids2(struct pipes_struct *p,
1079 : struct lsa_LookupSids2 *r)
1080 : {
1081 2 : if (p->transport != NCACN_NP && p->transport != NCALRPC) {
1082 0 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
1083 0 : return NT_STATUS_ACCESS_DENIED;
1084 : }
1085 :
1086 2 : return _lsa_LookupSids_common(p, r);
1087 : }
1088 :
1089 : /***************************************************************************
1090 : _lsa_LookupSids3
1091 : ***************************************************************************/
1092 :
1093 28 : NTSTATUS _lsa_LookupSids3(struct pipes_struct *p,
1094 : struct lsa_LookupSids3 *r)
1095 : {
1096 28 : struct dcesrv_call_state *dce_call = p->dce_call;
1097 28 : enum dcerpc_AuthType auth_type = DCERPC_AUTH_TYPE_NONE;
1098 28 : enum dcerpc_AuthLevel auth_level = DCERPC_AUTH_LEVEL_NONE;
1099 0 : struct lsa_LookupSids2 q;
1100 :
1101 28 : if (p->transport != NCACN_IP_TCP) {
1102 2 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
1103 2 : return NT_STATUS_ACCESS_DENIED;
1104 : }
1105 :
1106 26 : dcesrv_call_auth_info(dce_call, &auth_type, &auth_level);
1107 :
1108 : /* No policy handle on this call. Restrict to crypto connections. */
1109 26 : if (auth_type != DCERPC_AUTH_TYPE_SCHANNEL ||
1110 24 : auth_level < DCERPC_AUTH_LEVEL_INTEGRITY) {
1111 2 : DEBUG(1, ("_lsa_LookupSids3: The client %s is not using "
1112 : "a secure connection over netlogon\n",
1113 : get_remote_machine_name() ));
1114 2 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
1115 2 : return NT_STATUS_ACCESS_DENIED;
1116 : }
1117 :
1118 24 : q.in.handle = NULL;
1119 24 : q.in.sids = r->in.sids;
1120 24 : q.in.level = r->in.level;
1121 24 : q.in.lookup_options = r->in.lookup_options;
1122 24 : q.in.client_revision = r->in.client_revision;
1123 24 : q.in.names = r->in.names;
1124 24 : q.in.count = r->in.count;
1125 :
1126 24 : q.out.domains = r->out.domains;
1127 24 : q.out.names = r->out.names;
1128 24 : q.out.count = r->out.count;
1129 :
1130 24 : return _lsa_LookupSids_common(p, &q);
1131 : }
1132 :
1133 : /***************************************************************************
1134 : ***************************************************************************/
1135 :
1136 374 : static int lsa_lookup_level_to_flags(enum lsa_LookupNamesLevel level)
1137 : {
1138 0 : int flags;
1139 :
1140 374 : switch (level) {
1141 358 : case LSA_LOOKUP_NAMES_ALL: /* 1 */
1142 358 : flags = LOOKUP_NAME_ALL;
1143 358 : break;
1144 16 : case LSA_LOOKUP_NAMES_DOMAINS_ONLY: /* 2 */
1145 16 : flags = LOOKUP_NAME_DOMAIN|LOOKUP_NAME_REMOTE|LOOKUP_NAME_ISOLATED;
1146 16 : break;
1147 0 : case LSA_LOOKUP_NAMES_PRIMARY_DOMAIN_ONLY: /* 3 */
1148 0 : flags = LOOKUP_NAME_DOMAIN|LOOKUP_NAME_ISOLATED;
1149 0 : break;
1150 0 : case LSA_LOOKUP_NAMES_UPLEVEL_TRUSTS_ONLY: /* 4 */
1151 : case LSA_LOOKUP_NAMES_FOREST_TRUSTS_ONLY: /* 5 */
1152 : case LSA_LOOKUP_NAMES_UPLEVEL_TRUSTS_ONLY2: /* 6 */
1153 : case LSA_LOOKUP_NAMES_RODC_REFERRAL_TO_FULL_DC: /* 7 */
1154 : default:
1155 0 : flags = LOOKUP_NAME_NONE;
1156 0 : break;
1157 : }
1158 :
1159 374 : return flags;
1160 : }
1161 :
1162 : /***************************************************************************
1163 : _lsa_LookupNames
1164 : ***************************************************************************/
1165 :
1166 322 : NTSTATUS _lsa_LookupNames(struct pipes_struct *p,
1167 : struct lsa_LookupNames *r)
1168 : {
1169 322 : NTSTATUS status = NT_STATUS_NONE_MAPPED;
1170 0 : struct lsa_info *handle;
1171 322 : struct lsa_String *names = r->in.names;
1172 322 : uint32_t num_entries = r->in.num_names;
1173 322 : struct lsa_RefDomainList *domains = NULL;
1174 322 : struct lsa_TranslatedSid *rids = NULL;
1175 322 : uint32_t mapped_count = 0;
1176 322 : int flags = 0;
1177 :
1178 322 : if (p->transport != NCACN_NP && p->transport != NCALRPC) {
1179 0 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
1180 0 : return NT_STATUS_ACCESS_DENIED;
1181 : }
1182 :
1183 322 : if (num_entries > MAX_LOOKUP_SIDS) {
1184 0 : num_entries = MAX_LOOKUP_SIDS;
1185 0 : DEBUG(5,("_lsa_LookupNames: truncating name lookup list to %d\n",
1186 : num_entries));
1187 : }
1188 :
1189 322 : flags = lsa_lookup_level_to_flags(r->in.level);
1190 :
1191 322 : domains = talloc_zero(p->mem_ctx, struct lsa_RefDomainList);
1192 322 : if (!domains) {
1193 0 : return NT_STATUS_NO_MEMORY;
1194 : }
1195 :
1196 322 : if (num_entries) {
1197 322 : rids = talloc_zero_array(p->mem_ctx, struct lsa_TranslatedSid,
1198 : num_entries);
1199 322 : if (!rids) {
1200 0 : return NT_STATUS_NO_MEMORY;
1201 : }
1202 : } else {
1203 0 : rids = NULL;
1204 : }
1205 :
1206 322 : handle = find_policy_by_hnd(p,
1207 : r->in.handle,
1208 : LSA_HANDLE_POLICY_TYPE,
1209 : struct lsa_info,
1210 0 : &status);
1211 322 : if (!NT_STATUS_IS_OK(status)) {
1212 0 : status = NT_STATUS_INVALID_HANDLE;
1213 0 : goto done;
1214 : }
1215 :
1216 : /* check if the user has enough rights */
1217 322 : if (!(handle->access & LSA_POLICY_LOOKUP_NAMES)) {
1218 0 : status = NT_STATUS_ACCESS_DENIED;
1219 0 : goto done;
1220 : }
1221 :
1222 : /* set up the LSA Lookup RIDs response */
1223 322 : become_root(); /* lookup_name can require root privs */
1224 322 : status = lookup_lsa_rids(p->mem_ctx, domains, rids, num_entries,
1225 : names, flags, &mapped_count);
1226 322 : unbecome_root();
1227 :
1228 322 : done:
1229 :
1230 322 : if (NT_STATUS_IS_OK(status) && (num_entries != 0) ) {
1231 322 : if (mapped_count == 0) {
1232 18 : status = NT_STATUS_NONE_MAPPED;
1233 304 : } else if (mapped_count != num_entries) {
1234 0 : status = STATUS_SOME_UNMAPPED;
1235 : }
1236 : }
1237 :
1238 322 : *r->out.count = mapped_count;
1239 322 : *r->out.domains = domains;
1240 322 : r->out.sids->sids = rids;
1241 322 : r->out.sids->count = num_entries;
1242 :
1243 322 : return status;
1244 : }
1245 :
1246 : /***************************************************************************
1247 : _lsa_LookupNames2
1248 : ***************************************************************************/
1249 :
1250 4 : NTSTATUS _lsa_LookupNames2(struct pipes_struct *p,
1251 : struct lsa_LookupNames2 *r)
1252 : {
1253 0 : NTSTATUS status;
1254 0 : struct lsa_LookupNames q;
1255 4 : struct lsa_TransSidArray2 *sid_array2 = r->in.sids;
1256 4 : struct lsa_TransSidArray *sid_array = NULL;
1257 0 : uint32_t i;
1258 :
1259 4 : if (p->transport != NCACN_NP && p->transport != NCALRPC) {
1260 0 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
1261 0 : return NT_STATUS_ACCESS_DENIED;
1262 : }
1263 :
1264 4 : sid_array = talloc_zero(p->mem_ctx, struct lsa_TransSidArray);
1265 4 : if (!sid_array) {
1266 0 : return NT_STATUS_NO_MEMORY;
1267 : }
1268 :
1269 4 : q.in.handle = r->in.handle;
1270 4 : q.in.num_names = r->in.num_names;
1271 4 : q.in.names = r->in.names;
1272 4 : q.in.level = r->in.level;
1273 4 : q.in.sids = sid_array;
1274 4 : q.in.count = r->in.count;
1275 : /* we do not know what this is for */
1276 : /* = r->in.unknown1; */
1277 : /* = r->in.unknown2; */
1278 :
1279 4 : q.out.domains = r->out.domains;
1280 4 : q.out.sids = sid_array;
1281 4 : q.out.count = r->out.count;
1282 :
1283 4 : status = _lsa_LookupNames(p, &q);
1284 :
1285 4 : sid_array2->count = sid_array->count;
1286 4 : sid_array2->sids = talloc_array(p->mem_ctx, struct lsa_TranslatedSid2, sid_array->count);
1287 4 : if (!sid_array2->sids) {
1288 0 : return NT_STATUS_NO_MEMORY;
1289 : }
1290 :
1291 18 : for (i=0; i<sid_array->count; i++) {
1292 14 : sid_array2->sids[i].sid_type = sid_array->sids[i].sid_type;
1293 14 : sid_array2->sids[i].rid = sid_array->sids[i].rid;
1294 14 : sid_array2->sids[i].sid_index = sid_array->sids[i].sid_index;
1295 14 : sid_array2->sids[i].unknown = 0;
1296 : }
1297 :
1298 4 : r->out.sids = sid_array2;
1299 :
1300 4 : return status;
1301 : }
1302 :
1303 52 : static NTSTATUS _lsa_LookupNames_common(struct pipes_struct *p,
1304 : struct lsa_LookupNames3 *r)
1305 : {
1306 52 : struct dcesrv_call_state *dce_call = p->dce_call;
1307 0 : NTSTATUS status;
1308 0 : struct lsa_info *handle;
1309 52 : struct lsa_String *names = r->in.names;
1310 52 : uint32_t num_entries = r->in.num_names;
1311 52 : struct lsa_RefDomainList *domains = NULL;
1312 52 : struct lsa_TranslatedSid3 *trans_sids = NULL;
1313 52 : uint32_t mapped_count = 0;
1314 52 : int flags = 0;
1315 52 : bool check_policy = true;
1316 :
1317 52 : switch (dce_call->pkt.u.request.opnum) {
1318 48 : case NDR_LSA_LOOKUPNAMES4:
1319 48 : check_policy = false;
1320 48 : break;
1321 4 : case NDR_LSA_LOOKUPNAMES3:
1322 : default:
1323 4 : check_policy = true;
1324 : }
1325 :
1326 52 : if (num_entries > MAX_LOOKUP_SIDS) {
1327 0 : num_entries = MAX_LOOKUP_SIDS;
1328 0 : DEBUG(5,("_lsa_LookupNames3: truncating name lookup list to %d\n", num_entries));
1329 : }
1330 :
1331 52 : flags = lsa_lookup_level_to_flags(r->in.level);
1332 :
1333 52 : domains = talloc_zero(p->mem_ctx, struct lsa_RefDomainList);
1334 52 : if (!domains) {
1335 0 : return NT_STATUS_NO_MEMORY;
1336 : }
1337 :
1338 52 : if (num_entries) {
1339 28 : trans_sids = talloc_zero_array(p->mem_ctx, struct lsa_TranslatedSid3,
1340 : num_entries);
1341 28 : if (!trans_sids) {
1342 0 : return NT_STATUS_NO_MEMORY;
1343 : }
1344 : } else {
1345 24 : trans_sids = NULL;
1346 : }
1347 :
1348 52 : if (check_policy) {
1349 :
1350 4 : handle = find_policy_by_hnd(p,
1351 : r->in.handle,
1352 : LSA_HANDLE_POLICY_TYPE,
1353 : struct lsa_info,
1354 0 : &status);
1355 4 : if (!NT_STATUS_IS_OK(status)) {
1356 0 : status = NT_STATUS_INVALID_HANDLE;
1357 0 : goto done;
1358 : }
1359 :
1360 : /* check if the user has enough rights */
1361 4 : if (!(handle->access & LSA_POLICY_LOOKUP_NAMES)) {
1362 0 : status = NT_STATUS_ACCESS_DENIED;
1363 0 : goto done;
1364 : }
1365 : }
1366 :
1367 : /* set up the LSA Lookup SIDs response */
1368 52 : become_root(); /* lookup_name can require root privs */
1369 52 : status = lookup_lsa_sids(p->mem_ctx, domains, trans_sids, num_entries,
1370 : names, flags, &mapped_count);
1371 52 : unbecome_root();
1372 :
1373 52 : done:
1374 :
1375 52 : if (NT_STATUS_IS_OK(status)) {
1376 52 : if (mapped_count == 0) {
1377 24 : status = NT_STATUS_NONE_MAPPED;
1378 28 : } else if (mapped_count != num_entries) {
1379 0 : status = STATUS_SOME_UNMAPPED;
1380 : }
1381 : }
1382 :
1383 52 : *r->out.count = mapped_count;
1384 52 : *r->out.domains = domains;
1385 52 : r->out.sids->sids = trans_sids;
1386 52 : r->out.sids->count = num_entries;
1387 :
1388 52 : return status;
1389 : }
1390 :
1391 : /***************************************************************************
1392 : _lsa_LookupNames3
1393 : ***************************************************************************/
1394 :
1395 4 : NTSTATUS _lsa_LookupNames3(struct pipes_struct *p,
1396 : struct lsa_LookupNames3 *r)
1397 : {
1398 4 : if (p->transport != NCACN_NP && p->transport != NCALRPC) {
1399 0 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
1400 0 : return NT_STATUS_ACCESS_DENIED;
1401 : }
1402 :
1403 4 : return _lsa_LookupNames_common(p, r);
1404 : }
1405 :
1406 : /***************************************************************************
1407 : _lsa_LookupNames4
1408 : ***************************************************************************/
1409 :
1410 52 : NTSTATUS _lsa_LookupNames4(struct pipes_struct *p,
1411 : struct lsa_LookupNames4 *r)
1412 : {
1413 52 : struct dcesrv_call_state *dce_call = p->dce_call;
1414 52 : enum dcerpc_AuthType auth_type = DCERPC_AUTH_TYPE_NONE;
1415 52 : enum dcerpc_AuthLevel auth_level = DCERPC_AUTH_LEVEL_NONE;
1416 0 : struct lsa_LookupNames3 q;
1417 :
1418 52 : if (p->transport != NCACN_IP_TCP) {
1419 2 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
1420 2 : return NT_STATUS_ACCESS_DENIED;
1421 : }
1422 :
1423 50 : dcesrv_call_auth_info(dce_call, &auth_type, &auth_level);
1424 :
1425 : /* No policy handle on this call. Restrict to crypto connections. */
1426 50 : if (auth_type != DCERPC_AUTH_TYPE_SCHANNEL ||
1427 48 : auth_level < DCERPC_AUTH_LEVEL_INTEGRITY) {
1428 2 : DEBUG(1, ("_lsa_LookupNames4: The client %s is not using "
1429 : "a secure connection over netlogon\n",
1430 : get_remote_machine_name()));
1431 2 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
1432 2 : return NT_STATUS_ACCESS_DENIED;
1433 : }
1434 :
1435 48 : q.in.handle = NULL;
1436 48 : q.in.num_names = r->in.num_names;
1437 48 : q.in.names = r->in.names;
1438 48 : q.in.level = r->in.level;
1439 48 : q.in.lookup_options = r->in.lookup_options;
1440 48 : q.in.client_revision = r->in.client_revision;
1441 48 : q.in.sids = r->in.sids;
1442 48 : q.in.count = r->in.count;
1443 :
1444 48 : q.out.domains = r->out.domains;
1445 48 : q.out.sids = r->out.sids;
1446 48 : q.out.count = r->out.count;
1447 :
1448 48 : return _lsa_LookupNames_common(p, &q);
1449 : }
1450 :
1451 : /***************************************************************************
1452 : _lsa_close. Also weird - needs to check if lsa handle is correct. JRA.
1453 : ***************************************************************************/
1454 :
1455 978 : NTSTATUS _lsa_Close(struct pipes_struct *p, struct lsa_Close *r)
1456 : {
1457 0 : NTSTATUS status;
1458 :
1459 978 : if (p->transport != NCACN_NP && p->transport != NCALRPC) {
1460 0 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
1461 0 : return NT_STATUS_ACCESS_DENIED;
1462 : }
1463 :
1464 978 : (void)find_policy_by_hnd(p,
1465 : r->in.handle,
1466 : DCESRV_HANDLE_ANY,
1467 : struct lsa_info,
1468 0 : &status);
1469 978 : if (!NT_STATUS_IS_OK(status)) {
1470 26 : return NT_STATUS_INVALID_HANDLE;
1471 : }
1472 :
1473 952 : close_policy_hnd(p, r->in.handle);
1474 952 : ZERO_STRUCTP(r->out.handle);
1475 952 : return NT_STATUS_OK;
1476 : }
1477 :
1478 : /***************************************************************************
1479 : ***************************************************************************/
1480 :
1481 0 : static NTSTATUS lsa_lookup_trusted_domain_by_sid(TALLOC_CTX *mem_ctx,
1482 : const struct dom_sid *sid,
1483 : struct trustdom_info **info)
1484 : {
1485 0 : NTSTATUS status;
1486 0 : uint32_t num_domains = 0;
1487 0 : struct trustdom_info **domains = NULL;
1488 0 : int i;
1489 :
1490 0 : status = pdb_enum_trusteddoms(mem_ctx, &num_domains, &domains);
1491 0 : if (!NT_STATUS_IS_OK(status)) {
1492 0 : return status;
1493 : }
1494 :
1495 0 : for (i=0; i < num_domains; i++) {
1496 0 : if (dom_sid_equal(&domains[i]->sid, sid)) {
1497 0 : break;
1498 : }
1499 : }
1500 :
1501 0 : if (i == num_domains) {
1502 0 : return NT_STATUS_INVALID_PARAMETER;
1503 : }
1504 :
1505 0 : *info = domains[i];
1506 :
1507 0 : return NT_STATUS_OK;
1508 : }
1509 :
1510 : /***************************************************************************
1511 : ***************************************************************************/
1512 :
1513 0 : static NTSTATUS lsa_lookup_trusted_domain_by_name(TALLOC_CTX *mem_ctx,
1514 : const char *netbios_domain_name,
1515 : struct trustdom_info **info_p)
1516 : {
1517 0 : NTSTATUS status;
1518 0 : struct trustdom_info *info;
1519 0 : struct pdb_trusted_domain *td;
1520 :
1521 0 : status = pdb_get_trusted_domain(mem_ctx, netbios_domain_name, &td);
1522 0 : if (!NT_STATUS_IS_OK(status)) {
1523 0 : return status;
1524 : }
1525 :
1526 0 : info = talloc(mem_ctx, struct trustdom_info);
1527 0 : if (!info) {
1528 0 : return NT_STATUS_NO_MEMORY;
1529 : }
1530 :
1531 0 : info->name = talloc_strdup(info, netbios_domain_name);
1532 0 : NT_STATUS_HAVE_NO_MEMORY(info->name);
1533 :
1534 0 : sid_copy(&info->sid, &td->security_identifier);
1535 :
1536 0 : *info_p = info;
1537 :
1538 0 : return NT_STATUS_OK;
1539 : }
1540 :
1541 : /***************************************************************************
1542 : _lsa_OpenSecret
1543 : ***************************************************************************/
1544 :
1545 8 : NTSTATUS _lsa_OpenSecret(struct pipes_struct *p,
1546 : struct lsa_OpenSecret *r)
1547 : {
1548 8 : struct dcesrv_call_state *dce_call = p->dce_call;
1549 0 : struct auth_session_info *session_info =
1550 8 : dcesrv_call_session_info(dce_call);
1551 0 : struct security_descriptor *psd;
1552 0 : NTSTATUS status;
1553 0 : uint32_t acc_granted;
1554 :
1555 8 : (void)find_policy_by_hnd(p,
1556 : r->in.handle,
1557 : LSA_HANDLE_POLICY_TYPE,
1558 : struct lsa_info,
1559 0 : &status);
1560 8 : if (!NT_STATUS_IS_OK(status)) {
1561 0 : return NT_STATUS_INVALID_HANDLE;
1562 : }
1563 :
1564 8 : if (!r->in.name.string) {
1565 0 : return NT_STATUS_INVALID_PARAMETER;
1566 : }
1567 :
1568 : /* Work out max allowed. */
1569 8 : map_max_allowed_access(session_info->security_token,
1570 8 : session_info->unix_token,
1571 : &r->in.access_mask);
1572 :
1573 : /* map the generic bits to the lsa policy ones */
1574 8 : se_map_generic(&r->in.access_mask, &lsa_secret_mapping);
1575 :
1576 8 : status = pdb_get_secret(p->mem_ctx, r->in.name.string,
1577 : NULL,
1578 : NULL,
1579 : NULL,
1580 : NULL,
1581 : &psd);
1582 8 : if (!NT_STATUS_IS_OK(status)) {
1583 4 : return status;
1584 : }
1585 :
1586 4 : status = access_check_object(psd, session_info->security_token,
1587 : SEC_PRIV_INVALID, SEC_PRIV_INVALID, 0,
1588 : r->in.access_mask,
1589 : &acc_granted, "_lsa_OpenSecret");
1590 4 : if (!NT_STATUS_IS_OK(status)) {
1591 0 : return status;
1592 : }
1593 :
1594 4 : status = create_lsa_policy_handle(p->mem_ctx, p,
1595 : LSA_HANDLE_SECRET_TYPE,
1596 : acc_granted,
1597 : NULL,
1598 : r->in.name.string,
1599 : psd,
1600 : r->out.sec_handle);
1601 4 : if (!NT_STATUS_IS_OK(status)) {
1602 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1603 : }
1604 :
1605 4 : return NT_STATUS_OK;
1606 : }
1607 :
1608 : /***************************************************************************
1609 : _lsa_OpenTrustedDomain_base
1610 : ***************************************************************************/
1611 :
1612 0 : static NTSTATUS _lsa_OpenTrustedDomain_base(struct pipes_struct *p,
1613 : uint32_t access_mask,
1614 : struct trustdom_info *info,
1615 : struct policy_handle *handle)
1616 : {
1617 0 : struct dcesrv_call_state *dce_call = p->dce_call;
1618 0 : struct auth_session_info *session_info =
1619 0 : dcesrv_call_session_info(dce_call);
1620 0 : struct security_descriptor *psd = NULL;
1621 0 : size_t sd_size;
1622 0 : uint32_t acc_granted;
1623 0 : NTSTATUS status;
1624 :
1625 : /* des_access is for the account here, not the policy
1626 : * handle - so don't check against policy handle. */
1627 :
1628 : /* Work out max allowed. */
1629 0 : map_max_allowed_access(session_info->security_token,
1630 0 : session_info->unix_token,
1631 : &access_mask);
1632 :
1633 : /* map the generic bits to the lsa account ones */
1634 0 : se_map_generic(&access_mask, &lsa_trusted_domain_mapping);
1635 :
1636 : /* get the generic lsa account SD until we store it */
1637 0 : status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size,
1638 : &lsa_trusted_domain_mapping,
1639 : NULL, 0);
1640 0 : if (!NT_STATUS_IS_OK(status)) {
1641 0 : return status;
1642 : }
1643 :
1644 0 : status = access_check_object(psd, session_info->security_token,
1645 : SEC_PRIV_INVALID, SEC_PRIV_INVALID, 0,
1646 : access_mask, &acc_granted,
1647 : "_lsa_OpenTrustedDomain");
1648 0 : if (!NT_STATUS_IS_OK(status)) {
1649 0 : return status;
1650 : }
1651 :
1652 0 : status = create_lsa_policy_handle(p->mem_ctx, p,
1653 : LSA_HANDLE_TRUST_TYPE,
1654 : acc_granted,
1655 : &info->sid,
1656 0 : info->name,
1657 : psd,
1658 : handle);
1659 0 : if (!NT_STATUS_IS_OK(status)) {
1660 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1661 : }
1662 :
1663 0 : return NT_STATUS_OK;
1664 : }
1665 :
1666 : /***************************************************************************
1667 : _lsa_OpenTrustedDomain
1668 : ***************************************************************************/
1669 :
1670 0 : NTSTATUS _lsa_OpenTrustedDomain(struct pipes_struct *p,
1671 : struct lsa_OpenTrustedDomain *r)
1672 : {
1673 0 : struct trustdom_info *info = NULL;
1674 0 : NTSTATUS status;
1675 :
1676 0 : (void)find_policy_by_hnd(p,
1677 : r->in.handle,
1678 : LSA_HANDLE_POLICY_TYPE,
1679 : struct lsa_info,
1680 0 : &status);
1681 0 : if (!NT_STATUS_IS_OK(status)) {
1682 0 : return NT_STATUS_INVALID_HANDLE;
1683 : }
1684 :
1685 0 : status = lsa_lookup_trusted_domain_by_sid(p->mem_ctx,
1686 0 : r->in.sid,
1687 : &info);
1688 0 : if (!NT_STATUS_IS_OK(status)) {
1689 0 : return status;
1690 : }
1691 :
1692 0 : return _lsa_OpenTrustedDomain_base(p, r->in.access_mask, info,
1693 : r->out.trustdom_handle);
1694 : }
1695 :
1696 : /***************************************************************************
1697 : _lsa_OpenTrustedDomainByName
1698 : ***************************************************************************/
1699 :
1700 0 : NTSTATUS _lsa_OpenTrustedDomainByName(struct pipes_struct *p,
1701 : struct lsa_OpenTrustedDomainByName *r)
1702 : {
1703 0 : struct trustdom_info *info = NULL;
1704 0 : NTSTATUS status;
1705 :
1706 0 : (void)find_policy_by_hnd(p,
1707 : r->in.handle,
1708 : LSA_HANDLE_POLICY_TYPE,
1709 : struct lsa_info,
1710 0 : &status);
1711 0 : if (!NT_STATUS_IS_OK(status)) {
1712 0 : return NT_STATUS_INVALID_HANDLE;
1713 : }
1714 :
1715 0 : status = lsa_lookup_trusted_domain_by_name(p->mem_ctx,
1716 : r->in.name.string,
1717 : &info);
1718 0 : if (!NT_STATUS_IS_OK(status)) {
1719 0 : return status;
1720 : }
1721 :
1722 0 : return _lsa_OpenTrustedDomain_base(p, r->in.access_mask, info,
1723 : r->out.trustdom_handle);
1724 : }
1725 :
1726 0 : static NTSTATUS get_trustdom_auth_blob_aes(
1727 : struct dcesrv_call_state *dce_call,
1728 : TALLOC_CTX *mem_ctx,
1729 : struct lsa_TrustDomainInfoAuthInfoInternalAES *auth_info,
1730 : struct trustDomainPasswords *auth_struct)
1731 : {
1732 0 : DATA_BLOB session_key = data_blob_null;
1733 0 : DATA_BLOB salt = data_blob(auth_info->salt, sizeof(auth_info->salt));
1734 0 : DATA_BLOB auth_blob = data_blob(auth_info->cipher.data,
1735 : auth_info->cipher.size);
1736 0 : DATA_BLOB ciphertext = data_blob_null;
1737 0 : enum ndr_err_code ndr_err;
1738 0 : NTSTATUS status;
1739 :
1740 : /*
1741 : * The data blob starts with 512 bytes of random data and has two 32bit
1742 : * size parameters.
1743 : */
1744 0 : if (auth_blob.length < 520) {
1745 0 : return NT_STATUS_INVALID_PARAMETER;
1746 : }
1747 :
1748 0 : status = dcesrv_transport_session_key(dce_call, &session_key);
1749 0 : if (!NT_STATUS_IS_OK(status)) {
1750 0 : return status;
1751 : }
1752 :
1753 0 : status = samba_gnutls_aead_aes_256_cbc_hmac_sha512_decrypt(
1754 : mem_ctx,
1755 : &auth_blob,
1756 : &session_key,
1757 : &lsa_aes256_enc_key_salt,
1758 : &lsa_aes256_mac_key_salt,
1759 : &salt,
1760 0 : auth_info->auth_data,
1761 : &ciphertext);
1762 0 : if (!NT_STATUS_IS_OK(status)) {
1763 0 : return status;
1764 : }
1765 :
1766 0 : ndr_err = ndr_pull_struct_blob(
1767 : &ciphertext,
1768 : mem_ctx,
1769 : auth_struct,
1770 : (ndr_pull_flags_fn_t)ndr_pull_trustDomainPasswords);
1771 0 : if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
1772 0 : return NT_STATUS_INVALID_PARAMETER;
1773 : }
1774 :
1775 0 : return NT_STATUS_OK;
1776 : }
1777 :
1778 0 : static NTSTATUS get_trustdom_auth_blob(struct pipes_struct *p,
1779 : TALLOC_CTX *mem_ctx, DATA_BLOB *auth_blob,
1780 : struct trustDomainPasswords *auth_struct)
1781 : {
1782 0 : struct dcesrv_call_state *dce_call = p->dce_call;
1783 0 : struct auth_session_info *session_info =
1784 0 : dcesrv_call_session_info(dce_call);
1785 0 : enum ndr_err_code ndr_err;
1786 0 : DATA_BLOB lsession_key;
1787 0 : gnutls_cipher_hd_t cipher_hnd = NULL;
1788 0 : gnutls_datum_t my_session_key;
1789 0 : NTSTATUS status;
1790 0 : int rc;
1791 0 : bool encrypted;
1792 :
1793 0 : encrypted = dcerpc_is_transport_encrypted(session_info);
1794 0 : if (lp_weak_crypto() == SAMBA_WEAK_CRYPTO_DISALLOWED &&
1795 0 : !encrypted) {
1796 0 : return NT_STATUS_ACCESS_DENIED;
1797 : }
1798 :
1799 0 : status = session_extract_session_key(
1800 : session_info, &lsession_key, KEY_USE_16BYTES);
1801 0 : if (!NT_STATUS_IS_OK(status)) {
1802 0 : return NT_STATUS_INVALID_PARAMETER;
1803 : }
1804 :
1805 0 : my_session_key = (gnutls_datum_t) {
1806 0 : .data = lsession_key.data,
1807 0 : .size = lsession_key.length,
1808 : };
1809 :
1810 0 : GNUTLS_FIPS140_SET_LAX_MODE();
1811 0 : rc = gnutls_cipher_init(&cipher_hnd,
1812 : GNUTLS_CIPHER_ARCFOUR_128,
1813 : &my_session_key,
1814 : NULL);
1815 0 : if (rc < 0) {
1816 0 : GNUTLS_FIPS140_SET_STRICT_MODE();
1817 0 : status = gnutls_error_to_ntstatus(rc, NT_STATUS_CRYPTO_SYSTEM_INVALID);
1818 0 : goto out;
1819 : }
1820 :
1821 0 : rc = gnutls_cipher_decrypt(cipher_hnd,
1822 0 : auth_blob->data,
1823 : auth_blob->length);
1824 0 : gnutls_cipher_deinit(cipher_hnd);
1825 0 : GNUTLS_FIPS140_SET_STRICT_MODE();
1826 0 : if (rc < 0) {
1827 0 : status = gnutls_error_to_ntstatus(rc, NT_STATUS_CRYPTO_SYSTEM_INVALID);
1828 0 : goto out;
1829 : }
1830 :
1831 0 : ndr_err = ndr_pull_struct_blob(auth_blob, mem_ctx,
1832 : auth_struct,
1833 : (ndr_pull_flags_fn_t)ndr_pull_trustDomainPasswords);
1834 0 : if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
1835 0 : status = NT_STATUS_INVALID_PARAMETER;
1836 0 : goto out;
1837 : }
1838 :
1839 0 : status = NT_STATUS_OK;
1840 0 : out:
1841 0 : return status;
1842 : }
1843 :
1844 0 : static NTSTATUS get_trustauth_inout_blob(TALLOC_CTX *mem_ctx,
1845 : struct trustAuthInOutBlob *iopw,
1846 : DATA_BLOB *trustauth_blob)
1847 : {
1848 0 : enum ndr_err_code ndr_err;
1849 :
1850 0 : if (iopw->current.count != iopw->count) {
1851 0 : return NT_STATUS_INVALID_PARAMETER;
1852 : }
1853 :
1854 0 : if (iopw->previous.count > iopw->current.count) {
1855 0 : return NT_STATUS_INVALID_PARAMETER;
1856 : }
1857 :
1858 0 : if (iopw->previous.count == 0) {
1859 : /*
1860 : * If the previous credentials are not present
1861 : * we need to make a copy.
1862 : */
1863 0 : iopw->previous = iopw->current;
1864 : }
1865 :
1866 0 : if (iopw->previous.count < iopw->current.count) {
1867 0 : struct AuthenticationInformationArray *c = &iopw->current;
1868 0 : struct AuthenticationInformationArray *p = &iopw->previous;
1869 :
1870 : /*
1871 : * The previous array needs to have the same size
1872 : * as the current one.
1873 : *
1874 : * We may have to fill with TRUST_AUTH_TYPE_NONE
1875 : * elements.
1876 : */
1877 0 : p->array = talloc_realloc(mem_ctx, p->array,
1878 : struct AuthenticationInformation,
1879 : c->count);
1880 0 : if (p->array == NULL) {
1881 0 : return NT_STATUS_NO_MEMORY;
1882 : }
1883 :
1884 0 : while (p->count < c->count) {
1885 0 : struct AuthenticationInformation *a =
1886 0 : &p->array[p->count++];
1887 :
1888 0 : *a = (struct AuthenticationInformation) {
1889 0 : .LastUpdateTime = p->array[0].LastUpdateTime,
1890 : .AuthType = TRUST_AUTH_TYPE_NONE,
1891 : };
1892 : }
1893 : }
1894 :
1895 0 : ndr_err = ndr_push_struct_blob(trustauth_blob, mem_ctx,
1896 : iopw,
1897 : (ndr_push_flags_fn_t)ndr_push_trustAuthInOutBlob);
1898 0 : if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
1899 0 : return NT_STATUS_INVALID_PARAMETER;
1900 : }
1901 :
1902 0 : return NT_STATUS_OK;
1903 : }
1904 :
1905 0 : static NTSTATUS lsa_CreateTrustedDomain_precheck(
1906 : TALLOC_CTX *mem_ctx,
1907 : struct lsa_info *policy,
1908 : struct auth_session_info *session_info,
1909 : struct lsa_TrustDomainInfoInfoEx *info)
1910 : {
1911 0 : const char *netbios_name = NULL;
1912 0 : const char *dns_name = NULL;
1913 0 : bool ok;
1914 :
1915 0 : netbios_name = info->netbios_name.string;
1916 0 : if (netbios_name == NULL) {
1917 0 : return NT_STATUS_INVALID_PARAMETER;
1918 : }
1919 :
1920 0 : dns_name = info->domain_name.string;
1921 0 : if (dns_name == NULL) {
1922 0 : return NT_STATUS_INVALID_PARAMETER;
1923 : }
1924 :
1925 0 : if (info->sid == NULL) {
1926 0 : return NT_STATUS_INVALID_SID;
1927 : }
1928 :
1929 0 : if (!(policy->access & LSA_POLICY_TRUST_ADMIN)) {
1930 0 : return NT_STATUS_ACCESS_DENIED;
1931 : }
1932 :
1933 : /*
1934 : * We expect S-1-5-21-A-B-C, but we don't
1935 : * allow S-1-5-21-0-0-0 as this is used
1936 : * for claims and compound identities.
1937 : */
1938 0 : ok = dom_sid_is_valid_account_domain(info->sid);
1939 0 : if (!ok) {
1940 0 : return NT_STATUS_INVALID_PARAMETER;
1941 : }
1942 :
1943 0 : if (strcasecmp(netbios_name, "BUILTIN") == 0 ||
1944 0 : strcasecmp(dns_name, "BUILTIN") == 0)
1945 : {
1946 0 : return NT_STATUS_INVALID_PARAMETER;
1947 : }
1948 :
1949 0 : if (policy->name != NULL &&
1950 0 : (strcasecmp(netbios_name, policy->name) == 0 ||
1951 0 : strcasecmp(dns_name, policy->name) == 0))
1952 : {
1953 0 : return NT_STATUS_CURRENT_DOMAIN_NOT_ALLOWED;
1954 : }
1955 :
1956 0 : if (session_info->unix_token->uid != sec_initial_uid() &&
1957 0 : !nt_token_check_domain_rid(session_info->security_token,
1958 : DOMAIN_RID_ADMINS))
1959 : {
1960 0 : return NT_STATUS_ACCESS_DENIED;
1961 : }
1962 :
1963 0 : return NT_STATUS_OK;
1964 : }
1965 :
1966 0 : static NTSTATUS lsa_CreateTrustedDomain_common(
1967 : struct pipes_struct *p,
1968 : TALLOC_CTX *mem_ctx,
1969 : struct auth_session_info *session_info,
1970 : struct lsa_info *policy,
1971 : uint32_t access_mask,
1972 : struct lsa_TrustDomainInfoInfoEx *info,
1973 : struct trustDomainPasswords *auth_struct,
1974 : struct policy_handle **ptrustdom_handle)
1975 : {
1976 0 : struct security_descriptor *psd = NULL;
1977 0 : size_t sd_size = 0;
1978 0 : uint32_t acc_granted = 0;
1979 0 : struct pdb_trusted_domain td = {
1980 : .trust_type = 0,
1981 : };
1982 0 : NTSTATUS status;
1983 :
1984 : /* Work out max allowed. */
1985 0 : map_max_allowed_access(session_info->security_token,
1986 0 : session_info->unix_token,
1987 : &access_mask);
1988 :
1989 : /* map the generic bits to the lsa policy ones */
1990 0 : se_map_generic(&access_mask, &lsa_account_mapping);
1991 :
1992 0 : status = make_lsa_object_sd(
1993 : mem_ctx, &psd, &sd_size, &lsa_trusted_domain_mapping, NULL, 0);
1994 0 : if (!NT_STATUS_IS_OK(status)) {
1995 0 : return status;
1996 : }
1997 :
1998 0 : status = access_check_object(psd,
1999 : session_info->security_token,
2000 : SEC_PRIV_INVALID,
2001 : SEC_PRIV_INVALID,
2002 : 0,
2003 : access_mask,
2004 : &acc_granted,
2005 : "lsa_CreateTrustedDomain_common");
2006 0 : if (!NT_STATUS_IS_OK(status)) {
2007 0 : return status;
2008 : }
2009 :
2010 0 : td.domain_name = talloc_strdup(mem_ctx, info->domain_name.string);
2011 0 : if (td.domain_name == NULL) {
2012 0 : return NT_STATUS_NO_MEMORY;
2013 : }
2014 0 : td.netbios_name = talloc_strdup(mem_ctx, info->netbios_name.string);
2015 0 : if (td.netbios_name == NULL) {
2016 0 : return NT_STATUS_NO_MEMORY;
2017 : }
2018 0 : sid_copy(&td.security_identifier, info->sid);
2019 0 : td.trust_direction = info->trust_direction;
2020 0 : td.trust_type = info->trust_type;
2021 0 : td.trust_attributes = info->trust_attributes;
2022 :
2023 0 : status = get_trustauth_inout_blob(mem_ctx,
2024 : &auth_struct->incoming,
2025 : &td.trust_auth_incoming);
2026 0 : if (!NT_STATUS_IS_OK(status)) {
2027 0 : return NT_STATUS_UNSUCCESSFUL;
2028 : }
2029 :
2030 0 : status = get_trustauth_inout_blob(mem_ctx,
2031 : &auth_struct->outgoing,
2032 : &td.trust_auth_outgoing);
2033 0 : if (!NT_STATUS_IS_OK(status)) {
2034 0 : return NT_STATUS_UNSUCCESSFUL;
2035 : }
2036 :
2037 0 : status = pdb_set_trusted_domain(info->domain_name.string, &td);
2038 0 : if (!NT_STATUS_IS_OK(status)) {
2039 0 : DBG_ERR("pdb_set_trusted_domain failed: %s\n",
2040 : nt_errstr(status));
2041 0 : return status;
2042 : }
2043 :
2044 0 : status = create_lsa_policy_handle(mem_ctx, p,
2045 : LSA_HANDLE_TRUST_TYPE,
2046 : acc_granted,
2047 : info->sid,
2048 : info->netbios_name.string,
2049 : psd,
2050 : *ptrustdom_handle);
2051 0 : if (!NT_STATUS_IS_OK(status)) {
2052 0 : pdb_del_trusted_domain(info->netbios_name.string);
2053 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
2054 : }
2055 :
2056 0 : return NT_STATUS_OK;
2057 : }
2058 :
2059 : /***************************************************************************
2060 : _lsa_CreateTrustedDomainEx2
2061 : ***************************************************************************/
2062 :
2063 0 : NTSTATUS _lsa_CreateTrustedDomainEx2(struct pipes_struct *p,
2064 : struct lsa_CreateTrustedDomainEx2 *r)
2065 : {
2066 0 : struct dcesrv_call_state *dce_call = p->dce_call;
2067 0 : struct auth_session_info *session_info =
2068 0 : dcesrv_call_session_info(dce_call);
2069 0 : struct lsa_info *policy;
2070 0 : NTSTATUS status;
2071 0 : struct trustDomainPasswords auth_struct = {
2072 : .incoming_size = 0,
2073 : };
2074 0 : DATA_BLOB auth_blob = data_blob_null;
2075 :
2076 0 : if (!IS_DC) {
2077 0 : return NT_STATUS_NOT_SUPPORTED;
2078 : }
2079 :
2080 0 : policy = find_policy_by_hnd(p,
2081 : r->in.policy_handle,
2082 : LSA_HANDLE_POLICY_TYPE,
2083 : struct lsa_info,
2084 0 : &status);
2085 0 : if (!NT_STATUS_IS_OK(status)) {
2086 0 : return NT_STATUS_INVALID_HANDLE;
2087 : }
2088 :
2089 0 : status = lsa_CreateTrustedDomain_precheck(p->mem_ctx,
2090 : policy,
2091 : session_info,
2092 : r->in.info);
2093 0 : if (!NT_STATUS_IS_OK(status)) {
2094 0 : return status;
2095 : }
2096 :
2097 :
2098 0 : if (r->in.auth_info_internal->auth_blob.size == 0) {
2099 0 : return NT_STATUS_INVALID_PARAMETER;
2100 : }
2101 :
2102 0 : auth_blob = data_blob_const(r->in.auth_info_internal->auth_blob.data,
2103 0 : r->in.auth_info_internal->auth_blob.size);
2104 :
2105 0 : status = get_trustdom_auth_blob(p,
2106 : p->mem_ctx,
2107 : &auth_blob,
2108 : &auth_struct);
2109 0 : if (!NT_STATUS_IS_OK(status)) {
2110 0 : return NT_STATUS_UNSUCCESSFUL;
2111 : }
2112 :
2113 0 : status = lsa_CreateTrustedDomain_common(p,
2114 : p->mem_ctx,
2115 : session_info,
2116 : policy,
2117 : r->in.access_mask,
2118 : r->in.info,
2119 : &auth_struct,
2120 : &r->out.trustdom_handle);
2121 0 : if (!NT_STATUS_IS_OK(status)) {
2122 0 : return status;
2123 : }
2124 :
2125 0 : return NT_STATUS_OK;
2126 : }
2127 :
2128 : /***************************************************************************
2129 : _lsa_CreateTrustedDomainEx
2130 : ***************************************************************************/
2131 :
2132 0 : NTSTATUS _lsa_CreateTrustedDomainEx(struct pipes_struct *p,
2133 : struct lsa_CreateTrustedDomainEx *r)
2134 : {
2135 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
2136 0 : return NT_STATUS_NOT_IMPLEMENTED;
2137 : }
2138 :
2139 : /***************************************************************************
2140 : _lsa_CreateTrustedDomain
2141 : ***************************************************************************/
2142 :
2143 0 : NTSTATUS _lsa_CreateTrustedDomain(struct pipes_struct *p,
2144 : struct lsa_CreateTrustedDomain *r)
2145 : {
2146 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
2147 0 : return NT_STATUS_NOT_IMPLEMENTED;
2148 : }
2149 :
2150 : /***************************************************************************
2151 : _lsa_DeleteTrustedDomain
2152 : ***************************************************************************/
2153 :
2154 0 : NTSTATUS _lsa_DeleteTrustedDomain(struct pipes_struct *p,
2155 : struct lsa_DeleteTrustedDomain *r)
2156 : {
2157 0 : NTSTATUS status;
2158 0 : struct lsa_info *handle;
2159 0 : struct pdb_trusted_domain *td;
2160 :
2161 : /* find the connection policy handle. */
2162 0 : handle = find_policy_by_hnd(p,
2163 : r->in.handle,
2164 : LSA_HANDLE_POLICY_TYPE,
2165 : struct lsa_info,
2166 0 : &status);
2167 0 : if (!NT_STATUS_IS_OK(status)) {
2168 0 : return NT_STATUS_INVALID_HANDLE;
2169 : }
2170 :
2171 0 : if (!(handle->access & LSA_POLICY_TRUST_ADMIN)) {
2172 0 : return NT_STATUS_ACCESS_DENIED;
2173 : }
2174 :
2175 0 : status = pdb_get_trusted_domain_by_sid(p->mem_ctx, r->in.dom_sid, &td);
2176 0 : if (!NT_STATUS_IS_OK(status)) {
2177 0 : return status;
2178 : }
2179 :
2180 0 : if (td->netbios_name == NULL || *td->netbios_name == '\0') {
2181 0 : struct dom_sid_buf buf;
2182 0 : DEBUG(10, ("Missing netbios name for trusted domain %s.\n",
2183 : dom_sid_str_buf(r->in.dom_sid, &buf)));
2184 0 : return NT_STATUS_UNSUCCESSFUL;
2185 : }
2186 :
2187 0 : status = pdb_del_trusted_domain(td->netbios_name);
2188 0 : if (!NT_STATUS_IS_OK(status)) {
2189 0 : return status;
2190 : }
2191 :
2192 0 : return NT_STATUS_OK;
2193 : }
2194 :
2195 : /***************************************************************************
2196 : _lsa_CloseTrustedDomainEx
2197 : ***************************************************************************/
2198 :
2199 0 : NTSTATUS _lsa_CloseTrustedDomainEx(struct pipes_struct *p,
2200 : struct lsa_CloseTrustedDomainEx *r)
2201 : {
2202 0 : return NT_STATUS_NOT_IMPLEMENTED;
2203 : }
2204 :
2205 : /***************************************************************************
2206 : _lsa_QueryTrustedDomainInfo
2207 : ***************************************************************************/
2208 :
2209 0 : static NTSTATUS pdb_trusted_domain_2_info_ex(TALLOC_CTX *mem_ctx,
2210 : struct pdb_trusted_domain *td,
2211 : struct lsa_TrustDomainInfoInfoEx *info_ex)
2212 : {
2213 0 : if (td->domain_name == NULL ||
2214 0 : td->netbios_name == NULL ||
2215 0 : is_null_sid(&td->security_identifier)) {
2216 0 : return NT_STATUS_INVALID_PARAMETER;
2217 : }
2218 :
2219 0 : info_ex->domain_name.string = talloc_strdup(mem_ctx, td->domain_name);
2220 0 : info_ex->netbios_name.string = talloc_strdup(mem_ctx, td->netbios_name);
2221 0 : info_ex->sid = dom_sid_dup(mem_ctx, &td->security_identifier);
2222 0 : if (info_ex->domain_name.string == NULL ||
2223 0 : info_ex->netbios_name.string == NULL ||
2224 0 : info_ex->sid == NULL) {
2225 0 : return NT_STATUS_NO_MEMORY;
2226 : }
2227 :
2228 0 : info_ex->trust_direction = td->trust_direction;
2229 0 : info_ex->trust_type = td->trust_type;
2230 0 : info_ex->trust_attributes = td->trust_attributes;
2231 :
2232 0 : return NT_STATUS_OK;
2233 : }
2234 :
2235 0 : NTSTATUS _lsa_QueryTrustedDomainInfo(struct pipes_struct *p,
2236 : struct lsa_QueryTrustedDomainInfo *r)
2237 : {
2238 0 : NTSTATUS status;
2239 0 : struct lsa_info *handle;
2240 0 : union lsa_TrustedDomainInfo *info;
2241 0 : struct pdb_trusted_domain *td;
2242 0 : uint32_t acc_required;
2243 :
2244 : /* find the connection policy handle. */
2245 0 : handle = find_policy_by_hnd(p,
2246 : r->in.trustdom_handle,
2247 : LSA_HANDLE_TRUST_TYPE,
2248 : struct lsa_info,
2249 0 : &status);
2250 0 : if (!NT_STATUS_IS_OK(status)) {
2251 0 : return NT_STATUS_INVALID_HANDLE;
2252 : }
2253 :
2254 0 : switch (r->in.level) {
2255 0 : case LSA_TRUSTED_DOMAIN_INFO_NAME:
2256 0 : acc_required = LSA_TRUSTED_QUERY_DOMAIN_NAME;
2257 0 : break;
2258 0 : case LSA_TRUSTED_DOMAIN_INFO_CONTROLLERS:
2259 0 : acc_required = LSA_TRUSTED_QUERY_CONTROLLERS;
2260 0 : break;
2261 0 : case LSA_TRUSTED_DOMAIN_INFO_POSIX_OFFSET:
2262 0 : acc_required = LSA_TRUSTED_QUERY_POSIX;
2263 0 : break;
2264 0 : case LSA_TRUSTED_DOMAIN_INFO_PASSWORD:
2265 0 : acc_required = LSA_TRUSTED_QUERY_AUTH;
2266 0 : break;
2267 0 : case LSA_TRUSTED_DOMAIN_INFO_BASIC:
2268 0 : acc_required = LSA_TRUSTED_QUERY_DOMAIN_NAME;
2269 0 : break;
2270 0 : case LSA_TRUSTED_DOMAIN_INFO_INFO_EX:
2271 0 : acc_required = LSA_TRUSTED_QUERY_DOMAIN_NAME;
2272 0 : break;
2273 0 : case LSA_TRUSTED_DOMAIN_INFO_AUTH_INFO:
2274 0 : acc_required = LSA_TRUSTED_QUERY_AUTH;
2275 0 : break;
2276 0 : case LSA_TRUSTED_DOMAIN_INFO_FULL_INFO:
2277 0 : acc_required = LSA_TRUSTED_QUERY_DOMAIN_NAME |
2278 : LSA_TRUSTED_QUERY_POSIX |
2279 : LSA_TRUSTED_QUERY_AUTH;
2280 0 : break;
2281 0 : case LSA_TRUSTED_DOMAIN_INFO_AUTH_INFO_INTERNAL:
2282 0 : acc_required = LSA_TRUSTED_QUERY_AUTH;
2283 0 : break;
2284 0 : case LSA_TRUSTED_DOMAIN_INFO_FULL_INFO_INTERNAL:
2285 0 : acc_required = LSA_TRUSTED_QUERY_DOMAIN_NAME |
2286 : LSA_TRUSTED_QUERY_POSIX |
2287 : LSA_TRUSTED_QUERY_AUTH;
2288 0 : break;
2289 0 : case LSA_TRUSTED_DOMAIN_INFO_INFO_EX2_INTERNAL:
2290 0 : acc_required = LSA_TRUSTED_QUERY_DOMAIN_NAME;
2291 0 : break;
2292 0 : case LSA_TRUSTED_DOMAIN_INFO_FULL_INFO_2_INTERNAL:
2293 0 : acc_required = LSA_TRUSTED_QUERY_DOMAIN_NAME |
2294 : LSA_TRUSTED_QUERY_POSIX |
2295 : LSA_TRUSTED_QUERY_AUTH;
2296 0 : break;
2297 0 : case LSA_TRUSTED_DOMAIN_SUPPORTED_ENCRYPTION_TYPES:
2298 0 : acc_required = LSA_TRUSTED_QUERY_POSIX;
2299 0 : break;
2300 0 : default:
2301 0 : return NT_STATUS_INVALID_PARAMETER;
2302 : }
2303 :
2304 0 : if (!(handle->access & acc_required)) {
2305 0 : return NT_STATUS_ACCESS_DENIED;
2306 : }
2307 :
2308 0 : status = pdb_get_trusted_domain_by_sid(p->mem_ctx, &handle->sid, &td);
2309 0 : if (!NT_STATUS_IS_OK(status)) {
2310 0 : return status;
2311 : }
2312 :
2313 0 : info = talloc_zero(p->mem_ctx, union lsa_TrustedDomainInfo);
2314 0 : if (!info) {
2315 0 : return NT_STATUS_NO_MEMORY;
2316 : }
2317 :
2318 0 : switch (r->in.level) {
2319 0 : case LSA_TRUSTED_DOMAIN_INFO_NAME:
2320 0 : init_lsa_StringLarge(&info->name.netbios_name, td->netbios_name);
2321 0 : break;
2322 0 : case LSA_TRUSTED_DOMAIN_INFO_CONTROLLERS:
2323 0 : return NT_STATUS_INVALID_PARAMETER;
2324 0 : case LSA_TRUSTED_DOMAIN_INFO_POSIX_OFFSET:
2325 0 : info->posix_offset.posix_offset = *td->trust_posix_offset;
2326 0 : break;
2327 0 : case LSA_TRUSTED_DOMAIN_INFO_PASSWORD:
2328 0 : return NT_STATUS_INVALID_INFO_CLASS;
2329 0 : case LSA_TRUSTED_DOMAIN_INFO_BASIC:
2330 0 : return NT_STATUS_INVALID_PARAMETER;
2331 0 : case LSA_TRUSTED_DOMAIN_INFO_INFO_EX:
2332 0 : status = pdb_trusted_domain_2_info_ex(info, td, &info->info_ex);
2333 0 : if (!NT_STATUS_IS_OK(status)) {
2334 0 : return status;
2335 : }
2336 0 : break;
2337 0 : case LSA_TRUSTED_DOMAIN_INFO_AUTH_INFO:
2338 0 : return NT_STATUS_INVALID_INFO_CLASS;
2339 0 : case LSA_TRUSTED_DOMAIN_INFO_FULL_INFO:
2340 0 : status = pdb_trusted_domain_2_info_ex(info, td,
2341 : &info->full_info.info_ex);
2342 0 : if (!NT_STATUS_IS_OK(status)) {
2343 0 : return status;
2344 : }
2345 0 : info->full_info.posix_offset.posix_offset = *td->trust_posix_offset;
2346 0 : status = auth_blob_2_auth_info(p->mem_ctx,
2347 0 : td->trust_auth_incoming,
2348 0 : td->trust_auth_outgoing,
2349 : &info->full_info.auth_info);
2350 0 : if (!NT_STATUS_IS_OK(status)) {
2351 0 : return status;
2352 : }
2353 0 : break;
2354 0 : case LSA_TRUSTED_DOMAIN_INFO_AUTH_INFO_INTERNAL:
2355 0 : return NT_STATUS_INVALID_INFO_CLASS;
2356 0 : case LSA_TRUSTED_DOMAIN_INFO_FULL_INFO_INTERNAL:
2357 0 : return NT_STATUS_INVALID_INFO_CLASS;
2358 0 : case LSA_TRUSTED_DOMAIN_INFO_INFO_EX2_INTERNAL:
2359 0 : return NT_STATUS_INVALID_PARAMETER;
2360 0 : case LSA_TRUSTED_DOMAIN_INFO_FULL_INFO_2_INTERNAL:
2361 0 : info->full_info2_internal.posix_offset.posix_offset = *td->trust_posix_offset;
2362 0 : status = auth_blob_2_auth_info(p->mem_ctx,
2363 0 : td->trust_auth_incoming,
2364 0 : td->trust_auth_outgoing,
2365 : &info->full_info2_internal.auth_info);
2366 0 : if (!NT_STATUS_IS_OK(status)) {
2367 0 : return status;
2368 : }
2369 0 : break;
2370 0 : case LSA_TRUSTED_DOMAIN_SUPPORTED_ENCRYPTION_TYPES:
2371 0 : info->enc_types.enc_types = *td->supported_enc_type;
2372 0 : break;
2373 0 : default:
2374 0 : return NT_STATUS_INVALID_PARAMETER;
2375 : }
2376 :
2377 0 : *r->out.info = info;
2378 :
2379 0 : return NT_STATUS_OK;
2380 : }
2381 :
2382 : /***************************************************************************
2383 : _lsa_QueryTrustedDomainInfoBySid
2384 : ***************************************************************************/
2385 :
2386 0 : NTSTATUS _lsa_QueryTrustedDomainInfoBySid(struct pipes_struct *p,
2387 : struct lsa_QueryTrustedDomainInfoBySid *r)
2388 : {
2389 0 : NTSTATUS status;
2390 0 : struct policy_handle trustdom_handle;
2391 0 : struct lsa_OpenTrustedDomain o;
2392 0 : struct lsa_QueryTrustedDomainInfo q;
2393 0 : struct lsa_Close c;
2394 :
2395 0 : o.in.handle = r->in.handle;
2396 0 : o.in.sid = r->in.dom_sid;
2397 0 : o.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
2398 0 : o.out.trustdom_handle = &trustdom_handle;
2399 :
2400 0 : status = _lsa_OpenTrustedDomain(p, &o);
2401 0 : if (!NT_STATUS_IS_OK(status)) {
2402 0 : return status;
2403 : }
2404 :
2405 0 : q.in.trustdom_handle = &trustdom_handle;
2406 0 : q.in.level = r->in.level;
2407 0 : q.out.info = r->out.info;
2408 :
2409 0 : status = _lsa_QueryTrustedDomainInfo(p, &q);
2410 0 : if (!NT_STATUS_IS_OK(status)) {
2411 0 : return status;
2412 : }
2413 :
2414 0 : c.in.handle = &trustdom_handle;
2415 0 : c.out.handle = &trustdom_handle;
2416 :
2417 0 : return _lsa_Close(p, &c);
2418 : }
2419 :
2420 : /***************************************************************************
2421 : _lsa_QueryTrustedDomainInfoByName
2422 : ***************************************************************************/
2423 :
2424 0 : NTSTATUS _lsa_QueryTrustedDomainInfoByName(struct pipes_struct *p,
2425 : struct lsa_QueryTrustedDomainInfoByName *r)
2426 : {
2427 0 : NTSTATUS status;
2428 0 : struct policy_handle trustdom_handle;
2429 0 : struct lsa_OpenTrustedDomainByName o;
2430 0 : struct lsa_QueryTrustedDomainInfo q;
2431 0 : struct lsa_Close c;
2432 :
2433 0 : o.in.handle = r->in.handle;
2434 0 : o.in.name.string = r->in.trusted_domain->string;
2435 0 : o.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
2436 0 : o.out.trustdom_handle = &trustdom_handle;
2437 :
2438 0 : status = _lsa_OpenTrustedDomainByName(p, &o);
2439 0 : if (!NT_STATUS_IS_OK(status)) {
2440 0 : if (NT_STATUS_EQUAL(status, NT_STATUS_NO_SUCH_DOMAIN)) {
2441 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
2442 : }
2443 0 : return status;
2444 : }
2445 :
2446 0 : q.in.trustdom_handle = &trustdom_handle;
2447 0 : q.in.level = r->in.level;
2448 0 : q.out.info = r->out.info;
2449 :
2450 0 : status = _lsa_QueryTrustedDomainInfo(p, &q);
2451 0 : if (!NT_STATUS_IS_OK(status)) {
2452 0 : return status;
2453 : }
2454 :
2455 0 : c.in.handle = &trustdom_handle;
2456 0 : c.out.handle = &trustdom_handle;
2457 :
2458 0 : return _lsa_Close(p, &c);
2459 : }
2460 :
2461 : /***************************************************************************
2462 : _lsa_CreateSecret
2463 : ***************************************************************************/
2464 :
2465 632 : NTSTATUS _lsa_CreateSecret(struct pipes_struct *p,
2466 : struct lsa_CreateSecret *r)
2467 : {
2468 632 : struct dcesrv_call_state *dce_call = p->dce_call;
2469 0 : struct auth_session_info *session_info =
2470 632 : dcesrv_call_session_info(dce_call);
2471 0 : NTSTATUS status;
2472 0 : struct lsa_info *handle;
2473 0 : uint32_t acc_granted;
2474 0 : struct security_descriptor *psd;
2475 0 : size_t sd_size;
2476 :
2477 : /* find the connection policy handle. */
2478 632 : handle = find_policy_by_hnd(p,
2479 : r->in.handle,
2480 : LSA_HANDLE_POLICY_TYPE,
2481 : struct lsa_info,
2482 0 : &status);
2483 632 : if (!NT_STATUS_IS_OK(status)) {
2484 0 : return NT_STATUS_INVALID_HANDLE;
2485 : }
2486 :
2487 : /* check if the user has enough rights */
2488 :
2489 632 : if (!(handle->access & LSA_POLICY_CREATE_SECRET)) {
2490 0 : return NT_STATUS_ACCESS_DENIED;
2491 : }
2492 :
2493 : /* Work out max allowed. */
2494 632 : map_max_allowed_access(session_info->security_token,
2495 632 : session_info->unix_token,
2496 : &r->in.access_mask);
2497 :
2498 : /* map the generic bits to the lsa policy ones */
2499 632 : se_map_generic(&r->in.access_mask, &lsa_secret_mapping);
2500 :
2501 632 : status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size,
2502 : &lsa_secret_mapping,
2503 : NULL, 0);
2504 632 : if (!NT_STATUS_IS_OK(status)) {
2505 0 : return status;
2506 : }
2507 :
2508 632 : status = access_check_object(psd, session_info->security_token,
2509 : SEC_PRIV_INVALID, SEC_PRIV_INVALID, 0,
2510 : r->in.access_mask,
2511 : &acc_granted, "_lsa_CreateSecret");
2512 632 : if (!NT_STATUS_IS_OK(status)) {
2513 0 : return status;
2514 : }
2515 :
2516 632 : if (!r->in.name.string) {
2517 0 : return NT_STATUS_INVALID_PARAMETER;
2518 : }
2519 :
2520 632 : if (strlen(r->in.name.string) > 128) {
2521 0 : return NT_STATUS_NAME_TOO_LONG;
2522 : }
2523 :
2524 632 : status = pdb_get_secret(p->mem_ctx, r->in.name.string,
2525 : NULL, NULL, NULL, NULL, NULL);
2526 632 : if (NT_STATUS_IS_OK(status)) {
2527 4 : return NT_STATUS_OBJECT_NAME_COLLISION;
2528 : }
2529 :
2530 628 : status = pdb_set_secret(r->in.name.string, NULL, NULL, psd);
2531 628 : if (!NT_STATUS_IS_OK(status)) {
2532 0 : return status;
2533 : }
2534 :
2535 628 : status = create_lsa_policy_handle(p->mem_ctx, p,
2536 : LSA_HANDLE_SECRET_TYPE,
2537 : acc_granted,
2538 : NULL,
2539 : r->in.name.string,
2540 : psd,
2541 : r->out.sec_handle);
2542 628 : if (!NT_STATUS_IS_OK(status)) {
2543 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
2544 : }
2545 :
2546 628 : return NT_STATUS_OK;
2547 : }
2548 :
2549 : /***************************************************************************
2550 : _lsa_SetSecret
2551 : ***************************************************************************/
2552 :
2553 848 : NTSTATUS _lsa_SetSecret(struct pipes_struct *p,
2554 : struct lsa_SetSecret *r)
2555 : {
2556 848 : struct dcesrv_call_state *dce_call = p->dce_call;
2557 0 : struct auth_session_info *session_info =
2558 848 : dcesrv_call_session_info(dce_call);
2559 0 : NTSTATUS status;
2560 848 : struct lsa_info *info = NULL;
2561 0 : DATA_BLOB blob_new, blob_old;
2562 848 : DATA_BLOB cleartext_blob_new = data_blob_null;
2563 848 : DATA_BLOB cleartext_blob_old = data_blob_null;
2564 848 : DATA_BLOB *cleartext_blob_new_p = NULL;
2565 848 : DATA_BLOB *cleartext_blob_old_p = NULL;
2566 0 : DATA_BLOB session_key;
2567 :
2568 848 : info = find_policy_by_hnd(p,
2569 : r->in.sec_handle,
2570 : LSA_HANDLE_SECRET_TYPE,
2571 : struct lsa_info,
2572 0 : &status);
2573 848 : if (!NT_STATUS_IS_OK(status)) {
2574 0 : return NT_STATUS_INVALID_HANDLE;
2575 : }
2576 :
2577 848 : if (!(info->access & LSA_SECRET_SET_VALUE)) {
2578 0 : return NT_STATUS_ACCESS_DENIED;
2579 : }
2580 :
2581 848 : status = session_extract_session_key(
2582 : session_info, &session_key, KEY_USE_16BYTES);
2583 848 : if(!NT_STATUS_IS_OK(status)) {
2584 0 : return status;
2585 : }
2586 :
2587 848 : if (r->in.new_val) {
2588 844 : blob_new = data_blob_const(r->in.new_val->data,
2589 844 : r->in.new_val->length);
2590 :
2591 844 : status = sess_decrypt_blob(p->mem_ctx, &blob_new,
2592 : &session_key,
2593 : &cleartext_blob_new);
2594 844 : if (!NT_STATUS_IS_OK(status)) {
2595 420 : return status;
2596 : }
2597 :
2598 424 : cleartext_blob_new_p = &cleartext_blob_new;
2599 : }
2600 :
2601 428 : if (r->in.old_val) {
2602 4 : blob_old = data_blob_const(r->in.old_val->data,
2603 4 : r->in.old_val->length);
2604 :
2605 4 : status = sess_decrypt_blob(p->mem_ctx, &blob_old,
2606 : &session_key,
2607 : &cleartext_blob_old);
2608 4 : if (!NT_STATUS_IS_OK(status)) {
2609 0 : return status;
2610 : }
2611 :
2612 4 : cleartext_blob_old_p = &cleartext_blob_old;
2613 : }
2614 :
2615 428 : status = pdb_set_secret(info->name, cleartext_blob_new_p, cleartext_blob_old_p, NULL);
2616 428 : if (!NT_STATUS_IS_OK(status)) {
2617 0 : return status;
2618 : }
2619 :
2620 : #ifdef DEBUG_PASSWORD
2621 428 : DEBUG(10,("_lsa_SetSecret: successfully set new secret\n"));
2622 428 : dump_data(10, cleartext_blob_new.data, cleartext_blob_new.length);
2623 428 : DEBUG(10,("_lsa_SetSecret: successfully set old secret\n"));
2624 428 : dump_data(10, cleartext_blob_old.data, cleartext_blob_old.length);
2625 : #endif
2626 :
2627 428 : return NT_STATUS_OK;
2628 : }
2629 :
2630 : /***************************************************************************
2631 : _lsa_QuerySecret
2632 : ***************************************************************************/
2633 :
2634 428 : NTSTATUS _lsa_QuerySecret(struct pipes_struct *p,
2635 : struct lsa_QuerySecret *r)
2636 : {
2637 428 : struct dcesrv_call_state *dce_call = p->dce_call;
2638 0 : struct auth_session_info *session_info =
2639 428 : dcesrv_call_session_info(dce_call);
2640 428 : struct lsa_info *info = NULL;
2641 0 : DATA_BLOB blob_new, blob_old;
2642 0 : DATA_BLOB blob_new_crypt, blob_old_crypt;
2643 0 : DATA_BLOB session_key;
2644 0 : NTTIME nttime_new, nttime_old;
2645 0 : NTSTATUS status;
2646 :
2647 428 : info = find_policy_by_hnd(p,
2648 : r->in.sec_handle,
2649 : LSA_HANDLE_SECRET_TYPE,
2650 : struct lsa_info,
2651 0 : &status);
2652 428 : if (!NT_STATUS_IS_OK(status)) {
2653 0 : return NT_STATUS_INVALID_HANDLE;
2654 : }
2655 :
2656 428 : if (!(info->access & LSA_SECRET_QUERY_VALUE)) {
2657 0 : return NT_STATUS_ACCESS_DENIED;
2658 : }
2659 :
2660 428 : status = pdb_get_secret(p->mem_ctx, info->name,
2661 : &blob_new, &nttime_new,
2662 : &blob_old, &nttime_old,
2663 : NULL);
2664 428 : if (!NT_STATUS_IS_OK(status)) {
2665 0 : return status;
2666 : }
2667 :
2668 428 : status = session_extract_session_key(
2669 : session_info, &session_key, KEY_USE_16BYTES);
2670 428 : if(!NT_STATUS_IS_OK(status)) {
2671 0 : return status;
2672 : }
2673 :
2674 428 : if (r->in.new_val) {
2675 428 : if (blob_new.length) {
2676 424 : if (!r->out.new_val->buf) {
2677 424 : r->out.new_val->buf = talloc_zero(p->mem_ctx, struct lsa_DATA_BUF);
2678 : }
2679 424 : if (!r->out.new_val->buf) {
2680 0 : return NT_STATUS_NO_MEMORY;
2681 : }
2682 :
2683 424 : blob_new_crypt = sess_encrypt_blob(p->mem_ctx, &blob_new,
2684 : &session_key);
2685 424 : if (!blob_new_crypt.length) {
2686 0 : return NT_STATUS_NO_MEMORY;
2687 : }
2688 :
2689 424 : r->out.new_val->buf->data = blob_new_crypt.data;
2690 424 : r->out.new_val->buf->length = blob_new_crypt.length;
2691 424 : r->out.new_val->buf->size = blob_new_crypt.length;
2692 : }
2693 : }
2694 :
2695 428 : if (r->in.old_val) {
2696 8 : if (blob_old.length) {
2697 8 : if (!r->out.old_val->buf) {
2698 8 : r->out.old_val->buf = talloc_zero(p->mem_ctx, struct lsa_DATA_BUF);
2699 : }
2700 8 : if (!r->out.old_val->buf) {
2701 0 : return NT_STATUS_NO_MEMORY;
2702 : }
2703 :
2704 8 : blob_old_crypt = sess_encrypt_blob(p->mem_ctx, &blob_old,
2705 : &session_key);
2706 8 : if (!blob_old_crypt.length) {
2707 0 : return NT_STATUS_NO_MEMORY;
2708 : }
2709 :
2710 8 : r->out.old_val->buf->data = blob_old_crypt.data;
2711 8 : r->out.old_val->buf->length = blob_old_crypt.length;
2712 8 : r->out.old_val->buf->size = blob_old_crypt.length;
2713 : }
2714 : }
2715 :
2716 428 : if (r->out.new_mtime) {
2717 428 : *r->out.new_mtime = nttime_new;
2718 : }
2719 :
2720 428 : if (r->out.old_mtime) {
2721 8 : *r->out.old_mtime = nttime_old;
2722 : }
2723 :
2724 428 : return NT_STATUS_OK;
2725 : }
2726 :
2727 : /***************************************************************************
2728 : _lsa_DeleteObject
2729 : ***************************************************************************/
2730 :
2731 636 : NTSTATUS _lsa_DeleteObject(struct pipes_struct *p,
2732 : struct lsa_DeleteObject *r)
2733 : {
2734 0 : NTSTATUS status;
2735 636 : struct lsa_info *info = NULL;
2736 :
2737 636 : info = find_policy_by_hnd(p,
2738 : r->in.handle,
2739 : DCESRV_HANDLE_ANY,
2740 : struct lsa_info,
2741 0 : &status);
2742 636 : if (!NT_STATUS_IS_OK(status)) {
2743 0 : return NT_STATUS_INVALID_HANDLE;
2744 : }
2745 :
2746 636 : if (!(info->access & SEC_STD_DELETE)) {
2747 0 : return NT_STATUS_ACCESS_DENIED;
2748 : }
2749 :
2750 636 : switch (info->type) {
2751 4 : case LSA_HANDLE_ACCOUNT_TYPE:
2752 4 : status = privilege_delete_account(&info->sid);
2753 4 : if (!NT_STATUS_IS_OK(status)) {
2754 0 : DEBUG(10,("_lsa_DeleteObject: privilege_delete_account gave: %s\n",
2755 : nt_errstr(status)));
2756 4 : return status;
2757 : }
2758 4 : break;
2759 0 : case LSA_HANDLE_TRUST_TYPE:
2760 0 : if (!pdb_del_trusteddom_pw(info->name)) {
2761 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
2762 : }
2763 0 : status = NT_STATUS_OK;
2764 0 : break;
2765 632 : case LSA_HANDLE_SECRET_TYPE:
2766 632 : status = pdb_delete_secret(info->name);
2767 632 : if (NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_NOT_FOUND)) {
2768 4 : return NT_STATUS_INVALID_HANDLE;
2769 : }
2770 628 : break;
2771 0 : default:
2772 0 : return NT_STATUS_INVALID_HANDLE;
2773 : }
2774 :
2775 632 : close_policy_hnd(p, r->in.handle);
2776 632 : ZERO_STRUCTP(r->out.handle);
2777 :
2778 632 : return status;
2779 : }
2780 :
2781 : /***************************************************************************
2782 : _lsa_EnumPrivs
2783 : ***************************************************************************/
2784 :
2785 2 : NTSTATUS _lsa_EnumPrivs(struct pipes_struct *p,
2786 : struct lsa_EnumPrivs *r)
2787 : {
2788 0 : struct lsa_info *handle;
2789 0 : uint32_t i;
2790 2 : uint32_t enum_context = *r->in.resume_handle;
2791 2 : int num_privs = num_privileges_in_short_list();
2792 2 : struct lsa_PrivEntry *entries = NULL;
2793 0 : NTSTATUS status;
2794 :
2795 : /* remember that the enum_context starts at 0 and not 1 */
2796 :
2797 2 : if ( enum_context >= num_privs )
2798 0 : return NT_STATUS_NO_MORE_ENTRIES;
2799 :
2800 2 : DEBUG(10,("_lsa_EnumPrivs: enum_context:%d total entries:%d\n",
2801 : enum_context, num_privs));
2802 :
2803 2 : handle = find_policy_by_hnd(p,
2804 : r->in.handle,
2805 : LSA_HANDLE_POLICY_TYPE,
2806 : struct lsa_info,
2807 0 : &status);
2808 2 : if (!NT_STATUS_IS_OK(status)) {
2809 0 : return NT_STATUS_INVALID_HANDLE;
2810 : }
2811 :
2812 : /* check if the user has enough rights
2813 : I don't know if it's the right one. not documented. */
2814 :
2815 2 : if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
2816 0 : return NT_STATUS_ACCESS_DENIED;
2817 :
2818 2 : if (num_privs) {
2819 2 : entries = talloc_zero_array(p->mem_ctx, struct lsa_PrivEntry, num_privs);
2820 2 : if (!entries) {
2821 0 : return NT_STATUS_NO_MEMORY;
2822 : }
2823 : } else {
2824 0 : entries = NULL;
2825 : }
2826 :
2827 20 : for (i = 0; i < num_privs; i++) {
2828 18 : if( i < enum_context) {
2829 :
2830 0 : init_lsa_StringLarge(&entries[i].name, NULL);
2831 :
2832 0 : entries[i].luid.low = 0;
2833 0 : entries[i].luid.high = 0;
2834 : } else {
2835 :
2836 18 : init_lsa_StringLarge(&entries[i].name, sec_privilege_name_from_index(i));
2837 :
2838 18 : entries[i].luid.low = sec_privilege_from_index(i);
2839 18 : entries[i].luid.high = 0;
2840 : }
2841 : }
2842 :
2843 2 : enum_context = num_privs;
2844 :
2845 2 : *r->out.resume_handle = enum_context;
2846 2 : r->out.privs->count = num_privs;
2847 2 : r->out.privs->privs = entries;
2848 :
2849 2 : return NT_STATUS_OK;
2850 : }
2851 :
2852 : /***************************************************************************
2853 : _lsa_LookupPrivDisplayName
2854 : ***************************************************************************/
2855 :
2856 18 : NTSTATUS _lsa_LookupPrivDisplayName(struct pipes_struct *p,
2857 : struct lsa_LookupPrivDisplayName *r)
2858 : {
2859 0 : struct lsa_info *handle;
2860 0 : const char *description;
2861 0 : struct lsa_StringLarge *lsa_name;
2862 0 : NTSTATUS status;
2863 :
2864 18 : handle = find_policy_by_hnd(p,
2865 : r->in.handle,
2866 : LSA_HANDLE_POLICY_TYPE,
2867 : struct lsa_info,
2868 0 : &status);
2869 18 : if (!NT_STATUS_IS_OK(status)) {
2870 0 : return NT_STATUS_INVALID_HANDLE;
2871 : }
2872 :
2873 : /* check if the user has enough rights */
2874 :
2875 : /*
2876 : * I don't know if it's the right one. not documented.
2877 : */
2878 18 : if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
2879 0 : return NT_STATUS_ACCESS_DENIED;
2880 :
2881 18 : DEBUG(10,("_lsa_LookupPrivDisplayName: name = %s\n", r->in.name->string));
2882 :
2883 18 : description = get_privilege_dispname(r->in.name->string);
2884 18 : if (!description) {
2885 0 : DEBUG(10,("_lsa_LookupPrivDisplayName: doesn't exist\n"));
2886 0 : return NT_STATUS_NO_SUCH_PRIVILEGE;
2887 : }
2888 :
2889 18 : DEBUG(10,("_lsa_LookupPrivDisplayName: display name = %s\n", description));
2890 :
2891 18 : lsa_name = talloc_zero(p->mem_ctx, struct lsa_StringLarge);
2892 18 : if (!lsa_name) {
2893 0 : return NT_STATUS_NO_MEMORY;
2894 : }
2895 :
2896 18 : init_lsa_StringLarge(lsa_name, description);
2897 :
2898 18 : *r->out.returned_language_id = r->in.language_id;
2899 18 : *r->out.disp_name = lsa_name;
2900 :
2901 18 : return NT_STATUS_OK;
2902 : }
2903 :
2904 : /***************************************************************************
2905 : _lsa_EnumAccounts
2906 : ***************************************************************************/
2907 :
2908 10 : NTSTATUS _lsa_EnumAccounts(struct pipes_struct *p,
2909 : struct lsa_EnumAccounts *r)
2910 : {
2911 0 : struct lsa_info *handle;
2912 0 : struct dom_sid *sid_list;
2913 0 : int i, j, num_entries;
2914 0 : NTSTATUS status;
2915 10 : struct lsa_SidPtr *sids = NULL;
2916 :
2917 10 : handle = find_policy_by_hnd(p,
2918 : r->in.handle,
2919 : LSA_HANDLE_POLICY_TYPE,
2920 : struct lsa_info,
2921 0 : &status);
2922 10 : if (!NT_STATUS_IS_OK(status)) {
2923 0 : return NT_STATUS_INVALID_HANDLE;
2924 : }
2925 :
2926 10 : if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
2927 0 : return NT_STATUS_ACCESS_DENIED;
2928 :
2929 10 : sid_list = NULL;
2930 10 : num_entries = 0;
2931 :
2932 : /* The only way we can currently find out all the SIDs that have been
2933 : privileged is to scan all privileges */
2934 :
2935 10 : status = privilege_enumerate_accounts(&sid_list, &num_entries);
2936 10 : if (!NT_STATUS_IS_OK(status)) {
2937 0 : return status;
2938 : }
2939 :
2940 10 : if (*r->in.resume_handle >= num_entries) {
2941 2 : return NT_STATUS_NO_MORE_ENTRIES;
2942 : }
2943 :
2944 8 : if (num_entries - *r->in.resume_handle) {
2945 8 : sids = talloc_zero_array(p->mem_ctx, struct lsa_SidPtr,
2946 : num_entries - *r->in.resume_handle);
2947 8 : if (!sids) {
2948 0 : talloc_free(sid_list);
2949 0 : return NT_STATUS_NO_MEMORY;
2950 : }
2951 :
2952 60 : for (i = *r->in.resume_handle, j = 0; i < num_entries; i++, j++) {
2953 52 : sids[j].sid = dom_sid_dup(p->mem_ctx, &sid_list[i]);
2954 52 : if (!sids[j].sid) {
2955 0 : talloc_free(sid_list);
2956 0 : return NT_STATUS_NO_MEMORY;
2957 : }
2958 : }
2959 : }
2960 :
2961 8 : talloc_free(sid_list);
2962 :
2963 8 : *r->out.resume_handle = num_entries;
2964 8 : r->out.sids->num_sids = num_entries;
2965 8 : r->out.sids->sids = sids;
2966 :
2967 8 : return NT_STATUS_OK;
2968 : }
2969 :
2970 : /***************************************************************************
2971 : _lsa_GetUserName
2972 : ***************************************************************************/
2973 :
2974 394 : NTSTATUS _lsa_GetUserName(struct pipes_struct *p,
2975 : struct lsa_GetUserName *r)
2976 : {
2977 394 : struct dcesrv_call_state *dce_call = p->dce_call;
2978 0 : struct auth_session_info *session_info =
2979 394 : dcesrv_call_session_info(dce_call);
2980 0 : const char *username, *domname;
2981 394 : struct lsa_String *account_name = NULL;
2982 394 : struct lsa_String *authority_name = NULL;
2983 :
2984 394 : if (p->transport != NCACN_NP && p->transport != NCALRPC) {
2985 0 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
2986 0 : return NT_STATUS_ACCESS_DENIED;
2987 : }
2988 :
2989 394 : if (r->in.account_name &&
2990 394 : *r->in.account_name) {
2991 0 : return NT_STATUS_INVALID_PARAMETER;
2992 : }
2993 :
2994 394 : if (r->in.authority_name &&
2995 384 : *r->in.authority_name) {
2996 0 : return NT_STATUS_INVALID_PARAMETER;
2997 : }
2998 :
2999 394 : if (security_session_user_level(session_info, NULL) < SECURITY_USER) {
3000 : /*
3001 : * I'm 99% sure this is not the right place to do this,
3002 : * global_sid_Anonymous should probably be put into the token
3003 : * instead of the guest id -- vl
3004 : */
3005 142 : if (!lookup_sid(p->mem_ctx, &global_sid_Anonymous,
3006 : &domname, &username, NULL)) {
3007 0 : return NT_STATUS_NO_MEMORY;
3008 : }
3009 : } else {
3010 252 : username = session_info->unix_info->sanitized_username;
3011 252 : domname = session_info->info->domain_name;
3012 : }
3013 :
3014 394 : account_name = talloc(p->mem_ctx, struct lsa_String);
3015 394 : if (!account_name) {
3016 0 : return NT_STATUS_NO_MEMORY;
3017 : }
3018 394 : init_lsa_String(account_name, username);
3019 :
3020 394 : if (r->out.authority_name) {
3021 384 : authority_name = talloc(p->mem_ctx, struct lsa_String);
3022 384 : if (!authority_name) {
3023 0 : return NT_STATUS_NO_MEMORY;
3024 : }
3025 384 : init_lsa_String(authority_name, domname);
3026 : }
3027 :
3028 394 : *r->out.account_name = account_name;
3029 394 : if (r->out.authority_name) {
3030 384 : *r->out.authority_name = authority_name;
3031 : }
3032 :
3033 394 : return NT_STATUS_OK;
3034 : }
3035 :
3036 : /***************************************************************************
3037 : _lsa_CreateAccount
3038 : ***************************************************************************/
3039 :
3040 2 : NTSTATUS _lsa_CreateAccount(struct pipes_struct *p,
3041 : struct lsa_CreateAccount *r)
3042 : {
3043 2 : struct dcesrv_call_state *dce_call = p->dce_call;
3044 0 : struct auth_session_info *session_info =
3045 2 : dcesrv_call_session_info(dce_call);
3046 0 : NTSTATUS status;
3047 0 : struct lsa_info *handle;
3048 0 : uint32_t acc_granted;
3049 0 : struct security_descriptor *psd;
3050 0 : size_t sd_size;
3051 2 : uint32_t owner_access = (LSA_ACCOUNT_ALL_ACCESS &
3052 : ~(LSA_ACCOUNT_ADJUST_PRIVILEGES|
3053 : LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS|
3054 : SEC_STD_DELETE));
3055 :
3056 : /* find the connection policy handle. */
3057 2 : handle = find_policy_by_hnd(p,
3058 : r->in.handle,
3059 : LSA_HANDLE_POLICY_TYPE,
3060 : struct lsa_info,
3061 0 : &status);
3062 2 : if (!NT_STATUS_IS_OK(status)) {
3063 0 : return NT_STATUS_INVALID_HANDLE;
3064 : }
3065 :
3066 : /* check if the user has enough rights */
3067 :
3068 2 : if (!(handle->access & LSA_POLICY_CREATE_ACCOUNT)) {
3069 0 : return NT_STATUS_ACCESS_DENIED;
3070 : }
3071 :
3072 : /* Work out max allowed. */
3073 2 : map_max_allowed_access(session_info->security_token,
3074 2 : session_info->unix_token,
3075 : &r->in.access_mask);
3076 :
3077 : /* map the generic bits to the lsa policy ones */
3078 2 : se_map_generic(&r->in.access_mask, &lsa_account_mapping);
3079 :
3080 2 : status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size,
3081 : &lsa_account_mapping,
3082 : r->in.sid, owner_access);
3083 2 : if (!NT_STATUS_IS_OK(status)) {
3084 0 : return status;
3085 : }
3086 :
3087 2 : status = access_check_object(psd, session_info->security_token,
3088 : SEC_PRIV_INVALID, SEC_PRIV_INVALID, 0, r->in.access_mask,
3089 : &acc_granted, "_lsa_CreateAccount");
3090 2 : if (!NT_STATUS_IS_OK(status)) {
3091 0 : return status;
3092 : }
3093 :
3094 2 : if ( is_privileged_sid( r->in.sid ) )
3095 0 : return NT_STATUS_OBJECT_NAME_COLLISION;
3096 :
3097 2 : status = create_lsa_policy_handle(p->mem_ctx, p,
3098 : LSA_HANDLE_ACCOUNT_TYPE,
3099 : acc_granted,
3100 : r->in.sid,
3101 : NULL,
3102 : psd,
3103 : r->out.acct_handle);
3104 2 : if (!NT_STATUS_IS_OK(status)) {
3105 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
3106 : }
3107 :
3108 2 : return privilege_create_account(r->in.sid);
3109 : }
3110 :
3111 : /***************************************************************************
3112 : _lsa_OpenAccount
3113 : ***************************************************************************/
3114 :
3115 16 : NTSTATUS _lsa_OpenAccount(struct pipes_struct *p,
3116 : struct lsa_OpenAccount *r)
3117 : {
3118 16 : struct dcesrv_call_state *dce_call = p->dce_call;
3119 0 : struct auth_session_info *session_info =
3120 16 : dcesrv_call_session_info(dce_call);
3121 16 : struct security_descriptor *psd = NULL;
3122 0 : size_t sd_size;
3123 16 : uint32_t des_access = r->in.access_mask;
3124 0 : uint32_t acc_granted;
3125 16 : uint32_t owner_access = (LSA_ACCOUNT_ALL_ACCESS &
3126 : ~(LSA_ACCOUNT_ADJUST_PRIVILEGES|
3127 : LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS|
3128 : SEC_STD_DELETE));
3129 0 : NTSTATUS status;
3130 :
3131 : /* find the connection policy handle. */
3132 16 : (void)find_policy_by_hnd(p,
3133 : r->in.handle,
3134 : LSA_HANDLE_POLICY_TYPE,
3135 : struct lsa_info,
3136 0 : &status);
3137 16 : if (!NT_STATUS_IS_OK(status)) {
3138 0 : return NT_STATUS_INVALID_HANDLE;
3139 : }
3140 :
3141 : /* des_access is for the account here, not the policy
3142 : * handle - so don't check against policy handle. */
3143 :
3144 : /* Work out max allowed. */
3145 16 : map_max_allowed_access(session_info->security_token,
3146 16 : session_info->unix_token,
3147 : &des_access);
3148 :
3149 : /* map the generic bits to the lsa account ones */
3150 16 : se_map_generic(&des_access, &lsa_account_mapping);
3151 :
3152 : /* get the generic lsa account SD until we store it */
3153 16 : status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size,
3154 : &lsa_account_mapping,
3155 : r->in.sid, owner_access);
3156 16 : if (!NT_STATUS_IS_OK(status)) {
3157 0 : return status;
3158 : }
3159 :
3160 16 : status = access_check_object(psd, session_info->security_token,
3161 : SEC_PRIV_INVALID, SEC_PRIV_INVALID, 0, des_access,
3162 : &acc_granted, "_lsa_OpenAccount" );
3163 16 : if (!NT_STATUS_IS_OK(status)) {
3164 0 : return status;
3165 : }
3166 :
3167 : /* TODO: Fis the parsing routine before reenabling this check! */
3168 : #if 0
3169 : if (!lookup_sid(&handle->sid, dom_name, name, &type))
3170 : return NT_STATUS_ACCESS_DENIED;
3171 : #endif
3172 :
3173 16 : status = create_lsa_policy_handle(p->mem_ctx, p,
3174 : LSA_HANDLE_ACCOUNT_TYPE,
3175 : acc_granted,
3176 : r->in.sid,
3177 : NULL,
3178 : psd,
3179 : r->out.acct_handle);
3180 16 : if (!NT_STATUS_IS_OK(status)) {
3181 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
3182 : }
3183 :
3184 16 : return NT_STATUS_OK;
3185 : }
3186 :
3187 : /***************************************************************************
3188 : _lsa_EnumPrivsAccount
3189 : For a given SID, enumerate all the privilege this account has.
3190 : ***************************************************************************/
3191 :
3192 28 : NTSTATUS _lsa_EnumPrivsAccount(struct pipes_struct *p,
3193 : struct lsa_EnumPrivsAccount *r)
3194 : {
3195 28 : NTSTATUS status = NT_STATUS_OK;
3196 28 : struct lsa_info *info=NULL;
3197 0 : PRIVILEGE_SET *privileges;
3198 28 : struct lsa_PrivilegeSet *priv_set = NULL;
3199 0 : struct dom_sid_buf buf;
3200 :
3201 : /* find the connection policy handle. */
3202 28 : info = find_policy_by_hnd(p,
3203 : r->in.handle,
3204 : LSA_HANDLE_ACCOUNT_TYPE,
3205 : struct lsa_info,
3206 0 : &status);
3207 28 : if (!NT_STATUS_IS_OK(status)) {
3208 0 : return NT_STATUS_INVALID_HANDLE;
3209 : }
3210 :
3211 28 : if (!(info->access & LSA_ACCOUNT_VIEW))
3212 0 : return NT_STATUS_ACCESS_DENIED;
3213 :
3214 28 : status = get_privileges_for_sid_as_set(p->mem_ctx, &privileges, &info->sid);
3215 28 : if (!NT_STATUS_IS_OK(status)) {
3216 0 : return status;
3217 : }
3218 :
3219 28 : *r->out.privs = priv_set = talloc_zero(p->mem_ctx, struct lsa_PrivilegeSet);
3220 28 : if (!priv_set) {
3221 0 : return NT_STATUS_NO_MEMORY;
3222 : }
3223 :
3224 28 : DEBUG(10,("_lsa_EnumPrivsAccount: %s has %d privileges\n",
3225 : dom_sid_str_buf(&info->sid, &buf),
3226 : privileges->count));
3227 :
3228 28 : priv_set->count = privileges->count;
3229 28 : priv_set->unknown = 0;
3230 28 : priv_set->set = talloc_move(priv_set, &privileges->set);
3231 :
3232 28 : return status;
3233 : }
3234 :
3235 : /***************************************************************************
3236 : _lsa_GetSystemAccessAccount
3237 : ***************************************************************************/
3238 :
3239 16 : NTSTATUS _lsa_GetSystemAccessAccount(struct pipes_struct *p,
3240 : struct lsa_GetSystemAccessAccount *r)
3241 : {
3242 0 : NTSTATUS status;
3243 16 : struct lsa_info *info = NULL;
3244 0 : struct lsa_EnumPrivsAccount e;
3245 0 : struct lsa_PrivilegeSet *privset;
3246 :
3247 : /* find the connection policy handle. */
3248 :
3249 16 : info = find_policy_by_hnd(p,
3250 : r->in.handle,
3251 : LSA_HANDLE_ACCOUNT_TYPE,
3252 : struct lsa_info,
3253 0 : &status);
3254 16 : if (!NT_STATUS_IS_OK(status)) {
3255 0 : return NT_STATUS_INVALID_HANDLE;
3256 : }
3257 :
3258 16 : if (!(info->access & LSA_ACCOUNT_VIEW))
3259 0 : return NT_STATUS_ACCESS_DENIED;
3260 :
3261 16 : privset = talloc_zero(p->mem_ctx, struct lsa_PrivilegeSet);
3262 16 : if (!privset) {
3263 0 : return NT_STATUS_NO_MEMORY;
3264 : }
3265 :
3266 16 : e.in.handle = r->in.handle;
3267 16 : e.out.privs = &privset;
3268 :
3269 16 : status = _lsa_EnumPrivsAccount(p, &e);
3270 16 : if (!NT_STATUS_IS_OK(status)) {
3271 0 : DEBUG(10,("_lsa_GetSystemAccessAccount: "
3272 : "failed to call _lsa_EnumPrivsAccount(): %s\n",
3273 : nt_errstr(status)));
3274 0 : return status;
3275 : }
3276 :
3277 : /* Samba4 would iterate over the privset to merge the policy mode bits,
3278 : * not sure samba3 can do the same here, so just return what we did in
3279 : * the past - gd */
3280 :
3281 : /*
3282 : 0x01 -> Log on locally
3283 : 0x02 -> Access this computer from network
3284 : 0x04 -> Log on as a batch job
3285 : 0x10 -> Log on as a service
3286 :
3287 : they can be ORed together
3288 : */
3289 :
3290 16 : *r->out.access_mask = LSA_POLICY_MODE_INTERACTIVE |
3291 : LSA_POLICY_MODE_NETWORK;
3292 :
3293 16 : return NT_STATUS_OK;
3294 : }
3295 :
3296 : /***************************************************************************
3297 : update the systemaccount information
3298 : ***************************************************************************/
3299 :
3300 0 : NTSTATUS _lsa_SetSystemAccessAccount(struct pipes_struct *p,
3301 : struct lsa_SetSystemAccessAccount *r)
3302 : {
3303 0 : struct lsa_info *info=NULL;
3304 0 : NTSTATUS status;
3305 0 : GROUP_MAP *map;
3306 :
3307 : /* find the connection policy handle. */
3308 0 : info = find_policy_by_hnd(p,
3309 : r->in.handle,
3310 : LSA_HANDLE_ACCOUNT_TYPE,
3311 : struct lsa_info,
3312 0 : &status);
3313 0 : if (!NT_STATUS_IS_OK(status)) {
3314 0 : return NT_STATUS_INVALID_HANDLE;
3315 : }
3316 :
3317 0 : if (!(info->access & LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS)) {
3318 0 : return NT_STATUS_ACCESS_DENIED;
3319 : }
3320 :
3321 0 : map = talloc_zero(p->mem_ctx, GROUP_MAP);
3322 0 : if (!map) {
3323 0 : return NT_STATUS_NO_MEMORY;
3324 : }
3325 :
3326 0 : if (!pdb_getgrsid(map, info->sid)) {
3327 0 : TALLOC_FREE(map);
3328 0 : return NT_STATUS_NO_SUCH_GROUP;
3329 : }
3330 :
3331 0 : status = pdb_update_group_mapping_entry(map);
3332 0 : TALLOC_FREE(map);
3333 0 : return status;
3334 : }
3335 :
3336 : /***************************************************************************
3337 : _lsa_AddPrivilegesToAccount
3338 : For a given SID, add some privileges.
3339 : ***************************************************************************/
3340 :
3341 2 : NTSTATUS _lsa_AddPrivilegesToAccount(struct pipes_struct *p,
3342 : struct lsa_AddPrivilegesToAccount *r)
3343 : {
3344 2 : struct lsa_info *info = NULL;
3345 2 : struct lsa_PrivilegeSet *set = NULL;
3346 0 : NTSTATUS status;
3347 :
3348 : /* find the connection policy handle. */
3349 2 : info = find_policy_by_hnd(p,
3350 : r->in.handle,
3351 : LSA_HANDLE_ACCOUNT_TYPE,
3352 : struct lsa_info,
3353 0 : &status);
3354 2 : if (!NT_STATUS_IS_OK(status)) {
3355 0 : return NT_STATUS_INVALID_HANDLE;
3356 : }
3357 :
3358 2 : if (!(info->access & LSA_ACCOUNT_ADJUST_PRIVILEGES)) {
3359 0 : return NT_STATUS_ACCESS_DENIED;
3360 : }
3361 :
3362 2 : set = r->in.privs;
3363 :
3364 2 : if ( !grant_privilege_set( &info->sid, set ) ) {
3365 0 : struct dom_sid_buf buf;
3366 0 : DEBUG(3,("_lsa_AddPrivilegesToAccount: grant_privilege_set(%s) failed!\n",
3367 : dom_sid_str_buf(&info->sid, &buf)));
3368 0 : return NT_STATUS_NO_SUCH_PRIVILEGE;
3369 : }
3370 :
3371 2 : return NT_STATUS_OK;
3372 : }
3373 :
3374 : /***************************************************************************
3375 : _lsa_RemovePrivilegesFromAccount
3376 : For a given SID, remove some privileges.
3377 : ***************************************************************************/
3378 :
3379 2 : NTSTATUS _lsa_RemovePrivilegesFromAccount(struct pipes_struct *p,
3380 : struct lsa_RemovePrivilegesFromAccount *r)
3381 : {
3382 2 : struct lsa_info *info = NULL;
3383 2 : struct lsa_PrivilegeSet *set = NULL;
3384 0 : NTSTATUS status;
3385 :
3386 : /* find the connection policy handle. */
3387 2 : info = find_policy_by_hnd(p,
3388 : r->in.handle,
3389 : LSA_HANDLE_ACCOUNT_TYPE,
3390 : struct lsa_info,
3391 0 : &status);
3392 2 : if (!NT_STATUS_IS_OK(status)) {
3393 0 : return NT_STATUS_INVALID_HANDLE;
3394 : }
3395 :
3396 2 : if (!(info->access & LSA_ACCOUNT_ADJUST_PRIVILEGES)) {
3397 0 : return NT_STATUS_ACCESS_DENIED;
3398 : }
3399 :
3400 2 : set = r->in.privs;
3401 :
3402 2 : if ( !revoke_privilege_set( &info->sid, set) ) {
3403 0 : struct dom_sid_buf buf;
3404 0 : DEBUG(3,("_lsa_RemovePrivilegesFromAccount: revoke_privilege(%s) failed!\n",
3405 : dom_sid_str_buf(&info->sid, &buf)));
3406 0 : return NT_STATUS_NO_SUCH_PRIVILEGE;
3407 : }
3408 :
3409 2 : return NT_STATUS_OK;
3410 : }
3411 :
3412 : /***************************************************************************
3413 : _lsa_LookupPrivName
3414 : ***************************************************************************/
3415 :
3416 50 : NTSTATUS _lsa_LookupPrivName(struct pipes_struct *p,
3417 : struct lsa_LookupPrivName *r)
3418 : {
3419 50 : struct lsa_info *info = NULL;
3420 0 : const char *name;
3421 0 : struct lsa_StringLarge *lsa_name;
3422 0 : NTSTATUS status;
3423 :
3424 : /* find the connection policy handle. */
3425 50 : info = find_policy_by_hnd(p,
3426 : r->in.handle,
3427 : LSA_HANDLE_POLICY_TYPE,
3428 : struct lsa_info,
3429 0 : &status);
3430 50 : if (!NT_STATUS_IS_OK(status)) {
3431 0 : return NT_STATUS_INVALID_HANDLE;
3432 : }
3433 :
3434 50 : if (!(info->access & LSA_POLICY_VIEW_LOCAL_INFORMATION)) {
3435 0 : return NT_STATUS_ACCESS_DENIED;
3436 : }
3437 :
3438 50 : if (r->in.luid->high != 0) {
3439 0 : return NT_STATUS_NO_SUCH_PRIVILEGE;
3440 : }
3441 :
3442 50 : name = sec_privilege_name(r->in.luid->low);
3443 50 : if (!name) {
3444 0 : return NT_STATUS_NO_SUCH_PRIVILEGE;
3445 : }
3446 :
3447 50 : lsa_name = talloc_zero(p->mem_ctx, struct lsa_StringLarge);
3448 50 : if (!lsa_name) {
3449 0 : return NT_STATUS_NO_MEMORY;
3450 : }
3451 :
3452 50 : lsa_name->string = talloc_strdup(lsa_name, name);
3453 50 : if (!lsa_name->string) {
3454 0 : TALLOC_FREE(lsa_name);
3455 0 : return NT_STATUS_NO_MEMORY;
3456 : }
3457 :
3458 50 : *r->out.name = lsa_name;
3459 :
3460 50 : return NT_STATUS_OK;
3461 : }
3462 :
3463 : /***************************************************************************
3464 : _lsa_QuerySecurity
3465 : ***************************************************************************/
3466 :
3467 12 : NTSTATUS _lsa_QuerySecurity(struct pipes_struct *p,
3468 : struct lsa_QuerySecurity *r)
3469 : {
3470 12 : struct lsa_info *handle=NULL;
3471 12 : struct security_descriptor *psd = NULL;
3472 12 : size_t sd_size = 0;
3473 0 : NTSTATUS status;
3474 :
3475 : /* find the connection policy handle. */
3476 12 : handle = find_policy_by_hnd(p,
3477 : r->in.handle,
3478 : DCESRV_HANDLE_ANY,
3479 : struct lsa_info,
3480 0 : &status);
3481 12 : if (!NT_STATUS_IS_OK(status)) {
3482 0 : return NT_STATUS_INVALID_HANDLE;
3483 : }
3484 :
3485 12 : switch (handle->type) {
3486 12 : case LSA_HANDLE_POLICY_TYPE:
3487 : case LSA_HANDLE_ACCOUNT_TYPE:
3488 : case LSA_HANDLE_TRUST_TYPE:
3489 : case LSA_HANDLE_SECRET_TYPE:
3490 12 : psd = handle->sd;
3491 12 : sd_size = ndr_size_security_descriptor(psd, 0);
3492 12 : status = NT_STATUS_OK;
3493 12 : break;
3494 0 : default:
3495 0 : status = NT_STATUS_INVALID_HANDLE;
3496 0 : break;
3497 : }
3498 :
3499 12 : if (!NT_STATUS_IS_OK(status)) {
3500 0 : return status;
3501 : }
3502 :
3503 12 : *r->out.sdbuf = make_sec_desc_buf(p->mem_ctx, sd_size, psd);
3504 12 : if (!*r->out.sdbuf) {
3505 0 : return NT_STATUS_NO_MEMORY;
3506 : }
3507 :
3508 12 : return status;
3509 : }
3510 :
3511 : /***************************************************************************
3512 : _lsa_AddAccountRights
3513 : ***************************************************************************/
3514 :
3515 26 : NTSTATUS _lsa_AddAccountRights(struct pipes_struct *p,
3516 : struct lsa_AddAccountRights *r)
3517 : {
3518 26 : struct dcesrv_call_state *dce_call = p->dce_call;
3519 0 : struct auth_session_info *session_info =
3520 26 : dcesrv_call_session_info(dce_call);
3521 26 : int i = 0;
3522 26 : uint32_t acc_granted = 0;
3523 26 : struct security_descriptor *psd = NULL;
3524 0 : size_t sd_size;
3525 0 : struct dom_sid sid;
3526 0 : NTSTATUS status;
3527 :
3528 : /* find the connection policy handle. */
3529 26 : (void)find_policy_by_hnd(p,
3530 : r->in.handle,
3531 : LSA_HANDLE_POLICY_TYPE,
3532 : struct lsa_info,
3533 0 : &status);
3534 26 : if (!NT_STATUS_IS_OK(status)) {
3535 0 : return NT_STATUS_INVALID_HANDLE;
3536 : }
3537 :
3538 : /* get the generic lsa account SD for this SID until we store it */
3539 26 : status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size,
3540 : &lsa_account_mapping,
3541 : NULL, 0);
3542 26 : if (!NT_STATUS_IS_OK(status)) {
3543 0 : return status;
3544 : }
3545 :
3546 : /*
3547 : * From the MS DOCs. If the sid doesn't exist, ask for LSA_POLICY_CREATE_ACCOUNT
3548 : * on the policy handle. If it does, ask for
3549 : * LSA_ACCOUNT_ADJUST_PRIVILEGES|LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS|LSA_ACCOUNT_VIEW,
3550 : * on the account sid. We don't check here so just use the latter. JRA.
3551 : */
3552 :
3553 26 : status = access_check_object(psd, session_info->security_token,
3554 : SEC_PRIV_INVALID, SEC_PRIV_INVALID, 0,
3555 : LSA_ACCOUNT_ADJUST_PRIVILEGES|LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS|LSA_ACCOUNT_VIEW,
3556 : &acc_granted, "_lsa_AddAccountRights" );
3557 26 : if (!NT_STATUS_IS_OK(status)) {
3558 0 : return status;
3559 : }
3560 :
3561 : /* according to an NT4 PDC, you can add privileges to SIDs even without
3562 : call_lsa_create_account() first. And you can use any arbitrary SID. */
3563 :
3564 26 : sid_copy( &sid, r->in.sid );
3565 :
3566 50 : for ( i=0; i < r->in.rights->count; i++ ) {
3567 :
3568 26 : const char *privname = r->in.rights->names[i].string;
3569 :
3570 : /* only try to add non-null strings */
3571 :
3572 26 : if ( !privname )
3573 0 : continue;
3574 :
3575 26 : if ( !grant_privilege_by_name( &sid, privname ) ) {
3576 2 : DEBUG(2,("_lsa_AddAccountRights: Failed to add privilege [%s]\n",
3577 : privname ));
3578 2 : return NT_STATUS_NO_SUCH_PRIVILEGE;
3579 : }
3580 : }
3581 :
3582 24 : return NT_STATUS_OK;
3583 : }
3584 :
3585 : /***************************************************************************
3586 : _lsa_RemoveAccountRights
3587 : ***************************************************************************/
3588 :
3589 20 : NTSTATUS _lsa_RemoveAccountRights(struct pipes_struct *p,
3590 : struct lsa_RemoveAccountRights *r)
3591 : {
3592 20 : struct dcesrv_call_state *dce_call = p->dce_call;
3593 0 : struct auth_session_info *session_info =
3594 20 : dcesrv_call_session_info(dce_call);
3595 20 : int i = 0;
3596 20 : struct security_descriptor *psd = NULL;
3597 0 : size_t sd_size;
3598 0 : struct dom_sid sid;
3599 20 : const char *privname = NULL;
3600 20 : uint32_t acc_granted = 0;
3601 0 : NTSTATUS status;
3602 :
3603 : /* find the connection policy handle. */
3604 20 : (void)find_policy_by_hnd(p,
3605 : r->in.handle,
3606 : LSA_HANDLE_POLICY_TYPE,
3607 : struct lsa_info,
3608 0 : &status);
3609 20 : if (!NT_STATUS_IS_OK(status)) {
3610 0 : return NT_STATUS_INVALID_HANDLE;
3611 : }
3612 :
3613 : /* get the generic lsa account SD for this SID until we store it */
3614 20 : status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size,
3615 : &lsa_account_mapping,
3616 : NULL, 0);
3617 20 : if (!NT_STATUS_IS_OK(status)) {
3618 0 : return status;
3619 : }
3620 :
3621 : /*
3622 : * From the MS DOCs. We need
3623 : * LSA_ACCOUNT_ADJUST_PRIVILEGES|LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS|LSA_ACCOUNT_VIEW
3624 : * and DELETE on the account sid.
3625 : */
3626 :
3627 20 : status = access_check_object(psd, session_info->security_token,
3628 : SEC_PRIV_INVALID, SEC_PRIV_INVALID, 0,
3629 : LSA_ACCOUNT_ADJUST_PRIVILEGES|LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS|
3630 : LSA_ACCOUNT_VIEW|SEC_STD_DELETE,
3631 : &acc_granted, "_lsa_RemoveAccountRights");
3632 20 : if (!NT_STATUS_IS_OK(status)) {
3633 0 : return status;
3634 : }
3635 :
3636 20 : sid_copy( &sid, r->in.sid );
3637 :
3638 20 : if ( r->in.remove_all ) {
3639 0 : if ( !revoke_all_privileges( &sid ) )
3640 0 : return NT_STATUS_ACCESS_DENIED;
3641 :
3642 0 : return NT_STATUS_OK;
3643 : }
3644 :
3645 40 : for ( i=0; i < r->in.rights->count; i++ ) {
3646 :
3647 20 : privname = r->in.rights->names[i].string;
3648 :
3649 : /* only try to add non-null strings */
3650 :
3651 20 : if ( !privname )
3652 0 : continue;
3653 :
3654 20 : if ( !revoke_privilege_by_name( &sid, privname ) ) {
3655 0 : DEBUG(2,("_lsa_RemoveAccountRights: Failed to revoke privilege [%s]\n",
3656 : privname ));
3657 0 : return NT_STATUS_NO_SUCH_PRIVILEGE;
3658 : }
3659 : }
3660 :
3661 20 : return NT_STATUS_OK;
3662 : }
3663 :
3664 : /*******************************************************************
3665 : ********************************************************************/
3666 :
3667 16 : static NTSTATUS init_lsa_right_set(TALLOC_CTX *mem_ctx,
3668 : struct lsa_RightSet *r,
3669 : PRIVILEGE_SET *privileges)
3670 : {
3671 0 : uint32_t i;
3672 0 : const char *privname;
3673 16 : const char **privname_array = NULL;
3674 16 : size_t num_priv = 0;
3675 :
3676 70 : for (i=0; i<privileges->count; i++) {
3677 54 : if (privileges->set[i].luid.high) {
3678 0 : continue;
3679 : }
3680 54 : privname = sec_privilege_name(privileges->set[i].luid.low);
3681 54 : if (privname) {
3682 54 : if (!add_string_to_array(mem_ctx, privname,
3683 : &privname_array, &num_priv)) {
3684 0 : return NT_STATUS_NO_MEMORY;
3685 : }
3686 : }
3687 : }
3688 :
3689 16 : if (num_priv) {
3690 :
3691 6 : r->names = talloc_zero_array(mem_ctx, struct lsa_StringLarge,
3692 : num_priv);
3693 6 : if (!r->names) {
3694 0 : return NT_STATUS_NO_MEMORY;
3695 : }
3696 :
3697 60 : for (i=0; i<num_priv; i++) {
3698 54 : init_lsa_StringLarge(&r->names[i], privname_array[i]);
3699 : }
3700 :
3701 6 : r->count = num_priv;
3702 : }
3703 :
3704 16 : return NT_STATUS_OK;
3705 : }
3706 :
3707 : /***************************************************************************
3708 : _lsa_EnumAccountRights
3709 : ***************************************************************************/
3710 :
3711 116 : NTSTATUS _lsa_EnumAccountRights(struct pipes_struct *p,
3712 : struct lsa_EnumAccountRights *r)
3713 : {
3714 0 : NTSTATUS status;
3715 116 : struct lsa_info *info = NULL;
3716 0 : PRIVILEGE_SET *privileges;
3717 0 : struct dom_sid_buf buf;
3718 :
3719 : /* find the connection policy handle. */
3720 :
3721 116 : info = find_policy_by_hnd(p,
3722 : r->in.handle,
3723 : LSA_HANDLE_POLICY_TYPE,
3724 : struct lsa_info,
3725 0 : &status);
3726 116 : if (!NT_STATUS_IS_OK(status)) {
3727 0 : return NT_STATUS_INVALID_HANDLE;
3728 : }
3729 :
3730 116 : if (!(info->access & LSA_ACCOUNT_VIEW)) {
3731 0 : return NT_STATUS_ACCESS_DENIED;
3732 : }
3733 :
3734 : /* according to an NT4 PDC, you can add privileges to SIDs even without
3735 : call_lsa_create_account() first. And you can use any arbitrary SID. */
3736 :
3737 : /* according to MS-LSAD 3.1.4.5.10 it is required to return
3738 : * NT_STATUS_OBJECT_NAME_NOT_FOUND if the account sid was not found in
3739 : * the lsa database */
3740 :
3741 116 : status = get_privileges_for_sid_as_set(p->mem_ctx, &privileges, r->in.sid);
3742 116 : if (!NT_STATUS_IS_OK(status)) {
3743 100 : return status;
3744 : }
3745 :
3746 16 : DEBUG(10,("_lsa_EnumAccountRights: %s has %d privileges\n",
3747 : dom_sid_str_buf(r->in.sid, &buf),
3748 : privileges->count));
3749 :
3750 16 : status = init_lsa_right_set(p->mem_ctx, r->out.rights, privileges);
3751 :
3752 16 : return status;
3753 : }
3754 :
3755 : /***************************************************************************
3756 : _lsa_LookupPrivValue
3757 : ***************************************************************************/
3758 :
3759 20 : NTSTATUS _lsa_LookupPrivValue(struct pipes_struct *p,
3760 : struct lsa_LookupPrivValue *r)
3761 : {
3762 20 : struct lsa_info *info = NULL;
3763 20 : const char *name = NULL;
3764 0 : NTSTATUS status;
3765 :
3766 : /* find the connection policy handle. */
3767 :
3768 20 : info = find_policy_by_hnd(p,
3769 : r->in.handle,
3770 : LSA_HANDLE_POLICY_TYPE,
3771 : struct lsa_info,
3772 0 : &status);
3773 20 : if (!NT_STATUS_IS_OK(status)) {
3774 0 : return NT_STATUS_INVALID_HANDLE;
3775 : }
3776 :
3777 20 : if (!(info->access & LSA_POLICY_LOOKUP_NAMES))
3778 0 : return NT_STATUS_ACCESS_DENIED;
3779 :
3780 20 : name = r->in.name->string;
3781 :
3782 20 : DEBUG(10,("_lsa_lookup_priv_value: name = %s\n", name));
3783 :
3784 20 : r->out.luid->low = sec_privilege_id(name);
3785 20 : r->out.luid->high = 0;
3786 20 : if (r->out.luid->low == SEC_PRIV_INVALID) {
3787 0 : return NT_STATUS_NO_SUCH_PRIVILEGE;
3788 : }
3789 20 : return NT_STATUS_OK;
3790 : }
3791 :
3792 : /***************************************************************************
3793 : _lsa_EnumAccountsWithUserRight
3794 : ***************************************************************************/
3795 :
3796 18 : NTSTATUS _lsa_EnumAccountsWithUserRight(struct pipes_struct *p,
3797 : struct lsa_EnumAccountsWithUserRight *r)
3798 : {
3799 0 : NTSTATUS status;
3800 18 : struct lsa_info *info = NULL;
3801 18 : struct dom_sid *sids = NULL;
3802 18 : int num_sids = 0;
3803 0 : uint32_t i;
3804 0 : enum sec_privilege privilege;
3805 :
3806 18 : info = find_policy_by_hnd(p,
3807 : r->in.handle,
3808 : LSA_HANDLE_POLICY_TYPE,
3809 : struct lsa_info,
3810 0 : &status);
3811 18 : if (!NT_STATUS_IS_OK(status)) {
3812 0 : return NT_STATUS_INVALID_HANDLE;
3813 : }
3814 :
3815 18 : if (!(info->access & LSA_POLICY_LOOKUP_NAMES)) {
3816 0 : return NT_STATUS_ACCESS_DENIED;
3817 : }
3818 :
3819 18 : if (!r->in.name || !r->in.name->string) {
3820 0 : return NT_STATUS_NO_SUCH_PRIVILEGE;
3821 : }
3822 :
3823 18 : privilege = sec_privilege_id(r->in.name->string);
3824 18 : if (privilege == SEC_PRIV_INVALID) {
3825 0 : return NT_STATUS_NO_SUCH_PRIVILEGE;
3826 : }
3827 :
3828 18 : status = privilege_enum_sids(privilege, p->mem_ctx,
3829 : &sids, &num_sids);
3830 18 : if (!NT_STATUS_IS_OK(status)) {
3831 0 : return status;
3832 : }
3833 :
3834 18 : r->out.sids->num_sids = num_sids;
3835 18 : r->out.sids->sids = talloc_array(p->mem_ctx, struct lsa_SidPtr,
3836 : r->out.sids->num_sids);
3837 :
3838 36 : for (i=0; i < r->out.sids->num_sids; i++) {
3839 36 : r->out.sids->sids[i].sid = dom_sid_dup(r->out.sids->sids,
3840 18 : &sids[i]);
3841 18 : if (!r->out.sids->sids[i].sid) {
3842 0 : TALLOC_FREE(r->out.sids->sids);
3843 0 : r->out.sids->num_sids = 0;
3844 0 : return NT_STATUS_NO_MEMORY;
3845 : }
3846 : }
3847 :
3848 18 : return NT_STATUS_OK;
3849 : }
3850 :
3851 : /***************************************************************************
3852 : _lsa_Delete
3853 : ***************************************************************************/
3854 :
3855 8 : NTSTATUS _lsa_Delete(struct pipes_struct *p,
3856 : struct lsa_Delete *r)
3857 : {
3858 8 : return NT_STATUS_NOT_SUPPORTED;
3859 : }
3860 :
3861 0 : static NTSTATUS info_ex_2_pdb_trusted_domain(
3862 : struct lsa_TrustDomainInfoInfoEx *info_ex,
3863 : struct pdb_trusted_domain *td)
3864 : {
3865 0 : if (info_ex->domain_name.string == NULL ||
3866 0 : info_ex->netbios_name.string == NULL ||
3867 0 : info_ex->sid == NULL) {
3868 0 : return NT_STATUS_INVALID_PARAMETER;
3869 : }
3870 :
3871 0 : td->domain_name = talloc_strdup(td, info_ex->domain_name.string);
3872 0 : td->netbios_name = talloc_strdup(td, info_ex->netbios_name.string);
3873 0 : sid_copy(&td->security_identifier, info_ex->sid);
3874 0 : if (td->domain_name == NULL ||
3875 0 : td->netbios_name == NULL ||
3876 0 : is_null_sid(&td->security_identifier)) {
3877 0 : return NT_STATUS_NO_MEMORY;
3878 : }
3879 0 : td->trust_direction = info_ex->trust_direction;
3880 0 : td->trust_type = info_ex->trust_type;
3881 0 : td->trust_attributes = info_ex->trust_attributes;
3882 :
3883 0 : return NT_STATUS_OK;
3884 : }
3885 :
3886 0 : static NTSTATUS setInfoTrustedDomain_base(struct pipes_struct *p,
3887 : TALLOC_CTX *mem_ctx,
3888 : struct lsa_info *policy,
3889 : enum lsa_TrustDomInfoEnum level,
3890 : union lsa_TrustedDomainInfo *info)
3891 : {
3892 0 : struct lsa_TrustDomainInfoAuthInfoInternal *auth_info_int = NULL;
3893 0 : DATA_BLOB auth_blob;
3894 0 : struct trustDomainPasswords auth_struct;
3895 0 : NTSTATUS nt_status;
3896 :
3897 0 : struct pdb_trusted_domain *td;
3898 0 : struct pdb_trusted_domain *orig_td;
3899 :
3900 0 : td = talloc_zero(mem_ctx, struct pdb_trusted_domain);
3901 0 : if (td == NULL) {
3902 0 : return NT_STATUS_NO_MEMORY;
3903 : }
3904 :
3905 0 : switch (level) {
3906 0 : case LSA_TRUSTED_DOMAIN_INFO_POSIX_OFFSET:
3907 0 : if (!(policy->access & LSA_TRUSTED_SET_POSIX)) {
3908 0 : return NT_STATUS_ACCESS_DENIED;
3909 : }
3910 0 : td->trust_posix_offset = &info->posix_offset.posix_offset;
3911 0 : break;
3912 0 : case LSA_TRUSTED_DOMAIN_INFO_INFO_EX:
3913 0 : if (!(policy->access & LSA_TRUSTED_SET_POSIX)) {
3914 0 : return NT_STATUS_ACCESS_DENIED;
3915 : }
3916 0 : nt_status = info_ex_2_pdb_trusted_domain(&info->info_ex, td);
3917 0 : if (!NT_STATUS_IS_OK(nt_status)) {
3918 0 : return nt_status;
3919 : }
3920 0 : break;
3921 0 : case LSA_TRUSTED_DOMAIN_INFO_AUTH_INFO:
3922 0 : if (!(policy->access & LSA_TRUSTED_SET_AUTH)) {
3923 0 : return NT_STATUS_ACCESS_DENIED;
3924 : }
3925 0 : nt_status = auth_info_2_auth_blob(td, &info->auth_info,
3926 : &td->trust_auth_incoming,
3927 : &td->trust_auth_outgoing);
3928 0 : if (!NT_STATUS_IS_OK(nt_status)) {
3929 0 : return nt_status;
3930 : }
3931 0 : break;
3932 0 : case LSA_TRUSTED_DOMAIN_INFO_FULL_INFO:
3933 0 : if (!(policy->access & (LSA_TRUSTED_SET_AUTH | LSA_TRUSTED_SET_POSIX))) {
3934 0 : return NT_STATUS_ACCESS_DENIED;
3935 : }
3936 0 : td->trust_posix_offset = &info->full_info.posix_offset.posix_offset;
3937 0 : nt_status = info_ex_2_pdb_trusted_domain(&info->full_info.info_ex,
3938 : td);
3939 0 : if (!NT_STATUS_IS_OK(nt_status)) {
3940 0 : return nt_status;
3941 : }
3942 0 : nt_status = auth_info_2_auth_blob(td,
3943 : &info->full_info.auth_info,
3944 : &td->trust_auth_incoming,
3945 : &td->trust_auth_outgoing);
3946 0 : if (!NT_STATUS_IS_OK(nt_status)) {
3947 0 : return nt_status;
3948 : }
3949 0 : break;
3950 0 : case LSA_TRUSTED_DOMAIN_INFO_AUTH_INFO_INTERNAL:
3951 0 : if (!(policy->access & LSA_TRUSTED_SET_AUTH)) {
3952 0 : return NT_STATUS_ACCESS_DENIED;
3953 : }
3954 0 : auth_info_int = &info->auth_info_internal;
3955 0 : break;
3956 0 : case LSA_TRUSTED_DOMAIN_INFO_FULL_INFO_INTERNAL:
3957 0 : if (!(policy->access & (LSA_TRUSTED_SET_AUTH | LSA_TRUSTED_SET_POSIX))) {
3958 0 : return NT_STATUS_ACCESS_DENIED;
3959 : }
3960 0 : td->trust_posix_offset = &info->full_info_internal.posix_offset.posix_offset;
3961 0 : nt_status = info_ex_2_pdb_trusted_domain(&info->full_info_internal.info_ex,
3962 : td);
3963 0 : if (!NT_STATUS_IS_OK(nt_status)) {
3964 0 : return nt_status;
3965 : }
3966 0 : auth_info_int = &info->full_info_internal.auth_info;
3967 0 : break;
3968 0 : case LSA_TRUSTED_DOMAIN_SUPPORTED_ENCRYPTION_TYPES:
3969 0 : if (!(policy->access & LSA_TRUSTED_SET_POSIX)) {
3970 0 : return NT_STATUS_ACCESS_DENIED;
3971 : }
3972 0 : td->supported_enc_type = &info->enc_types.enc_types;
3973 0 : break;
3974 0 : default:
3975 0 : return NT_STATUS_INVALID_PARAMETER;
3976 : }
3977 :
3978 : /* decode auth_info_int if set */
3979 0 : if (auth_info_int) {
3980 :
3981 : /* now decrypt blob */
3982 0 : auth_blob = data_blob_const(auth_info_int->auth_blob.data,
3983 0 : auth_info_int->auth_blob.size);
3984 :
3985 0 : nt_status = get_trustdom_auth_blob(p, mem_ctx,
3986 : &auth_blob, &auth_struct);
3987 0 : if (!NT_STATUS_IS_OK(nt_status)) {
3988 0 : return nt_status;
3989 : }
3990 : } else {
3991 0 : memset(&auth_struct, 0, sizeof(auth_struct));
3992 : }
3993 :
3994 : /* TODO: verify only one object matches the dns/netbios/sid triplet and that
3995 : * this is the one we already have */
3996 :
3997 : /* TODO: check if the trust direction is changed and we need to add or remove
3998 : * auth data */
3999 :
4000 : /* TODO: check if trust type shall be changed and return an error in this case
4001 : * */
4002 0 : nt_status = pdb_get_trusted_domain_by_sid(p->mem_ctx, &policy->sid,
4003 : &orig_td);
4004 0 : if (!NT_STATUS_IS_OK(nt_status)) {
4005 0 : return nt_status;
4006 : }
4007 :
4008 :
4009 : /* TODO: should we fetch previous values from the existing entry
4010 : * and append them ? */
4011 0 : if (auth_struct.incoming.count) {
4012 0 : nt_status = get_trustauth_inout_blob(mem_ctx,
4013 : &auth_struct.incoming,
4014 : &td->trust_auth_incoming);
4015 0 : if (!NT_STATUS_IS_OK(nt_status)) {
4016 0 : return nt_status;
4017 : }
4018 : } else {
4019 0 : ZERO_STRUCT(td->trust_auth_incoming);
4020 : }
4021 :
4022 0 : if (auth_struct.outgoing.count) {
4023 0 : nt_status = get_trustauth_inout_blob(mem_ctx,
4024 : &auth_struct.outgoing,
4025 : &td->trust_auth_outgoing);
4026 0 : if (!NT_STATUS_IS_OK(nt_status)) {
4027 0 : return nt_status;
4028 : }
4029 : } else {
4030 0 : ZERO_STRUCT(td->trust_auth_outgoing);
4031 : }
4032 :
4033 0 : nt_status = pdb_set_trusted_domain(orig_td->domain_name, td);
4034 0 : if (!NT_STATUS_IS_OK(nt_status)) {
4035 0 : return nt_status;
4036 : }
4037 :
4038 0 : return NT_STATUS_OK;
4039 : }
4040 :
4041 0 : NTSTATUS _lsa_SetTrustedDomainInfo(struct pipes_struct *p,
4042 : struct lsa_SetTrustedDomainInfo *r)
4043 : {
4044 0 : NTSTATUS status;
4045 0 : struct policy_handle trustdom_handle;
4046 0 : struct lsa_OpenTrustedDomain o;
4047 0 : struct lsa_SetInformationTrustedDomain s;
4048 0 : struct lsa_Close c;
4049 :
4050 0 : o.in.handle = r->in.handle;
4051 0 : o.in.sid = r->in.dom_sid;
4052 0 : o.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
4053 0 : o.out.trustdom_handle = &trustdom_handle;
4054 :
4055 0 : status = _lsa_OpenTrustedDomain(p, &o);
4056 0 : if (!NT_STATUS_IS_OK(status)) {
4057 0 : return status;
4058 : }
4059 :
4060 0 : s.in.trustdom_handle = &trustdom_handle;
4061 0 : s.in.level = r->in.level;
4062 0 : s.in.info = r->in.info;
4063 :
4064 0 : status = _lsa_SetInformationTrustedDomain(p, &s);
4065 0 : if (!NT_STATUS_IS_OK(status)) {
4066 0 : return status;
4067 : }
4068 :
4069 0 : c.in.handle = &trustdom_handle;
4070 0 : c.out.handle = &trustdom_handle;
4071 :
4072 0 : return _lsa_Close(p, &c);
4073 : }
4074 :
4075 0 : NTSTATUS _lsa_SetTrustedDomainInfoByName(struct pipes_struct *p,
4076 : struct lsa_SetTrustedDomainInfoByName *r)
4077 : {
4078 0 : NTSTATUS status;
4079 0 : struct policy_handle trustdom_handle;
4080 0 : struct lsa_OpenTrustedDomainByName o;
4081 0 : struct lsa_SetInformationTrustedDomain s;
4082 0 : struct lsa_Close c;
4083 :
4084 0 : o.in.handle = r->in.handle;
4085 0 : o.in.name.string = r->in.trusted_domain->string;
4086 0 : o.in.access_mask = SEC_FLAG_MAXIMUM_ALLOWED;
4087 0 : o.out.trustdom_handle = &trustdom_handle;
4088 :
4089 0 : status = _lsa_OpenTrustedDomainByName(p, &o);
4090 0 : if (!NT_STATUS_IS_OK(status)) {
4091 0 : if (NT_STATUS_EQUAL(status, NT_STATUS_NO_SUCH_DOMAIN)) {
4092 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
4093 : }
4094 0 : return status;
4095 : }
4096 :
4097 0 : s.in.trustdom_handle = &trustdom_handle;
4098 0 : s.in.level = r->in.level;
4099 0 : s.in.info = r->in.info;
4100 :
4101 0 : status = _lsa_SetInformationTrustedDomain(p, &s);
4102 0 : if (!NT_STATUS_IS_OK(status)) {
4103 0 : return status;
4104 : }
4105 :
4106 0 : c.in.handle = &trustdom_handle;
4107 0 : c.out.handle = &trustdom_handle;
4108 :
4109 0 : return _lsa_Close(p, &c);
4110 : }
4111 :
4112 0 : NTSTATUS _lsa_SetInformationTrustedDomain(struct pipes_struct *p,
4113 : struct lsa_SetInformationTrustedDomain *r)
4114 : {
4115 0 : struct lsa_info *policy;
4116 0 : NTSTATUS status;
4117 :
4118 0 : policy = find_policy_by_hnd(p,
4119 : r->in.trustdom_handle,
4120 : LSA_HANDLE_TRUST_TYPE,
4121 : struct lsa_info,
4122 0 : &status);
4123 0 : if (!NT_STATUS_IS_OK(status)) {
4124 0 : return NT_STATUS_INVALID_HANDLE;
4125 : }
4126 :
4127 0 : return setInfoTrustedDomain_base(p, p->mem_ctx, policy,
4128 : r->in.level, r->in.info);
4129 : }
4130 :
4131 :
4132 : /*
4133 : * From here on the server routines are just dummy ones to make smbd link with
4134 : * librpc/gen_ndr/srv_lsa.c. These routines are actually never called, we are
4135 : * pulling the server stubs across one by one.
4136 : */
4137 :
4138 0 : NTSTATUS _lsa_SetSecObj(struct pipes_struct *p, struct lsa_SetSecObj *r)
4139 : {
4140 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4141 0 : return NT_STATUS_NOT_IMPLEMENTED;
4142 : }
4143 :
4144 0 : NTSTATUS _lsa_ChangePassword(struct pipes_struct *p,
4145 : struct lsa_ChangePassword *r)
4146 : {
4147 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4148 0 : return NT_STATUS_NOT_IMPLEMENTED;
4149 : }
4150 :
4151 0 : NTSTATUS _lsa_SetInfoPolicy(struct pipes_struct *p, struct lsa_SetInfoPolicy *r)
4152 : {
4153 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4154 0 : return NT_STATUS_NOT_IMPLEMENTED;
4155 : }
4156 :
4157 0 : NTSTATUS _lsa_ClearAuditLog(struct pipes_struct *p, struct lsa_ClearAuditLog *r)
4158 : {
4159 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4160 0 : return NT_STATUS_NOT_IMPLEMENTED;
4161 : }
4162 :
4163 0 : NTSTATUS _lsa_GetQuotasForAccount(struct pipes_struct *p,
4164 : struct lsa_GetQuotasForAccount *r)
4165 : {
4166 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4167 0 : return NT_STATUS_NOT_IMPLEMENTED;
4168 : }
4169 :
4170 0 : NTSTATUS _lsa_SetQuotasForAccount(struct pipes_struct *p,
4171 : struct lsa_SetQuotasForAccount *r)
4172 : {
4173 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4174 0 : return NT_STATUS_NOT_IMPLEMENTED;
4175 : }
4176 :
4177 0 : NTSTATUS _lsa_StorePrivateData(struct pipes_struct *p,
4178 : struct lsa_StorePrivateData *r)
4179 : {
4180 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4181 0 : return NT_STATUS_NOT_IMPLEMENTED;
4182 : }
4183 :
4184 0 : NTSTATUS _lsa_RetrievePrivateData(struct pipes_struct *p,
4185 : struct lsa_RetrievePrivateData *r)
4186 : {
4187 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4188 0 : return NT_STATUS_NOT_IMPLEMENTED;
4189 : }
4190 :
4191 0 : NTSTATUS _lsa_SetInfoPolicy2(struct pipes_struct *p,
4192 : struct lsa_SetInfoPolicy2 *r)
4193 : {
4194 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4195 0 : return NT_STATUS_NOT_IMPLEMENTED;
4196 : }
4197 :
4198 0 : NTSTATUS _lsa_EnumTrustedDomainsEx(struct pipes_struct *p,
4199 : struct lsa_EnumTrustedDomainsEx *r)
4200 : {
4201 0 : struct lsa_info *info;
4202 0 : uint32_t count;
4203 0 : struct pdb_trusted_domain **domains;
4204 0 : struct lsa_TrustDomainInfoInfoEx *entries;
4205 0 : int i;
4206 0 : NTSTATUS nt_status;
4207 :
4208 : /* bail out early if pdb backend is not capable of ex trusted domains,
4209 : * if we don't do that, the client might not call
4210 : * _lsa_EnumTrustedDomains() afterwards - gd */
4211 :
4212 0 : if (!(pdb_capabilities() & PDB_CAP_TRUSTED_DOMAINS_EX)) {
4213 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4214 0 : return NT_STATUS_NOT_IMPLEMENTED;
4215 : }
4216 :
4217 0 : info = find_policy_by_hnd(p,
4218 : r->in.handle,
4219 : LSA_HANDLE_POLICY_TYPE,
4220 : struct lsa_info,
4221 0 : &nt_status);
4222 0 : if (!NT_STATUS_IS_OK(nt_status)) {
4223 0 : return NT_STATUS_INVALID_HANDLE;
4224 : }
4225 :
4226 : /* check if the user has enough rights */
4227 0 : if (!(info->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
4228 0 : return NT_STATUS_ACCESS_DENIED;
4229 :
4230 0 : become_root();
4231 0 : nt_status = pdb_enum_trusted_domains(p->mem_ctx, &count, &domains);
4232 0 : unbecome_root();
4233 :
4234 0 : if (!NT_STATUS_IS_OK(nt_status)) {
4235 0 : return nt_status;
4236 : }
4237 :
4238 0 : entries = talloc_zero_array(p->mem_ctx, struct lsa_TrustDomainInfoInfoEx,
4239 : count);
4240 0 : if (!entries) {
4241 0 : return NT_STATUS_NO_MEMORY;
4242 : }
4243 :
4244 0 : for (i=0; i<count; i++) {
4245 0 : init_lsa_StringLarge(&entries[i].domain_name,
4246 0 : domains[i]->domain_name);
4247 0 : init_lsa_StringLarge(&entries[i].netbios_name,
4248 0 : domains[i]->netbios_name);
4249 0 : entries[i].sid = &domains[i]->security_identifier;
4250 0 : entries[i].trust_direction = domains[i]->trust_direction;
4251 0 : entries[i].trust_type = domains[i]->trust_type;
4252 0 : entries[i].trust_attributes = domains[i]->trust_attributes;
4253 : }
4254 :
4255 0 : if (*r->in.resume_handle >= count) {
4256 0 : *r->out.resume_handle = -1;
4257 0 : TALLOC_FREE(entries);
4258 0 : return NT_STATUS_NO_MORE_ENTRIES;
4259 : }
4260 :
4261 : /* return the rest, limit by max_size. Note that we
4262 : use the w2k3 element size value of 60 */
4263 0 : r->out.domains->count = count - *r->in.resume_handle;
4264 0 : r->out.domains->count = MIN(r->out.domains->count,
4265 : (r->in.max_size/LSA_ENUM_TRUST_DOMAIN_EX_MULTIPLIER));
4266 :
4267 0 : r->out.domains->domains = entries + *r->in.resume_handle;
4268 :
4269 0 : if (r->out.domains->count < count - *r->in.resume_handle) {
4270 0 : *r->out.resume_handle = *r->in.resume_handle + r->out.domains->count;
4271 0 : return STATUS_MORE_ENTRIES;
4272 : }
4273 :
4274 : /* according to MS-LSAD 3.1.4.7.8 output resume handle MUST
4275 : * always be larger than the previous input resume handle, in
4276 : * particular when hitting the last query it is vital to set the
4277 : * resume handle correctly to avoid infinite client loops, as
4278 : * seen e.g. with Windows XP SP3 when resume handle is 0 and
4279 : * status is NT_STATUS_OK - gd */
4280 :
4281 0 : *r->out.resume_handle = (uint32_t)-1;
4282 :
4283 0 : return NT_STATUS_OK;
4284 : }
4285 :
4286 0 : NTSTATUS _lsa_QueryDomainInformationPolicy(struct pipes_struct *p,
4287 : struct lsa_QueryDomainInformationPolicy *r)
4288 : {
4289 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4290 0 : return NT_STATUS_NOT_IMPLEMENTED;
4291 : }
4292 :
4293 0 : NTSTATUS _lsa_SetDomainInformationPolicy(struct pipes_struct *p,
4294 : struct lsa_SetDomainInformationPolicy *r)
4295 : {
4296 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4297 0 : return NT_STATUS_NOT_IMPLEMENTED;
4298 : }
4299 :
4300 0 : NTSTATUS _lsa_TestCall(struct pipes_struct *p, struct lsa_TestCall *r)
4301 : {
4302 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4303 0 : return NT_STATUS_NOT_IMPLEMENTED;
4304 : }
4305 :
4306 0 : NTSTATUS _lsa_CREDRWRITE(struct pipes_struct *p, struct lsa_CREDRWRITE *r)
4307 : {
4308 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4309 0 : return NT_STATUS_NOT_IMPLEMENTED;
4310 : }
4311 :
4312 0 : NTSTATUS _lsa_CREDRREAD(struct pipes_struct *p, struct lsa_CREDRREAD *r)
4313 : {
4314 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4315 0 : return NT_STATUS_NOT_IMPLEMENTED;
4316 : }
4317 :
4318 0 : NTSTATUS _lsa_CREDRENUMERATE(struct pipes_struct *p, struct lsa_CREDRENUMERATE *r)
4319 : {
4320 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4321 0 : return NT_STATUS_NOT_IMPLEMENTED;
4322 : }
4323 :
4324 0 : NTSTATUS _lsa_CREDRWRITEDOMAINCREDENTIALS(struct pipes_struct *p,
4325 : struct lsa_CREDRWRITEDOMAINCREDENTIALS *r)
4326 : {
4327 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4328 0 : return NT_STATUS_NOT_IMPLEMENTED;
4329 : }
4330 :
4331 0 : NTSTATUS _lsa_CREDRREADDOMAINCREDENTIALS(struct pipes_struct *p,
4332 : struct lsa_CREDRREADDOMAINCREDENTIALS *r)
4333 : {
4334 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4335 0 : return NT_STATUS_NOT_IMPLEMENTED;
4336 : }
4337 :
4338 0 : NTSTATUS _lsa_CREDRDELETE(struct pipes_struct *p, struct lsa_CREDRDELETE *r)
4339 : {
4340 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4341 0 : return NT_STATUS_NOT_IMPLEMENTED;
4342 : }
4343 :
4344 0 : NTSTATUS _lsa_CREDRGETTARGETINFO(struct pipes_struct *p,
4345 : struct lsa_CREDRGETTARGETINFO *r)
4346 : {
4347 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4348 0 : return NT_STATUS_NOT_IMPLEMENTED;
4349 : }
4350 :
4351 0 : NTSTATUS _lsa_CREDRPROFILELOADED(struct pipes_struct *p,
4352 : struct lsa_CREDRPROFILELOADED *r)
4353 : {
4354 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4355 0 : return NT_STATUS_NOT_IMPLEMENTED;
4356 : }
4357 :
4358 0 : NTSTATUS _lsa_CREDRGETSESSIONTYPES(struct pipes_struct *p,
4359 : struct lsa_CREDRGETSESSIONTYPES *r)
4360 : {
4361 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4362 0 : return NT_STATUS_NOT_IMPLEMENTED;
4363 : }
4364 :
4365 0 : NTSTATUS _lsa_LSARREGISTERAUDITEVENT(struct pipes_struct *p,
4366 : struct lsa_LSARREGISTERAUDITEVENT *r)
4367 : {
4368 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4369 0 : return NT_STATUS_NOT_IMPLEMENTED;
4370 : }
4371 :
4372 0 : NTSTATUS _lsa_LSARGENAUDITEVENT(struct pipes_struct *p,
4373 : struct lsa_LSARGENAUDITEVENT *r)
4374 : {
4375 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4376 0 : return NT_STATUS_NOT_IMPLEMENTED;
4377 : }
4378 :
4379 0 : NTSTATUS _lsa_LSARUNREGISTERAUDITEVENT(struct pipes_struct *p,
4380 : struct lsa_LSARUNREGISTERAUDITEVENT *r)
4381 : {
4382 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4383 0 : return NT_STATUS_NOT_IMPLEMENTED;
4384 : }
4385 :
4386 0 : NTSTATUS _lsa_lsaRQueryForestTrustInformation(struct pipes_struct *p,
4387 : struct lsa_lsaRQueryForestTrustInformation *r)
4388 : {
4389 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4390 0 : return NT_STATUS_NOT_IMPLEMENTED;
4391 : }
4392 :
4393 : #define DNS_CMP_MATCH 0
4394 : #define DNS_CMP_FIRST_IS_CHILD 1
4395 : #define DNS_CMP_SECOND_IS_CHILD 2
4396 : #define DNS_CMP_NO_MATCH 3
4397 :
4398 : /* this function assumes names are well formed DNS names.
4399 : * it doesn't validate them */
4400 0 : static int dns_cmp(const char *s1, size_t l1,
4401 : const char *s2, size_t l2)
4402 : {
4403 0 : const char *p1, *p2;
4404 0 : size_t t1, t2;
4405 0 : int cret;
4406 :
4407 0 : if (l1 == l2) {
4408 0 : if (strcasecmp_m(s1, s2) == 0) {
4409 0 : return DNS_CMP_MATCH;
4410 : }
4411 0 : return DNS_CMP_NO_MATCH;
4412 : }
4413 :
4414 0 : if (l1 > l2) {
4415 0 : p1 = s1;
4416 0 : p2 = s2;
4417 0 : t1 = l1;
4418 0 : t2 = l2;
4419 0 : cret = DNS_CMP_FIRST_IS_CHILD;
4420 : } else {
4421 0 : p1 = s2;
4422 0 : p2 = s1;
4423 0 : t1 = l2;
4424 0 : t2 = l1;
4425 0 : cret = DNS_CMP_SECOND_IS_CHILD;
4426 : }
4427 :
4428 0 : if (p1[t1 - t2 - 1] != '.') {
4429 0 : return DNS_CMP_NO_MATCH;
4430 : }
4431 :
4432 0 : if (strcasecmp_m(&p1[t1 - t2], p2) == 0) {
4433 0 : return cret;
4434 : }
4435 :
4436 0 : return DNS_CMP_NO_MATCH;
4437 : }
4438 :
4439 0 : static NTSTATUS make_ft_info(TALLOC_CTX *mem_ctx,
4440 : struct lsa_ForestTrustInformation *lfti,
4441 : struct ForestTrustInfo *fti)
4442 : {
4443 0 : struct lsa_ForestTrustRecord *lrec;
4444 0 : struct ForestTrustInfoRecord *rec;
4445 0 : struct lsa_StringLarge *tln;
4446 0 : struct lsa_ForestTrustDomainInfo *info;
4447 0 : uint32_t i;
4448 :
4449 0 : fti->version = 1;
4450 0 : fti->count = lfti->count;
4451 0 : fti->records = talloc_array(mem_ctx,
4452 : struct ForestTrustInfoRecordArmor,
4453 : fti->count);
4454 0 : if (!fti->records) {
4455 0 : return NT_STATUS_NO_MEMORY;
4456 : }
4457 0 : for (i = 0; i < fti->count; i++) {
4458 0 : lrec = lfti->entries[i];
4459 0 : rec = &fti->records[i].record;
4460 :
4461 0 : rec->flags = lrec->flags;
4462 0 : rec->timestamp = lrec->time;
4463 0 : rec->type = (enum ForestTrustInfoRecordType)lrec->type;
4464 :
4465 0 : switch (lrec->type) {
4466 0 : case LSA_FOREST_TRUST_TOP_LEVEL_NAME:
4467 : case LSA_FOREST_TRUST_TOP_LEVEL_NAME_EX:
4468 0 : tln = &lrec->forest_trust_data.top_level_name;
4469 0 : rec->data.name.string =
4470 0 : talloc_strdup(mem_ctx, tln->string);
4471 0 : if (!rec->data.name.string) {
4472 0 : return NT_STATUS_NO_MEMORY;
4473 : }
4474 0 : rec->data.name.size = strlen(rec->data.name.string);
4475 0 : break;
4476 0 : case LSA_FOREST_TRUST_DOMAIN_INFO:
4477 0 : info = &lrec->forest_trust_data.domain_info;
4478 0 : rec->data.info.sid = *info->domain_sid;
4479 0 : rec->data.info.dns_name.string =
4480 0 : talloc_strdup(mem_ctx,
4481 : info->dns_domain_name.string);
4482 0 : if (!rec->data.info.dns_name.string) {
4483 0 : return NT_STATUS_NO_MEMORY;
4484 : }
4485 0 : rec->data.info.dns_name.size =
4486 0 : strlen(rec->data.info.dns_name.string);
4487 0 : rec->data.info.netbios_name.string =
4488 0 : talloc_strdup(mem_ctx,
4489 : info->netbios_domain_name.string);
4490 0 : if (!rec->data.info.netbios_name.string) {
4491 0 : return NT_STATUS_NO_MEMORY;
4492 : }
4493 0 : rec->data.info.netbios_name.size =
4494 0 : strlen(rec->data.info.netbios_name.string);
4495 0 : break;
4496 0 : default:
4497 0 : return NT_STATUS_INVALID_DOMAIN_STATE;
4498 : }
4499 : }
4500 :
4501 0 : return NT_STATUS_OK;
4502 : }
4503 :
4504 : static NTSTATUS add_collision(struct lsa_ForestTrustCollisionInfo *c_info,
4505 : uint32_t index, uint32_t collision_type,
4506 : uint32_t conflict_type, const char *tdo_name);
4507 :
4508 0 : static NTSTATUS check_ft_info(TALLOC_CTX *mem_ctx,
4509 : const char *tdo_name,
4510 : struct ForestTrustInfo *tdo_fti,
4511 : struct ForestTrustInfo *new_fti,
4512 : struct lsa_ForestTrustCollisionInfo *c_info)
4513 : {
4514 0 : struct ForestTrustInfoRecord *nrec;
4515 0 : struct ForestTrustInfoRecord *trec;
4516 0 : const char *dns_name;
4517 0 : const char *nb_name = NULL;
4518 0 : struct dom_sid *sid = NULL;
4519 0 : const char *tname = NULL;
4520 0 : size_t dns_len = 0;
4521 0 : size_t tlen = 0;
4522 0 : uint32_t new_fti_idx;
4523 0 : uint32_t i;
4524 : /* use always TDO type, until we understand when Xref can be used */
4525 0 : uint32_t collision_type = LSA_FOREST_TRUST_COLLISION_TDO;
4526 0 : bool tln_conflict;
4527 0 : bool sid_conflict;
4528 0 : bool nb_conflict;
4529 0 : bool exclusion;
4530 0 : bool ex_rule = false;
4531 0 : int ret;
4532 :
4533 0 : for (new_fti_idx = 0; new_fti_idx < new_fti->count; new_fti_idx++) {
4534 :
4535 0 : nrec = &new_fti->records[new_fti_idx].record;
4536 0 : dns_name = NULL;
4537 0 : tln_conflict = false;
4538 0 : sid_conflict = false;
4539 0 : nb_conflict = false;
4540 0 : exclusion = false;
4541 :
4542 0 : switch (nrec->type) {
4543 0 : case LSA_FOREST_TRUST_TOP_LEVEL_NAME_EX:
4544 : /* exclusions do not conflict by definition */
4545 0 : break;
4546 :
4547 0 : case FOREST_TRUST_TOP_LEVEL_NAME:
4548 0 : dns_name = nrec->data.name.string;
4549 0 : dns_len = nrec->data.name.size;
4550 0 : break;
4551 :
4552 0 : case LSA_FOREST_TRUST_DOMAIN_INFO:
4553 0 : dns_name = nrec->data.info.dns_name.string;
4554 0 : dns_len = nrec->data.info.dns_name.size;
4555 0 : nb_name = nrec->data.info.netbios_name.string;
4556 0 : sid = &nrec->data.info.sid;
4557 0 : break;
4558 : }
4559 :
4560 0 : if (!dns_name) continue;
4561 :
4562 : /* check if this is already taken and not excluded */
4563 0 : for (i = 0; i < tdo_fti->count; i++) {
4564 0 : trec = &tdo_fti->records[i].record;
4565 :
4566 0 : switch (trec->type) {
4567 0 : case FOREST_TRUST_TOP_LEVEL_NAME:
4568 0 : ex_rule = false;
4569 0 : tname = trec->data.name.string;
4570 0 : tlen = trec->data.name.size;
4571 0 : break;
4572 0 : case FOREST_TRUST_TOP_LEVEL_NAME_EX:
4573 0 : ex_rule = true;
4574 0 : tname = trec->data.name.string;
4575 0 : tlen = trec->data.name.size;
4576 0 : break;
4577 0 : case FOREST_TRUST_DOMAIN_INFO:
4578 0 : ex_rule = false;
4579 0 : tname = trec->data.info.dns_name.string;
4580 0 : tlen = trec->data.info.dns_name.size;
4581 0 : break;
4582 0 : default:
4583 0 : return NT_STATUS_INVALID_PARAMETER;
4584 : }
4585 0 : ret = dns_cmp(dns_name, dns_len, tname, tlen);
4586 0 : switch (ret) {
4587 0 : case DNS_CMP_MATCH:
4588 : /* if it matches exclusion,
4589 : * it doesn't conflict */
4590 0 : if (ex_rule) {
4591 0 : exclusion = true;
4592 0 : break;
4593 : }
4594 :
4595 0 : FALL_THROUGH;
4596 : case DNS_CMP_FIRST_IS_CHILD:
4597 : case DNS_CMP_SECOND_IS_CHILD:
4598 0 : tln_conflict = true;
4599 :
4600 : FALL_THROUGH;
4601 0 : default:
4602 0 : break;
4603 : }
4604 :
4605 : /* explicit exclusion, no dns name conflict here */
4606 0 : if (exclusion) {
4607 0 : tln_conflict = false;
4608 : }
4609 :
4610 0 : if (trec->type != FOREST_TRUST_DOMAIN_INFO) {
4611 0 : continue;
4612 : }
4613 :
4614 : /* also test for domain info */
4615 0 : if (!(trec->flags & LSA_SID_DISABLED_ADMIN) &&
4616 0 : dom_sid_compare(&trec->data.info.sid, sid) == 0) {
4617 0 : sid_conflict = true;
4618 : }
4619 0 : if (!(trec->flags & LSA_NB_DISABLED_ADMIN) &&
4620 0 : strcasecmp_m(trec->data.info.netbios_name.string,
4621 : nb_name) == 0) {
4622 0 : nb_conflict = true;
4623 : }
4624 : }
4625 :
4626 0 : if (tln_conflict) {
4627 0 : (void)add_collision(c_info, new_fti_idx,
4628 : collision_type,
4629 : LSA_TLN_DISABLED_CONFLICT,
4630 : tdo_name);
4631 : }
4632 0 : if (sid_conflict) {
4633 0 : (void)add_collision(c_info, new_fti_idx,
4634 : collision_type,
4635 : LSA_SID_DISABLED_CONFLICT,
4636 : tdo_name);
4637 : }
4638 0 : if (nb_conflict) {
4639 0 : (void)add_collision(c_info, new_fti_idx,
4640 : collision_type,
4641 : LSA_NB_DISABLED_CONFLICT,
4642 : tdo_name);
4643 : }
4644 : }
4645 :
4646 0 : return NT_STATUS_OK;
4647 : }
4648 :
4649 0 : static NTSTATUS add_collision(struct lsa_ForestTrustCollisionInfo *c_info,
4650 : uint32_t idx, uint32_t collision_type,
4651 : uint32_t conflict_type, const char *tdo_name)
4652 : {
4653 0 : struct lsa_ForestTrustCollisionRecord **es;
4654 0 : uint32_t i = c_info->count;
4655 :
4656 0 : es = talloc_realloc(c_info, c_info->entries,
4657 : struct lsa_ForestTrustCollisionRecord *, i + 1);
4658 0 : if (!es) {
4659 0 : return NT_STATUS_NO_MEMORY;
4660 : }
4661 0 : c_info->entries = es;
4662 0 : c_info->count = i + 1;
4663 :
4664 0 : es[i] = talloc(es, struct lsa_ForestTrustCollisionRecord);
4665 0 : if (!es[i]) {
4666 0 : return NT_STATUS_NO_MEMORY;
4667 : }
4668 :
4669 0 : es[i]->index = idx;
4670 0 : es[i]->type = collision_type;
4671 0 : es[i]->flags = conflict_type;
4672 0 : es[i]->name.string = talloc_strdup(es[i], tdo_name);
4673 0 : if (!es[i]->name.string) {
4674 0 : return NT_STATUS_NO_MEMORY;
4675 : }
4676 0 : es[i]->name.size = strlen(es[i]->name.string);
4677 :
4678 0 : return NT_STATUS_OK;
4679 : }
4680 :
4681 0 : static NTSTATUS get_ft_info(TALLOC_CTX *mem_ctx,
4682 : struct pdb_trusted_domain *td,
4683 : struct ForestTrustInfo *info)
4684 : {
4685 0 : enum ndr_err_code ndr_err;
4686 :
4687 0 : if (td->trust_forest_trust_info.length == 0 ||
4688 0 : td->trust_forest_trust_info.data == NULL) {
4689 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
4690 : }
4691 0 : ndr_err = ndr_pull_struct_blob_all(&td->trust_forest_trust_info, mem_ctx,
4692 : info,
4693 : (ndr_pull_flags_fn_t)ndr_pull_ForestTrustInfo);
4694 0 : if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
4695 0 : return NT_STATUS_INVALID_DOMAIN_STATE;
4696 : }
4697 :
4698 0 : return NT_STATUS_OK;
4699 : }
4700 :
4701 0 : static NTSTATUS own_ft_info(struct pdb_domain_info *dom_info,
4702 : struct ForestTrustInfo *fti)
4703 : {
4704 0 : struct ForestTrustDataDomainInfo *info;
4705 0 : struct ForestTrustInfoRecord *rec;
4706 :
4707 0 : fti->version = 1;
4708 0 : fti->count = 2;
4709 0 : fti->records = talloc_array(fti,
4710 : struct ForestTrustInfoRecordArmor, 2);
4711 0 : if (!fti->records) {
4712 0 : return NT_STATUS_NO_MEMORY;
4713 : }
4714 :
4715 : /* TLN info */
4716 0 : rec = &fti->records[0].record;
4717 :
4718 0 : rec->flags = 0;
4719 0 : rec->timestamp = 0;
4720 0 : rec->type = FOREST_TRUST_TOP_LEVEL_NAME;
4721 :
4722 0 : rec->data.name.string = talloc_strdup(fti, dom_info->dns_forest);
4723 0 : if (!rec->data.name.string) {
4724 0 : return NT_STATUS_NO_MEMORY;
4725 : }
4726 0 : rec->data.name.size = strlen(rec->data.name.string);
4727 :
4728 : /* DOMAIN info */
4729 0 : rec = &fti->records[1].record;
4730 :
4731 0 : rec->flags = 0;
4732 0 : rec->timestamp = 0;
4733 0 : rec->type = FOREST_TRUST_DOMAIN_INFO;
4734 :
4735 0 : info = &rec->data.info;
4736 :
4737 0 : info->sid = dom_info->sid;
4738 0 : info->dns_name.string = talloc_strdup(fti, dom_info->dns_domain);
4739 0 : if (!info->dns_name.string) {
4740 0 : return NT_STATUS_NO_MEMORY;
4741 : }
4742 0 : info->dns_name.size = strlen(info->dns_name.string);
4743 0 : info->netbios_name.string = talloc_strdup(fti, dom_info->name);
4744 0 : if (!info->netbios_name.string) {
4745 0 : return NT_STATUS_NO_MEMORY;
4746 : }
4747 0 : info->netbios_name.size = strlen(info->netbios_name.string);
4748 :
4749 0 : return NT_STATUS_OK;
4750 : }
4751 :
4752 0 : NTSTATUS _lsa_lsaRSetForestTrustInformation(struct pipes_struct *p,
4753 : struct lsa_lsaRSetForestTrustInformation *r)
4754 : {
4755 0 : NTSTATUS status;
4756 0 : int i;
4757 0 : int j;
4758 0 : struct lsa_info *handle;
4759 0 : uint32_t num_domains;
4760 0 : struct pdb_trusted_domain **domains;
4761 0 : struct ForestTrustInfo *nfti;
4762 0 : struct ForestTrustInfo *fti;
4763 0 : struct lsa_ForestTrustCollisionInfo *c_info;
4764 0 : struct pdb_domain_info *dom_info;
4765 0 : enum ndr_err_code ndr_err;
4766 :
4767 0 : if (!IS_DC) {
4768 0 : return NT_STATUS_NOT_SUPPORTED;
4769 : }
4770 :
4771 0 : handle = find_policy_by_hnd(p,
4772 : r->in.handle,
4773 : LSA_HANDLE_TRUST_TYPE,
4774 : struct lsa_info,
4775 0 : &status);
4776 0 : if (!NT_STATUS_IS_OK(status)) {
4777 0 : return NT_STATUS_INVALID_HANDLE;
4778 : }
4779 :
4780 0 : if (!(handle->access & LSA_TRUSTED_SET_AUTH)) {
4781 0 : return NT_STATUS_ACCESS_DENIED;
4782 : }
4783 :
4784 0 : status = pdb_enum_trusted_domains(p->mem_ctx, &num_domains, &domains);
4785 0 : if (!NT_STATUS_IS_OK(status)) {
4786 0 : return status;
4787 : }
4788 0 : if (num_domains == 0) {
4789 0 : return NT_STATUS_NO_SUCH_DOMAIN;
4790 : }
4791 :
4792 0 : for (i = 0; i < num_domains; i++) {
4793 0 : if (domains[i]->domain_name == NULL) {
4794 0 : return NT_STATUS_INVALID_DOMAIN_STATE;
4795 : }
4796 0 : if (strcasecmp_m(domains[i]->domain_name,
4797 0 : r->in.trusted_domain_name->string) == 0) {
4798 0 : break;
4799 : }
4800 : }
4801 0 : if (i >= num_domains) {
4802 0 : return NT_STATUS_NO_SUCH_DOMAIN;
4803 : }
4804 :
4805 0 : if (!(domains[i]->trust_attributes &
4806 : LSA_TRUST_ATTRIBUTE_FOREST_TRANSITIVE)) {
4807 0 : return NT_STATUS_INVALID_PARAMETER;
4808 : }
4809 :
4810 0 : if (r->in.highest_record_type >= LSA_FOREST_TRUST_RECORD_TYPE_LAST) {
4811 0 : return NT_STATUS_INVALID_PARAMETER;
4812 : }
4813 :
4814 : /* The following section until COPY_END is a copy from
4815 : * source4/rpmc_server/lsa/scesrc_lsa.c */
4816 0 : nfti = talloc(p->mem_ctx, struct ForestTrustInfo);
4817 0 : if (!nfti) {
4818 0 : return NT_STATUS_NO_MEMORY;
4819 : }
4820 :
4821 0 : status = make_ft_info(nfti, r->in.forest_trust_info, nfti);
4822 0 : if (!NT_STATUS_IS_OK(status)) {
4823 0 : return status;
4824 : }
4825 :
4826 0 : c_info = talloc_zero(r->out.collision_info,
4827 : struct lsa_ForestTrustCollisionInfo);
4828 0 : if (!c_info) {
4829 0 : return NT_STATUS_NO_MEMORY;
4830 : }
4831 :
4832 : /* first check own info, then other domains */
4833 0 : fti = talloc(p->mem_ctx, struct ForestTrustInfo);
4834 0 : if (!fti) {
4835 0 : return NT_STATUS_NO_MEMORY;
4836 : }
4837 :
4838 0 : dom_info = pdb_get_domain_info(p->mem_ctx);
4839 :
4840 0 : status = own_ft_info(dom_info, fti);
4841 0 : if (!NT_STATUS_IS_OK(status)) {
4842 0 : return status;
4843 : }
4844 :
4845 0 : status = check_ft_info(c_info, dom_info->dns_domain, fti, nfti, c_info);
4846 0 : if (!NT_STATUS_IS_OK(status)) {
4847 0 : return status;
4848 : }
4849 :
4850 0 : for (j = 0; j < num_domains; j++) {
4851 0 : fti = talloc(p->mem_ctx, struct ForestTrustInfo);
4852 0 : if (!fti) {
4853 0 : return NT_STATUS_NO_MEMORY;
4854 : }
4855 :
4856 0 : status = get_ft_info(p->mem_ctx, domains[j], fti);
4857 0 : if (!NT_STATUS_IS_OK(status)) {
4858 0 : if (NT_STATUS_EQUAL(status,
4859 : NT_STATUS_OBJECT_NAME_NOT_FOUND)) {
4860 0 : continue;
4861 : }
4862 0 : return status;
4863 : }
4864 :
4865 0 : if (domains[j]->domain_name == NULL) {
4866 0 : return NT_STATUS_INVALID_DOMAIN_STATE;
4867 : }
4868 :
4869 0 : status = check_ft_info(c_info, domains[j]->domain_name,
4870 : fti, nfti, c_info);
4871 0 : if (!NT_STATUS_IS_OK(status)) {
4872 0 : return status;
4873 : }
4874 : }
4875 :
4876 0 : if (c_info->count != 0) {
4877 0 : *r->out.collision_info = c_info;
4878 : }
4879 :
4880 0 : if (r->in.check_only != 0) {
4881 0 : return NT_STATUS_OK;
4882 : }
4883 :
4884 : /* COPY_END */
4885 :
4886 0 : ndr_err = ndr_push_struct_blob(&domains[i]->trust_forest_trust_info,
4887 : p->mem_ctx, nfti,
4888 : (ndr_push_flags_fn_t)ndr_push_ForestTrustInfo);
4889 0 : if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
4890 0 : return NT_STATUS_INVALID_PARAMETER;
4891 : }
4892 :
4893 0 : status = pdb_set_trusted_domain(domains[i]->domain_name, domains[i]);
4894 0 : if (!NT_STATUS_IS_OK(status)) {
4895 0 : return status;
4896 : }
4897 :
4898 0 : return NT_STATUS_OK;
4899 : }
4900 :
4901 0 : NTSTATUS _lsa_CREDRRENAME(struct pipes_struct *p,
4902 : struct lsa_CREDRRENAME *r)
4903 : {
4904 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4905 0 : return NT_STATUS_NOT_IMPLEMENTED;
4906 : }
4907 :
4908 0 : NTSTATUS _lsa_LSAROPENPOLICYSCE(struct pipes_struct *p,
4909 : struct lsa_LSAROPENPOLICYSCE *r)
4910 : {
4911 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4912 0 : return NT_STATUS_NOT_IMPLEMENTED;
4913 : }
4914 :
4915 0 : NTSTATUS _lsa_LSARADTREGISTERSECURITYEVENTSOURCE(struct pipes_struct *p,
4916 : struct lsa_LSARADTREGISTERSECURITYEVENTSOURCE *r)
4917 : {
4918 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4919 0 : return NT_STATUS_NOT_IMPLEMENTED;
4920 : }
4921 :
4922 0 : NTSTATUS _lsa_LSARADTUNREGISTERSECURITYEVENTSOURCE(struct pipes_struct *p,
4923 : struct lsa_LSARADTUNREGISTERSECURITYEVENTSOURCE *r)
4924 : {
4925 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4926 0 : return NT_STATUS_NOT_IMPLEMENTED;
4927 : }
4928 :
4929 0 : NTSTATUS _lsa_LSARADTREPORTSECURITYEVENT(struct pipes_struct *p,
4930 : struct lsa_LSARADTREPORTSECURITYEVENT *r)
4931 : {
4932 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4933 0 : return NT_STATUS_NOT_IMPLEMENTED;
4934 : }
4935 :
4936 0 : void _lsa_Opnum82NotUsedOnWire(struct pipes_struct *p,
4937 : struct lsa_Opnum82NotUsedOnWire *r)
4938 : {
4939 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4940 0 : }
4941 :
4942 0 : void _lsa_Opnum83NotUsedOnWire(struct pipes_struct *p,
4943 : struct lsa_Opnum83NotUsedOnWire *r)
4944 : {
4945 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4946 0 : }
4947 :
4948 0 : void _lsa_Opnum84NotUsedOnWire(struct pipes_struct *p,
4949 : struct lsa_Opnum84NotUsedOnWire *r)
4950 : {
4951 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4952 0 : }
4953 :
4954 0 : void _lsa_Opnum85NotUsedOnWire(struct pipes_struct *p,
4955 : struct lsa_Opnum85NotUsedOnWire *r)
4956 : {
4957 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4958 0 : }
4959 :
4960 0 : void _lsa_Opnum86NotUsedOnWire(struct pipes_struct *p,
4961 : struct lsa_Opnum86NotUsedOnWire *r)
4962 : {
4963 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4964 0 : }
4965 :
4966 0 : void _lsa_Opnum87NotUsedOnWire(struct pipes_struct *p,
4967 : struct lsa_Opnum87NotUsedOnWire *r)
4968 : {
4969 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4970 0 : }
4971 :
4972 0 : void _lsa_Opnum88NotUsedOnWire(struct pipes_struct *p,
4973 : struct lsa_Opnum88NotUsedOnWire *r)
4974 : {
4975 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4976 0 : }
4977 :
4978 0 : void _lsa_Opnum89NotUsedOnWire(struct pipes_struct *p,
4979 : struct lsa_Opnum89NotUsedOnWire *r)
4980 : {
4981 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4982 0 : }
4983 :
4984 0 : void _lsa_Opnum90NotUsedOnWire(struct pipes_struct *p,
4985 : struct lsa_Opnum90NotUsedOnWire *r)
4986 : {
4987 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4988 0 : }
4989 :
4990 0 : void _lsa_Opnum91NotUsedOnWire(struct pipes_struct *p,
4991 : struct lsa_Opnum91NotUsedOnWire *r)
4992 : {
4993 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
4994 0 : }
4995 :
4996 0 : void _lsa_Opnum92NotUsedOnWire(struct pipes_struct *p,
4997 : struct lsa_Opnum92NotUsedOnWire *r)
4998 : {
4999 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5000 0 : }
5001 :
5002 0 : void _lsa_Opnum93NotUsedOnWire(struct pipes_struct *p,
5003 : struct lsa_Opnum93NotUsedOnWire *r)
5004 : {
5005 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5006 0 : }
5007 :
5008 0 : void _lsa_Opnum94NotUsedOnWire(struct pipes_struct *p,
5009 : struct lsa_Opnum94NotUsedOnWire *r)
5010 : {
5011 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5012 0 : }
5013 :
5014 0 : void _lsa_Opnum95NotUsedOnWire(struct pipes_struct *p,
5015 : struct lsa_Opnum95NotUsedOnWire *r)
5016 : {
5017 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5018 0 : }
5019 :
5020 0 : void _lsa_Opnum96NotUsedOnWire(struct pipes_struct *p,
5021 : struct lsa_Opnum96NotUsedOnWire *r)
5022 : {
5023 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5024 0 : }
5025 :
5026 0 : void _lsa_Opnum97NotUsedOnWire(struct pipes_struct *p,
5027 : struct lsa_Opnum97NotUsedOnWire *r)
5028 : {
5029 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5030 0 : }
5031 :
5032 0 : void _lsa_Opnum98NotUsedOnWire(struct pipes_struct *p,
5033 : struct lsa_Opnum98NotUsedOnWire *r)
5034 : {
5035 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5036 0 : }
5037 :
5038 0 : void _lsa_Opnum99NotUsedOnWire(struct pipes_struct *p,
5039 : struct lsa_Opnum99NotUsedOnWire *r)
5040 : {
5041 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5042 0 : }
5043 :
5044 0 : void _lsa_Opnum100NotUsedOnWire(struct pipes_struct *p,
5045 : struct lsa_Opnum100NotUsedOnWire *r)
5046 : {
5047 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5048 0 : }
5049 :
5050 0 : void _lsa_Opnum101NotUsedOnWire(struct pipes_struct *p,
5051 : struct lsa_Opnum101NotUsedOnWire *r)
5052 : {
5053 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5054 0 : }
5055 :
5056 0 : void _lsa_Opnum102NotUsedOnWire(struct pipes_struct *p,
5057 : struct lsa_Opnum102NotUsedOnWire *r)
5058 : {
5059 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5060 0 : }
5061 :
5062 0 : void _lsa_Opnum103NotUsedOnWire(struct pipes_struct *p,
5063 : struct lsa_Opnum103NotUsedOnWire *r)
5064 : {
5065 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5066 0 : }
5067 :
5068 0 : void _lsa_Opnum104NotUsedOnWire(struct pipes_struct *p,
5069 : struct lsa_Opnum104NotUsedOnWire *r)
5070 : {
5071 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5072 0 : }
5073 :
5074 0 : void _lsa_Opnum105NotUsedOnWire(struct pipes_struct *p,
5075 : struct lsa_Opnum105NotUsedOnWire *r)
5076 : {
5077 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5078 0 : }
5079 :
5080 0 : void _lsa_Opnum106NotUsedOnWire(struct pipes_struct *p,
5081 : struct lsa_Opnum106NotUsedOnWire *r)
5082 : {
5083 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5084 0 : }
5085 :
5086 0 : void _lsa_Opnum107NotUsedOnWire(struct pipes_struct *p,
5087 : struct lsa_Opnum107NotUsedOnWire *r)
5088 : {
5089 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5090 0 : }
5091 :
5092 0 : void _lsa_Opnum108NotUsedOnWire(struct pipes_struct *p,
5093 : struct lsa_Opnum108NotUsedOnWire *r)
5094 : {
5095 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5096 0 : }
5097 :
5098 0 : void _lsa_Opnum109NotUsedOnWire(struct pipes_struct *p,
5099 : struct lsa_Opnum109NotUsedOnWire *r)
5100 : {
5101 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5102 0 : }
5103 :
5104 0 : void _lsa_Opnum110NotUsedOnWire(struct pipes_struct *p,
5105 : struct lsa_Opnum110NotUsedOnWire *r)
5106 : {
5107 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5108 0 : }
5109 :
5110 0 : void _lsa_Opnum111NotUsedOnWire(struct pipes_struct *p,
5111 : struct lsa_Opnum111NotUsedOnWire *r)
5112 : {
5113 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5114 0 : }
5115 :
5116 0 : void _lsa_Opnum112NotUsedOnWire(struct pipes_struct *p,
5117 : struct lsa_Opnum112NotUsedOnWire *r)
5118 : {
5119 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5120 0 : }
5121 :
5122 0 : void _lsa_Opnum113NotUsedOnWire(struct pipes_struct *p,
5123 : struct lsa_Opnum113NotUsedOnWire *r)
5124 : {
5125 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5126 0 : }
5127 :
5128 0 : void _lsa_Opnum114NotUsedOnWire(struct pipes_struct *p,
5129 : struct lsa_Opnum114NotUsedOnWire *r)
5130 : {
5131 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5132 0 : }
5133 :
5134 0 : void _lsa_Opnum115NotUsedOnWire(struct pipes_struct *p,
5135 : struct lsa_Opnum115NotUsedOnWire *r)
5136 : {
5137 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5138 0 : }
5139 :
5140 0 : void _lsa_Opnum116NotUsedOnWire(struct pipes_struct *p,
5141 : struct lsa_Opnum116NotUsedOnWire *r)
5142 : {
5143 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5144 0 : }
5145 :
5146 0 : void _lsa_Opnum117NotUsedOnWire(struct pipes_struct *p,
5147 : struct lsa_Opnum117NotUsedOnWire *r)
5148 : {
5149 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5150 0 : }
5151 :
5152 0 : void _lsa_Opnum118NotUsedOnWire(struct pipes_struct *p,
5153 : struct lsa_Opnum118NotUsedOnWire *r)
5154 : {
5155 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5156 0 : }
5157 :
5158 0 : void _lsa_Opnum119NotUsedOnWire(struct pipes_struct *p,
5159 : struct lsa_Opnum119NotUsedOnWire *r)
5160 : {
5161 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5162 0 : }
5163 :
5164 0 : void _lsa_Opnum120NotUsedOnWire(struct pipes_struct *p,
5165 : struct lsa_Opnum120NotUsedOnWire *r)
5166 : {
5167 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5168 0 : }
5169 :
5170 0 : void _lsa_Opnum121NotUsedOnWire(struct pipes_struct *p,
5171 : struct lsa_Opnum121NotUsedOnWire *r)
5172 : {
5173 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5174 0 : }
5175 :
5176 0 : void _lsa_Opnum122NotUsedOnWire(struct pipes_struct *p,
5177 : struct lsa_Opnum122NotUsedOnWire *r)
5178 : {
5179 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5180 0 : }
5181 :
5182 0 : void _lsa_Opnum123NotUsedOnWire(struct pipes_struct *p,
5183 : struct lsa_Opnum123NotUsedOnWire *r)
5184 : {
5185 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5186 0 : }
5187 :
5188 0 : void _lsa_Opnum124NotUsedOnWire(struct pipes_struct *p,
5189 : struct lsa_Opnum124NotUsedOnWire *r)
5190 : {
5191 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5192 0 : }
5193 :
5194 0 : void _lsa_Opnum125NotUsedOnWire(struct pipes_struct *p,
5195 : struct lsa_Opnum125NotUsedOnWire *r)
5196 : {
5197 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5198 0 : }
5199 :
5200 0 : void _lsa_Opnum126NotUsedOnWire(struct pipes_struct *p,
5201 : struct lsa_Opnum126NotUsedOnWire *r)
5202 : {
5203 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5204 0 : }
5205 :
5206 0 : void _lsa_Opnum127NotUsedOnWire(struct pipes_struct *p,
5207 : struct lsa_Opnum127NotUsedOnWire *r)
5208 : {
5209 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5210 0 : }
5211 :
5212 0 : void _lsa_Opnum128NotUsedOnWire(struct pipes_struct *p,
5213 : struct lsa_Opnum128NotUsedOnWire *r)
5214 : {
5215 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5216 0 : }
5217 :
5218 : /***************************************************************************
5219 : _lsa_CreateTrustedDomainEx3
5220 : ***************************************************************************/
5221 :
5222 0 : NTSTATUS _lsa_CreateTrustedDomainEx3(struct pipes_struct *p,
5223 : struct lsa_CreateTrustedDomainEx3 *r)
5224 : {
5225 0 : struct dcesrv_call_state *dce_call = p->dce_call;
5226 0 : struct auth_session_info *session_info =
5227 0 : dcesrv_call_session_info(dce_call);
5228 0 : struct lsa_info *policy;
5229 0 : NTSTATUS status;
5230 0 : struct trustDomainPasswords auth_struct = {
5231 : .incoming_size = 0,
5232 : };
5233 :
5234 0 : if (!IS_DC) {
5235 0 : return NT_STATUS_NOT_SUPPORTED;
5236 : }
5237 :
5238 0 : policy = find_policy_by_hnd(p,
5239 : r->in.policy_handle,
5240 : LSA_HANDLE_POLICY_TYPE,
5241 : struct lsa_info,
5242 0 : &status);
5243 0 : if (!NT_STATUS_IS_OK(status)) {
5244 0 : return NT_STATUS_INVALID_HANDLE;
5245 : }
5246 :
5247 0 : status = lsa_CreateTrustedDomain_precheck(p->mem_ctx,
5248 : policy,
5249 : session_info,
5250 : r->in.info);
5251 0 : if (!NT_STATUS_IS_OK(status)) {
5252 0 : return status;
5253 : }
5254 :
5255 :
5256 0 : status = get_trustdom_auth_blob_aes(dce_call,
5257 : p->mem_ctx,
5258 : r->in.auth_info_internal,
5259 : &auth_struct);
5260 0 : if (!NT_STATUS_IS_OK(status)) {
5261 0 : return NT_STATUS_UNSUCCESSFUL;
5262 : }
5263 :
5264 0 : status = lsa_CreateTrustedDomain_common(p,
5265 : p->mem_ctx,
5266 : session_info,
5267 : policy,
5268 : r->in.access_mask,
5269 : r->in.info,
5270 : &auth_struct,
5271 : &r->out.trustdom_handle);
5272 0 : if (!NT_STATUS_IS_OK(status)) {
5273 0 : return status;
5274 : }
5275 :
5276 0 : return NT_STATUS_OK;
5277 : }
5278 :
5279 : /***************************************************************************
5280 : _lsa_OpenPolicy3
5281 : ***************************************************************************/
5282 :
5283 68 : NTSTATUS _lsa_OpenPolicy3(struct pipes_struct *p,
5284 : struct lsa_OpenPolicy3 *r)
5285 : {
5286 68 : struct dcesrv_call_state *dce_call = p->dce_call;
5287 0 : struct auth_session_info *session_info =
5288 68 : dcesrv_call_session_info(dce_call);
5289 68 : struct security_descriptor *psd = NULL;
5290 0 : size_t sd_size;
5291 68 : uint32_t des_access = r->in.access_mask;
5292 0 : uint32_t acc_granted;
5293 0 : NTSTATUS status;
5294 :
5295 68 : if (p->transport != NCACN_NP && p->transport != NCALRPC) {
5296 2 : p->fault_state = DCERPC_FAULT_ACCESS_DENIED;
5297 2 : return NT_STATUS_ACCESS_DENIED;
5298 : }
5299 :
5300 66 : ZERO_STRUCTP(r->out.handle);
5301 :
5302 : /*
5303 : * The attributes have no effect and MUST be ignored, except the
5304 : * root_dir which MUST be NULL.
5305 : */
5306 66 : if (r->in.attr != NULL && r->in.attr->root_dir != NULL) {
5307 0 : return NT_STATUS_INVALID_PARAMETER;
5308 : }
5309 :
5310 66 : switch (r->in.in_version) {
5311 66 : case 1:
5312 66 : *r->out.out_version = 1;
5313 :
5314 66 : r->out.out_revision_info->info1.revision = 1;
5315 : /* TODO: Enable as soon as we support it */
5316 : #if 0
5317 : r->out.out_revision_info->info1.supported_features =
5318 : LSA_FEATURE_TDO_AUTH_INFO_AES_CIPHER;
5319 : #endif
5320 :
5321 66 : break;
5322 0 : default:
5323 0 : return NT_STATUS_NOT_SUPPORTED;
5324 : }
5325 :
5326 : /* Work out max allowed. */
5327 66 : map_max_allowed_access(session_info->security_token,
5328 66 : session_info->unix_token,
5329 : &des_access);
5330 :
5331 : /* map the generic bits to the lsa policy ones */
5332 66 : se_map_generic(&des_access, &lsa_policy_mapping);
5333 :
5334 : /* get the generic lsa policy SD until we store it */
5335 66 : status = make_lsa_object_sd(p->mem_ctx,
5336 : &psd,
5337 : &sd_size,
5338 : &lsa_policy_mapping,
5339 : NULL,
5340 : 0);
5341 66 : if (!NT_STATUS_IS_OK(status)) {
5342 0 : return status;
5343 : }
5344 :
5345 66 : status = access_check_object(psd,
5346 : session_info->security_token,
5347 : SEC_PRIV_INVALID,
5348 : SEC_PRIV_INVALID,
5349 : 0,
5350 : des_access,
5351 : &acc_granted,
5352 : "_lsa_OpenPolicy2");
5353 66 : if (!NT_STATUS_IS_OK(status)) {
5354 0 : return status;
5355 : }
5356 :
5357 66 : status = create_lsa_policy_handle(p->mem_ctx,
5358 : p,
5359 : LSA_HANDLE_POLICY_TYPE,
5360 : acc_granted,
5361 : get_global_sam_sid(),
5362 : NULL,
5363 : psd,
5364 : r->out.handle);
5365 66 : if (!NT_STATUS_IS_OK(status)) {
5366 0 : return NT_STATUS_OBJECT_NAME_NOT_FOUND;
5367 : }
5368 :
5369 66 : return NT_STATUS_OK;
5370 : }
5371 :
5372 0 : void _lsa_Opnum131NotUsedOnWire(struct pipes_struct *p,
5373 : struct lsa_Opnum131NotUsedOnWire *r)
5374 : {
5375 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5376 0 : }
5377 :
5378 0 : NTSTATUS _lsa_lsaRQueryForestTrustInformation2(struct pipes_struct *p,
5379 : struct lsa_lsaRQueryForestTrustInformation2 *r)
5380 : {
5381 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5382 0 : return NT_STATUS_NOT_IMPLEMENTED;
5383 : }
5384 :
5385 0 : NTSTATUS _lsa_lsaRSetForestTrustInformation2(struct pipes_struct *p,
5386 : struct lsa_lsaRSetForestTrustInformation2 *r)
5387 : {
5388 0 : p->fault_state = DCERPC_FAULT_OP_RNG_ERROR;
5389 0 : return NT_STATUS_NOT_IMPLEMENTED;
5390 : }
5391 :
5392 : #include "librpc/rpc/dcesrv_core.h"
5393 :
5394 : #define DCESRV_INTERFACE_LSARPC_BIND(context, iface) \
5395 : dcesrv_interface_lsarpc_bind(context, iface)
5396 :
5397 2794 : static NTSTATUS dcesrv_interface_lsarpc_bind(
5398 : struct dcesrv_connection_context *context,
5399 : const struct dcesrv_interface *iface)
5400 : {
5401 2794 : return dcesrv_interface_bind_reject_connect(context, iface);
5402 : }
5403 :
5404 : static NTSTATUS lsarpc__op_init_server(struct dcesrv_context *dce_ctx,
5405 : const struct dcesrv_endpoint_server *ep_server);
5406 : static const struct dcesrv_interface dcesrv_lsarpc_interface;
5407 :
5408 : #define NCACN_NP_PIPE_NETLOGON "ncacn_np:[\\pipe\\netlogon]"
5409 : #define NCACN_NP_PIPE_LSASS "ncacn_np:[\\pipe\\lsass]"
5410 :
5411 : #define DCESRV_INTERFACE_LSARPC_NCACN_NP_SECONDARY_ENDPOINT \
5412 : NCACN_NP_PIPE_LSASS
5413 :
5414 : #define DCESRV_INTERFACE_LSARPC_INIT_SERVER \
5415 : dcesrv_interface_lsarpc_init_server
5416 :
5417 215 : static NTSTATUS dcesrv_interface_lsarpc_init_server(
5418 : struct dcesrv_context *dce_ctx,
5419 : const struct dcesrv_endpoint_server *ep_server)
5420 : {
5421 215 : NTSTATUS ret = dcesrv_interface_register(dce_ctx,
5422 : NCACN_NP_PIPE_NETLOGON,
5423 : NCACN_NP_PIPE_LSASS,
5424 : &dcesrv_lsarpc_interface,
5425 : NULL);
5426 215 : if (!NT_STATUS_IS_OK(ret)) {
5427 0 : DBG_ERR("Failed to register endpoint "
5428 : "'\\pipe\\netlogon'\n");
5429 0 : return ret;
5430 : }
5431 :
5432 215 : return lsarpc__op_init_server(dce_ctx, ep_server);
5433 : }
5434 :
5435 : /* include the generated boilerplate */
5436 : #include "librpc/gen_ndr/ndr_lsa_scompat.c"
|