c62991ee01a767a118e724437f9e1c12c5a1dcdb
[ira/wip.git] / source3 / rpc_server / srv_lsa_nt.c
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  *
15  *  This program is free software; you can redistribute it and/or modify
16  *  it under the terms of the GNU General Public License as published by
17  *  the Free Software Foundation; either version 3 of the License, or
18  *  (at your option) any later version.
19  *
20  *  This program is distributed in the hope that it will be useful,
21  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
22  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
23  *  GNU General Public License for more details.
24  *
25  *  You should have received a copy of the GNU General Public License
26  *  along with this program; if not, see <http://www.gnu.org/licenses/>.
27  */
28
29 /* This is the implementation of the lsa server code. */
30
31 #include "includes.h"
32
33 #undef DBGC_CLASS
34 #define DBGC_CLASS DBGC_RPC_SRV
35
36 #define MAX_LOOKUP_SIDS 0x5000 /* 20480 */
37
38 extern PRIVS privs[];
39
40 enum lsa_handle_type { LSA_HANDLE_POLICY_TYPE = 1, LSA_HANDLE_ACCOUNT_TYPE };
41
42 struct lsa_info {
43         DOM_SID sid;
44         uint32 access;
45         enum lsa_handle_type type;
46 };
47
48 const struct generic_mapping lsa_account_mapping = {
49         LSA_ACCOUNT_READ,
50         LSA_ACCOUNT_WRITE,
51         LSA_ACCOUNT_EXECUTE,
52         LSA_ACCOUNT_ALL_ACCESS
53 };
54
55 const struct generic_mapping lsa_policy_mapping = {
56         LSA_POLICY_READ,
57         LSA_POLICY_WRITE,
58         LSA_POLICY_EXECUTE,
59         LSA_POLICY_ALL_ACCESS
60 };
61
62 /***************************************************************************
63  init_lsa_ref_domain_list - adds a domain if it's not already in, returns the index.
64 ***************************************************************************/
65
66 static int init_lsa_ref_domain_list(TALLOC_CTX *mem_ctx,
67                                     struct lsa_RefDomainList *ref,
68                                     const char *dom_name,
69                                     DOM_SID *dom_sid)
70 {
71         int num = 0;
72
73         if (dom_name != NULL) {
74                 for (num = 0; num < ref->count; num++) {
75                         if (sid_equal(dom_sid, ref->domains[num].sid)) {
76                                 return num;
77                         }
78                 }
79         } else {
80                 num = ref->count;
81         }
82
83         if (num >= LSA_REF_DOMAIN_LIST_MULTIPLIER) {
84                 /* index not found, already at maximum domain limit */
85                 return -1;
86         }
87
88         ref->count = num + 1;
89         ref->max_size = LSA_REF_DOMAIN_LIST_MULTIPLIER;
90
91         ref->domains = TALLOC_REALLOC_ARRAY(mem_ctx, ref->domains,
92                                             struct lsa_DomainInfo, ref->count);
93         if (!ref->domains) {
94                 return -1;
95         }
96
97         ZERO_STRUCT(ref->domains[num]);
98
99         init_lsa_StringLarge(&ref->domains[num].name, dom_name);
100         ref->domains[num].sid = sid_dup_talloc(mem_ctx, dom_sid);
101         if (!ref->domains[num].sid) {
102                 return -1;
103         }
104
105         return num;
106 }
107
108
109 /***************************************************************************
110  initialize a lsa_DomainInfo structure.
111  ***************************************************************************/
112
113 static void init_dom_query_3(struct lsa_DomainInfo *r,
114                              const char *name,
115                              DOM_SID *sid)
116 {
117         init_lsa_StringLarge(&r->name, name);
118         r->sid = sid;
119 }
120
121 /***************************************************************************
122  initialize a lsa_DomainInfo structure.
123  ***************************************************************************/
124
125 static void init_dom_query_5(struct lsa_DomainInfo *r,
126                              const char *name,
127                              DOM_SID *sid)
128 {
129         init_lsa_StringLarge(&r->name, name);
130         r->sid = sid;
131 }
132
133 /***************************************************************************
134  lookup_lsa_rids. Must be called as root for lookup_name to work.
135  ***************************************************************************/
136
137 static NTSTATUS lookup_lsa_rids(TALLOC_CTX *mem_ctx,
138                                 struct lsa_RefDomainList *ref,
139                                 struct lsa_TranslatedSid *prid,
140                                 uint32_t num_entries,
141                                 struct lsa_String *name,
142                                 int flags,
143                                 uint32_t *pmapped_count)
144 {
145         uint32 mapped_count, i;
146
147         SMB_ASSERT(num_entries <= MAX_LOOKUP_SIDS);
148
149         mapped_count = 0;
150         *pmapped_count = 0;
151
152         for (i = 0; i < num_entries; i++) {
153                 DOM_SID sid;
154                 uint32 rid;
155                 int dom_idx;
156                 const char *full_name;
157                 const char *domain;
158                 enum lsa_SidType type = SID_NAME_UNKNOWN;
159
160                 /* Split name into domain and user component */
161
162                 full_name = name[i].string;
163                 if (full_name == NULL) {
164                         return NT_STATUS_NO_MEMORY;
165                 }
166
167                 DEBUG(5, ("lookup_lsa_rids: looking up name %s\n", full_name));
168
169                 /* We can ignore the result of lookup_name, it will not touch
170                    "type" if it's not successful */
171
172                 lookup_name(mem_ctx, full_name, flags, &domain, NULL,
173                             &sid, &type);
174
175                 switch (type) {
176                 case SID_NAME_USER:
177                 case SID_NAME_DOM_GRP:
178                 case SID_NAME_DOMAIN:
179                 case SID_NAME_ALIAS:
180                 case SID_NAME_WKN_GRP:
181                         DEBUG(5, ("init_lsa_rids: %s found\n", full_name));
182                         /* Leave these unchanged */
183                         break;
184                 default:
185                         /* Don't hand out anything but the list above */
186                         DEBUG(5, ("init_lsa_rids: %s not found\n", full_name));
187                         type = SID_NAME_UNKNOWN;
188                         break;
189                 }
190
191                 rid = 0;
192                 dom_idx = -1;
193
194                 if (type != SID_NAME_UNKNOWN) {
195                         sid_split_rid(&sid, &rid);
196                         dom_idx = init_lsa_ref_domain_list(mem_ctx, ref, domain, &sid);
197                         mapped_count++;
198                 }
199
200                 prid[i].sid_type        = type;
201                 prid[i].rid             = rid;
202                 prid[i].sid_index       = dom_idx;
203         }
204
205         *pmapped_count = mapped_count;
206         return NT_STATUS_OK;
207 }
208
209 /***************************************************************************
210  lookup_lsa_sids. Must be called as root for lookup_name to work.
211  ***************************************************************************/
212
213 static NTSTATUS lookup_lsa_sids(TALLOC_CTX *mem_ctx,
214                                 struct lsa_RefDomainList *ref,
215                                 struct lsa_TranslatedSid3 *trans_sids,
216                                 uint32_t num_entries,
217                                 struct lsa_String *name,
218                                 int flags,
219                                 uint32 *pmapped_count)
220 {
221         uint32 mapped_count, i;
222
223         SMB_ASSERT(num_entries <= MAX_LOOKUP_SIDS);
224
225         mapped_count = 0;
226         *pmapped_count = 0;
227
228         for (i = 0; i < num_entries; i++) {
229                 DOM_SID sid;
230                 uint32 rid;
231                 int dom_idx;
232                 const char *full_name;
233                 const char *domain;
234                 enum lsa_SidType type = SID_NAME_UNKNOWN;
235
236                 ZERO_STRUCT(sid);
237
238                 /* Split name into domain and user component */
239
240                 full_name = name[i].string;
241                 if (full_name == NULL) {
242                         return NT_STATUS_NO_MEMORY;
243                 }
244
245                 DEBUG(5, ("init_lsa_sids: looking up name %s\n", full_name));
246
247                 /* We can ignore the result of lookup_name, it will not touch
248                    "type" if it's not successful */
249
250                 lookup_name(mem_ctx, full_name, flags, &domain, NULL,
251                             &sid, &type);
252
253                 switch (type) {
254                 case SID_NAME_USER:
255                 case SID_NAME_DOM_GRP:
256                 case SID_NAME_DOMAIN:
257                 case SID_NAME_ALIAS:
258                 case SID_NAME_WKN_GRP:
259                         DEBUG(5, ("init_lsa_sids: %s found\n", full_name));
260                         /* Leave these unchanged */
261                         break;
262                 default:
263                         /* Don't hand out anything but the list above */
264                         DEBUG(5, ("init_lsa_sids: %s not found\n", full_name));
265                         type = SID_NAME_UNKNOWN;
266                         break;
267                 }
268
269                 rid = 0;
270                 dom_idx = -1;
271
272                 if (type != SID_NAME_UNKNOWN) {
273                         DOM_SID domain_sid;
274                         sid_copy(&domain_sid, &sid);
275                         sid_split_rid(&domain_sid, &rid);
276                         dom_idx = init_lsa_ref_domain_list(mem_ctx, ref, domain, &domain_sid);
277                         mapped_count++;
278                 }
279
280                 /* Initialize the lsa_TranslatedSid3 return. */
281                 trans_sids[i].sid_type = type;
282                 trans_sids[i].sid = sid_dup_talloc(mem_ctx, &sid);
283                 trans_sids[i].sid_index = dom_idx;
284         }
285
286         *pmapped_count = mapped_count;
287         return NT_STATUS_OK;
288 }
289
290 static NTSTATUS make_lsa_object_sd(TALLOC_CTX *mem_ctx, SEC_DESC **sd, size_t *sd_size,
291                                         const struct generic_mapping *map,
292                                         DOM_SID *sid, uint32_t sid_access)
293 {
294         DOM_SID adm_sid;
295         SEC_ACE ace[5];
296         size_t i = 0;
297
298         SEC_ACL *psa = NULL;
299
300         /* READ|EXECUTE access for Everyone */
301
302         init_sec_ace(&ace[i++], &global_sid_World, SEC_ACE_TYPE_ACCESS_ALLOWED,
303                         map->generic_execute | map->generic_read, 0);
304
305         /* Add Full Access 'BUILTIN\Administrators' and 'BUILTIN\Account Operators */
306
307         init_sec_ace(&ace[i++], &global_sid_Builtin_Administrators,
308                         SEC_ACE_TYPE_ACCESS_ALLOWED, map->generic_all, 0);
309         init_sec_ace(&ace[i++], &global_sid_Builtin_Account_Operators,
310                         SEC_ACE_TYPE_ACCESS_ALLOWED, map->generic_all, 0);
311
312         /* Add Full Access for Domain Admins */
313         sid_copy(&adm_sid, get_global_sam_sid());
314         sid_append_rid(&adm_sid, DOMAIN_GROUP_RID_ADMINS);
315         init_sec_ace(&ace[i++], &adm_sid, SEC_ACE_TYPE_ACCESS_ALLOWED,
316                         map->generic_all, 0);
317
318         /* If we have a sid, give it some special access */
319
320         if (sid) {
321                 init_sec_ace(&ace[i++], sid, SEC_ACE_TYPE_ACCESS_ALLOWED,
322                         sid_access, 0);
323         }
324
325         if((psa = make_sec_acl(mem_ctx, NT4_ACL_REVISION, i, ace)) == NULL)
326                 return NT_STATUS_NO_MEMORY;
327
328         if((*sd = make_sec_desc(mem_ctx, SECURITY_DESCRIPTOR_REVISION_1,
329                                 SEC_DESC_SELF_RELATIVE, &adm_sid, NULL, NULL,
330                                 psa, sd_size)) == NULL)
331                 return NT_STATUS_NO_MEMORY;
332
333         return NT_STATUS_OK;
334 }
335
336
337 /***************************************************************************
338  _lsa_OpenPolicy2
339  ***************************************************************************/
340
341 NTSTATUS _lsa_OpenPolicy2(pipes_struct *p,
342                           struct lsa_OpenPolicy2 *r)
343 {
344         struct lsa_info *info;
345         SEC_DESC *psd = NULL;
346         size_t sd_size;
347         uint32 des_access = r->in.access_mask;
348         uint32 acc_granted;
349         NTSTATUS status;
350
351         /* Work out max allowed. */
352         map_max_allowed_access(p->server_info->ptok,
353                                &p->server_info->utok,
354                                &des_access);
355
356         /* map the generic bits to the lsa policy ones */
357         se_map_generic(&des_access, &lsa_policy_mapping);
358
359         /* get the generic lsa policy SD until we store it */
360         status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size, &lsa_policy_mapping,
361                         NULL, 0);
362         if (!NT_STATUS_IS_OK(status)) {
363                 return status;
364         }
365
366         status = access_check_object(psd, p->server_info->ptok,
367                 NULL, 0, des_access,
368                 &acc_granted, "_lsa_OpenPolicy2" );
369
370         if (!NT_STATUS_IS_OK(status)) {
371                 return status;
372         }
373
374         /* associate the domain SID with the (unique) handle. */
375         info = TALLOC_ZERO_P(p->mem_ctx, struct lsa_info);
376         if (info == NULL) {
377                 return NT_STATUS_NO_MEMORY;
378         }
379
380         sid_copy(&info->sid,get_global_sam_sid());
381         info->access = acc_granted;
382         info->type = LSA_HANDLE_POLICY_TYPE;
383
384         /* set up the LSA QUERY INFO response */
385         if (!create_policy_hnd(p, r->out.handle, info))
386                 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
387
388         return NT_STATUS_OK;
389 }
390
391 /***************************************************************************
392  _lsa_OpenPolicy
393  ***************************************************************************/
394
395 NTSTATUS _lsa_OpenPolicy(pipes_struct *p,
396                          struct lsa_OpenPolicy *r)
397 {
398         struct lsa_OpenPolicy2 o;
399
400         o.in.system_name        = NULL; /* should be ignored */
401         o.in.attr               = r->in.attr;
402         o.in.access_mask        = r->in.access_mask;
403
404         o.out.handle            = r->out.handle;
405
406         return _lsa_OpenPolicy2(p, &o);
407 }
408
409 /***************************************************************************
410  _lsa_EnumTrustDom - this needs fixing to do more than return NULL ! JRA.
411  ufff, done :)  mimir
412  ***************************************************************************/
413
414 NTSTATUS _lsa_EnumTrustDom(pipes_struct *p,
415                            struct lsa_EnumTrustDom *r)
416 {
417         struct lsa_info *info;
418         uint32 next_idx;
419         struct trustdom_info **domains;
420         struct lsa_DomainInfo *lsa_domains = NULL;
421         int i;
422
423         /*
424          * preferred length is set to 5 as a "our" preferred length
425          * nt sets this parameter to 2
426          * update (20.08.2002): it's not preferred length, but preferred size!
427          * it needs further investigation how to optimally choose this value
428          */
429         uint32 max_num_domains =
430                 r->in.max_size < 5 ? r->in.max_size : 10;
431         uint32 num_domains;
432         NTSTATUS nt_status;
433         uint32 num_thistime;
434
435         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&info))
436                 return NT_STATUS_INVALID_HANDLE;
437
438         if (info->type != LSA_HANDLE_POLICY_TYPE) {
439                 return NT_STATUS_INVALID_HANDLE;
440         }
441
442         /* check if the user has enough rights */
443         if (!(info->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
444                 return NT_STATUS_ACCESS_DENIED;
445
446         become_root();
447         nt_status = pdb_enum_trusteddoms(p->mem_ctx, &num_domains, &domains);
448         unbecome_root();
449
450         if (!NT_STATUS_IS_OK(nt_status)) {
451                 return nt_status;
452         }
453
454         if (*r->in.resume_handle < num_domains) {
455                 num_thistime = MIN(num_domains, max_num_domains);
456
457                 nt_status = STATUS_MORE_ENTRIES;
458
459                 if (*r->in.resume_handle + num_thistime > num_domains) {
460                         num_thistime = num_domains - *r->in.resume_handle;
461                         nt_status = NT_STATUS_OK;
462                 }
463
464                 next_idx = *r->in.resume_handle + num_thistime;
465         } else {
466                 num_thistime = 0;
467                 next_idx = 0xffffffff;
468                 nt_status = NT_STATUS_NO_MORE_ENTRIES;
469         }
470
471         /* set up the lsa_enum_trust_dom response */
472
473         lsa_domains = TALLOC_ZERO_ARRAY(p->mem_ctx, struct lsa_DomainInfo,
474                                         num_thistime);
475         if (!lsa_domains) {
476                 return NT_STATUS_NO_MEMORY;
477         }
478
479         for (i=0; i<num_thistime; i++) {
480                 init_lsa_StringLarge(&lsa_domains[i].name, domains[i]->name);
481                 lsa_domains[i].sid = &domains[i]->sid;
482         }
483
484         *r->out.resume_handle = next_idx;
485         r->out.domains->count = num_thistime;
486         r->out.domains->domains = lsa_domains;
487
488         return nt_status;
489 }
490
491 #define LSA_AUDIT_NUM_CATEGORIES_NT4    7
492 #define LSA_AUDIT_NUM_CATEGORIES_WIN2K  9
493 #define LSA_AUDIT_NUM_CATEGORIES LSA_AUDIT_NUM_CATEGORIES_NT4
494
495 /***************************************************************************
496  _lsa_QueryInfoPolicy
497  ***************************************************************************/
498
499 NTSTATUS _lsa_QueryInfoPolicy(pipes_struct *p,
500                               struct lsa_QueryInfoPolicy *r)
501 {
502         NTSTATUS status = NT_STATUS_OK;
503         struct lsa_info *handle;
504         DOM_SID domain_sid;
505         const char *name;
506         DOM_SID *sid = NULL;
507         union lsa_PolicyInformation *info = NULL;
508
509         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&handle))
510                 return NT_STATUS_INVALID_HANDLE;
511
512         if (handle->type != LSA_HANDLE_POLICY_TYPE) {
513                 return NT_STATUS_INVALID_HANDLE;
514         }
515
516         info = TALLOC_ZERO_P(p->mem_ctx, union lsa_PolicyInformation);
517         if (!info) {
518                 return NT_STATUS_NO_MEMORY;
519         }
520
521         switch (r->in.level) {
522         case LSA_POLICY_INFO_AUDIT_EVENTS:
523                 {
524
525                 uint32 policy_def = LSA_AUDIT_POLICY_ALL;
526
527                 /* check if the user has enough rights */
528                 if (!(handle->access & LSA_POLICY_VIEW_AUDIT_INFORMATION)) {
529                         DEBUG(10,("_lsa_QueryInfoPolicy: insufficient access rights\n"));
530                         return NT_STATUS_ACCESS_DENIED;
531                 }
532
533                 /* fake info: We audit everything. ;) */
534
535                 info->audit_events.auditing_mode = true;
536                 info->audit_events.count = LSA_AUDIT_NUM_CATEGORIES;
537                 info->audit_events.settings = TALLOC_ZERO_ARRAY(p->mem_ctx,
538                                                                 enum lsa_PolicyAuditPolicy,
539                                                                 info->audit_events.count);
540                 if (!info->audit_events.settings) {
541                         return NT_STATUS_NO_MEMORY;
542                 }
543
544                 info->audit_events.settings[LSA_AUDIT_CATEGORY_ACCOUNT_MANAGEMENT] = policy_def;
545                 info->audit_events.settings[LSA_AUDIT_CATEGORY_FILE_AND_OBJECT_ACCESS] = policy_def;
546                 info->audit_events.settings[LSA_AUDIT_CATEGORY_LOGON] = policy_def;
547                 info->audit_events.settings[LSA_AUDIT_CATEGORY_PROCCESS_TRACKING] = policy_def;
548                 info->audit_events.settings[LSA_AUDIT_CATEGORY_SECURITY_POLICY_CHANGES] = policy_def;
549                 info->audit_events.settings[LSA_AUDIT_CATEGORY_SYSTEM] = policy_def;
550                 info->audit_events.settings[LSA_AUDIT_CATEGORY_USE_OF_USER_RIGHTS] = policy_def;
551
552                 break;
553                 }
554         case LSA_POLICY_INFO_DOMAIN:
555                 /* check if the user has enough rights */
556                 if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
557                         return NT_STATUS_ACCESS_DENIED;
558
559                 /* Request PolicyPrimaryDomainInformation. */
560                 switch (lp_server_role()) {
561                         case ROLE_DOMAIN_PDC:
562                         case ROLE_DOMAIN_BDC:
563                                 name = get_global_sam_name();
564                                 sid = sid_dup_talloc(p->mem_ctx, get_global_sam_sid());
565                                 if (!sid) {
566                                         return NT_STATUS_NO_MEMORY;
567                                 }
568                                 break;
569                         case ROLE_DOMAIN_MEMBER:
570                                 name = lp_workgroup();
571                                 /* We need to return the Domain SID here. */
572                                 if (secrets_fetch_domain_sid(lp_workgroup(), &domain_sid)) {
573                                         sid = sid_dup_talloc(p->mem_ctx, &domain_sid);
574                                         if (!sid) {
575                                                 return NT_STATUS_NO_MEMORY;
576                                         }
577                                 } else {
578                                         return NT_STATUS_CANT_ACCESS_DOMAIN_INFO;
579                                 }
580                                 break;
581                         case ROLE_STANDALONE:
582                                 name = lp_workgroup();
583                                 sid = NULL;
584                                 break;
585                         default:
586                                 return NT_STATUS_CANT_ACCESS_DOMAIN_INFO;
587                 }
588                 init_dom_query_3(&info->domain, name, sid);
589                 break;
590         case LSA_POLICY_INFO_ACCOUNT_DOMAIN:
591                 /* check if the user has enough rights */
592                 if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
593                         return NT_STATUS_ACCESS_DENIED;
594
595                 /* Request PolicyAccountDomainInformation. */
596                 name = get_global_sam_name();
597                 sid = get_global_sam_sid();
598
599                 init_dom_query_5(&info->account_domain, name, sid);
600                 break;
601         case LSA_POLICY_INFO_ROLE:
602                 /* check if the user has enough rights */
603                 if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
604                         return NT_STATUS_ACCESS_DENIED;
605
606                 switch (lp_server_role()) {
607                         case ROLE_DOMAIN_BDC:
608                                 /*
609                                  * only a BDC is a backup controller
610                                  * of the domain, it controls.
611                                  */
612                                 info->role.role = LSA_ROLE_BACKUP;
613                                 break;
614                         default:
615                                 /*
616                                  * any other role is a primary
617                                  * of the domain, it controls.
618                                  */
619                                 info->role.role = LSA_ROLE_PRIMARY;
620                                 break;
621                 }
622                 break;
623         case LSA_POLICY_INFO_DNS: {
624                 struct pdb_domain_info *dominfo;
625
626                 if ((pdb_capabilities() & PDB_CAP_ADS) == 0) {
627                         DEBUG(10, ("Not replying to LSA_POLICY_INFO_DNS "
628                                    "without ADS passdb backend\n"));
629                         status = NT_STATUS_INVALID_INFO_CLASS;
630                         break;
631                 }
632
633                 dominfo = pdb_get_domain_info(info);
634                 if (dominfo == NULL) {
635                         status = NT_STATUS_NO_MEMORY;
636                         break;
637                 }
638
639                 init_lsa_StringLarge(&info->dns.name,
640                                      dominfo->name);
641                 init_lsa_StringLarge(&info->dns.dns_domain,
642                                      dominfo->dns_domain);
643                 init_lsa_StringLarge(&info->dns.dns_forest,
644                                      dominfo->dns_forest);
645                 info->dns.domain_guid = dominfo->guid;
646                 info->dns.sid = &dominfo->sid;
647                 break;
648         }
649         default:
650                 DEBUG(0,("_lsa_QueryInfoPolicy: unknown info level in Lsa Query: %d\n",
651                         r->in.level));
652                 status = NT_STATUS_INVALID_INFO_CLASS;
653                 break;
654         }
655
656         *r->out.info = info;
657
658         return status;
659 }
660
661 /***************************************************************************
662  _lsa_lookup_sids_internal
663  ***************************************************************************/
664
665 static NTSTATUS _lsa_lookup_sids_internal(pipes_struct *p,
666                                           TALLOC_CTX *mem_ctx,
667                                           uint16_t level,                       /* input */
668                                           int num_sids,                         /* input */
669                                           struct lsa_SidPtr *sid,               /* input */
670                                           struct lsa_RefDomainList **pp_ref,    /* input/output */
671                                           struct lsa_TranslatedName2 **pp_names,/* input/output */
672                                           uint32_t *pp_mapped_count)            /* input/output */
673 {
674         NTSTATUS status;
675         int i;
676         const DOM_SID **sids = NULL;
677         struct lsa_RefDomainList *ref = NULL;
678         uint32 mapped_count = 0;
679         struct lsa_dom_info *dom_infos = NULL;
680         struct lsa_name_info *name_infos = NULL;
681         struct lsa_TranslatedName2 *names = NULL;
682
683         *pp_mapped_count = 0;
684         *pp_names = NULL;
685         *pp_ref = NULL;
686
687         if (num_sids == 0) {
688                 return NT_STATUS_OK;
689         }
690
691         sids = TALLOC_ARRAY(p->mem_ctx, const DOM_SID *, num_sids);
692         ref = TALLOC_ZERO_P(p->mem_ctx, struct lsa_RefDomainList);
693
694         if (sids == NULL || ref == NULL) {
695                 return NT_STATUS_NO_MEMORY;
696         }
697
698         for (i=0; i<num_sids; i++) {
699                 sids[i] = sid[i].sid;
700         }
701
702         status = lookup_sids(p->mem_ctx, num_sids, sids, level,
703                                   &dom_infos, &name_infos);
704
705         if (!NT_STATUS_IS_OK(status)) {
706                 return status;
707         }
708
709         names = TALLOC_ARRAY(p->mem_ctx, struct lsa_TranslatedName2, num_sids);
710         if (names == NULL) {
711                 return NT_STATUS_NO_MEMORY;
712         }
713
714         for (i=0; i<LSA_REF_DOMAIN_LIST_MULTIPLIER; i++) {
715
716                 if (!dom_infos[i].valid) {
717                         break;
718                 }
719
720                 if (init_lsa_ref_domain_list(mem_ctx, ref,
721                                              dom_infos[i].name,
722                                              &dom_infos[i].sid) != i) {
723                         DEBUG(0, ("Domain %s mentioned twice??\n",
724                                   dom_infos[i].name));
725                         return NT_STATUS_INTERNAL_ERROR;
726                 }
727         }
728
729         for (i=0; i<num_sids; i++) {
730                 struct lsa_name_info *name = &name_infos[i];
731
732                 if (name->type == SID_NAME_UNKNOWN) {
733                         fstring tmp;
734                         name->dom_idx = -1;
735                         /* Unknown sids should return the string
736                          * representation of the SID. Windows 2003 behaves
737                          * rather erratic here, in many cases it returns the
738                          * RID as 8 bytes hex, in others it returns the full
739                          * SID. We (Jerry/VL) could not figure out which the
740                          * hard cases are, so leave it with the SID.  */
741                         name->name = talloc_asprintf(p->mem_ctx, "%s",
742                                                      sid_to_fstring(tmp,
743                                                                     sids[i]));
744                         if (name->name == NULL) {
745                                 return NT_STATUS_NO_MEMORY;
746                         }
747                 } else {
748                         mapped_count += 1;
749                 }
750
751                 names[i].sid_type       = name->type;
752                 names[i].name.string    = name->name;
753                 names[i].sid_index      = name->dom_idx;
754                 names[i].unknown        = 0;
755         }
756
757         status = NT_STATUS_NONE_MAPPED;
758         if (mapped_count > 0) {
759                 status = (mapped_count < num_sids) ?
760                         STATUS_SOME_UNMAPPED : NT_STATUS_OK;
761         }
762
763         DEBUG(10, ("num_sids %d, mapped_count %d, status %s\n",
764                    num_sids, mapped_count, nt_errstr(status)));
765
766         *pp_mapped_count = mapped_count;
767         *pp_names = names;
768         *pp_ref = ref;
769
770         return status;
771 }
772
773 /***************************************************************************
774  _lsa_LookupSids
775  ***************************************************************************/
776
777 NTSTATUS _lsa_LookupSids(pipes_struct *p,
778                          struct lsa_LookupSids *r)
779 {
780         NTSTATUS status;
781         struct lsa_info *handle;
782         int num_sids = r->in.sids->num_sids;
783         uint32 mapped_count = 0;
784         struct lsa_RefDomainList *domains = NULL;
785         struct lsa_TranslatedName *names_out = NULL;
786         struct lsa_TranslatedName2 *names = NULL;
787         int i;
788
789         if ((r->in.level < 1) || (r->in.level > 6)) {
790                 return NT_STATUS_INVALID_PARAMETER;
791         }
792
793         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&handle)) {
794                 return NT_STATUS_INVALID_HANDLE;
795         }
796
797         if (handle->type != LSA_HANDLE_POLICY_TYPE) {
798                 return NT_STATUS_INVALID_HANDLE;
799         }
800
801         /* check if the user has enough rights */
802         if (!(handle->access & LSA_POLICY_LOOKUP_NAMES)) {
803                 return NT_STATUS_ACCESS_DENIED;
804         }
805
806         if (num_sids >  MAX_LOOKUP_SIDS) {
807                 DEBUG(5,("_lsa_LookupSids: limit of %d exceeded, requested %d\n",
808                          MAX_LOOKUP_SIDS, num_sids));
809                 return NT_STATUS_NONE_MAPPED;
810         }
811
812         status = _lsa_lookup_sids_internal(p,
813                                            p->mem_ctx,
814                                            r->in.level,
815                                            num_sids,
816                                            r->in.sids->sids,
817                                            &domains,
818                                            &names,
819                                            &mapped_count);
820
821         /* Only return here when there is a real error.
822            NT_STATUS_NONE_MAPPED is a special case as it indicates that none of
823            the requested sids could be resolved. Older versions of XP (pre SP3)
824            rely that we return with the string representations of those SIDs in
825            that case. If we don't, XP crashes - Guenther
826            */
827
828         if (NT_STATUS_IS_ERR(status) &&
829             !NT_STATUS_EQUAL(status, NT_STATUS_NONE_MAPPED)) {
830                 return status;
831         }
832
833         /* Convert from lsa_TranslatedName2 to lsa_TranslatedName */
834         names_out = TALLOC_ARRAY(p->mem_ctx, struct lsa_TranslatedName,
835                                  num_sids);
836         if (!names_out) {
837                 return NT_STATUS_NO_MEMORY;
838         }
839
840         for (i=0; i<num_sids; i++) {
841                 names_out[i].sid_type = names[i].sid_type;
842                 names_out[i].name = names[i].name;
843                 names_out[i].sid_index = names[i].sid_index;
844         }
845
846         *r->out.domains = domains;
847         r->out.names->count = num_sids;
848         r->out.names->names = names_out;
849         *r->out.count = mapped_count;
850
851         return status;
852 }
853
854 /***************************************************************************
855  _lsa_LookupSids2
856  ***************************************************************************/
857
858 NTSTATUS _lsa_LookupSids2(pipes_struct *p,
859                           struct lsa_LookupSids2 *r)
860 {
861         NTSTATUS status;
862         struct lsa_info *handle;
863         int num_sids = r->in.sids->num_sids;
864         uint32 mapped_count = 0;
865         struct lsa_RefDomainList *domains = NULL;
866         struct lsa_TranslatedName2 *names = NULL;
867         bool check_policy = true;
868
869         switch (p->hdr_req.opnum) {
870                 case NDR_LSA_LOOKUPSIDS3:
871                         check_policy = false;
872                         break;
873                 case NDR_LSA_LOOKUPSIDS2:
874                 default:
875                         check_policy = true;
876         }
877
878         if ((r->in.level < 1) || (r->in.level > 6)) {
879                 return NT_STATUS_INVALID_PARAMETER;
880         }
881
882         if (check_policy) {
883                 if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&handle)) {
884                         return NT_STATUS_INVALID_HANDLE;
885                 }
886
887                 if (handle->type != LSA_HANDLE_POLICY_TYPE) {
888                         return NT_STATUS_INVALID_HANDLE;
889                 }
890
891                 /* check if the user has enough rights */
892                 if (!(handle->access & LSA_POLICY_LOOKUP_NAMES)) {
893                         return NT_STATUS_ACCESS_DENIED;
894                 }
895         }
896
897         if (num_sids >  MAX_LOOKUP_SIDS) {
898                 DEBUG(5,("_lsa_LookupSids2: limit of %d exceeded, requested %d\n",
899                          MAX_LOOKUP_SIDS, num_sids));
900                 return NT_STATUS_NONE_MAPPED;
901         }
902
903         status = _lsa_lookup_sids_internal(p,
904                                            p->mem_ctx,
905                                            r->in.level,
906                                            num_sids,
907                                            r->in.sids->sids,
908                                            &domains,
909                                            &names,
910                                            &mapped_count);
911
912         *r->out.domains = domains;
913         r->out.names->count = num_sids;
914         r->out.names->names = names;
915         *r->out.count = mapped_count;
916
917         return status;
918 }
919
920 /***************************************************************************
921  _lsa_LookupSids3
922  ***************************************************************************/
923
924 NTSTATUS _lsa_LookupSids3(pipes_struct *p,
925                           struct lsa_LookupSids3 *r)
926 {
927         struct lsa_LookupSids2 q;
928
929         /* No policy handle on this call. Restrict to crypto connections. */
930         if (p->auth.auth_type != PIPE_AUTH_TYPE_SCHANNEL) {
931                 DEBUG(0,("_lsa_LookupSids3: client %s not using schannel for netlogon\n",
932                         get_remote_machine_name() ));
933                 return NT_STATUS_INVALID_PARAMETER;
934         }
935
936         q.in.handle             = NULL;
937         q.in.sids               = r->in.sids;
938         q.in.level              = r->in.level;
939         q.in.unknown1           = r->in.unknown1;
940         q.in.unknown2           = r->in.unknown2;
941         q.in.names              = r->in.names;
942         q.in.count              = r->in.count;
943
944         q.out.domains           = r->out.domains;
945         q.out.names             = r->out.names;
946         q.out.count             = r->out.count;
947
948         return _lsa_LookupSids2(p, &q);
949 }
950
951 /***************************************************************************
952  ***************************************************************************/
953
954 static int lsa_lookup_level_to_flags(uint16 level)
955 {
956         int flags;
957
958         switch (level) {
959                 case 1:
960                         flags = LOOKUP_NAME_ALL;
961                         break;
962                 case 2:
963                         flags = LOOKUP_NAME_DOMAIN|LOOKUP_NAME_REMOTE|LOOKUP_NAME_ISOLATED;
964                         break;
965                 case 3:
966                         flags = LOOKUP_NAME_DOMAIN|LOOKUP_NAME_ISOLATED;
967                         break;
968                 case 4:
969                 case 5:
970                 case 6:
971                 default:
972                         flags = LOOKUP_NAME_NONE;
973                         break;
974         }
975
976         return flags;
977 }
978
979 /***************************************************************************
980  _lsa_LookupNames
981  ***************************************************************************/
982
983 NTSTATUS _lsa_LookupNames(pipes_struct *p,
984                           struct lsa_LookupNames *r)
985 {
986         NTSTATUS status = NT_STATUS_NONE_MAPPED;
987         struct lsa_info *handle;
988         struct lsa_String *names = r->in.names;
989         uint32 num_entries = r->in.num_names;
990         struct lsa_RefDomainList *domains = NULL;
991         struct lsa_TranslatedSid *rids = NULL;
992         uint32 mapped_count = 0;
993         int flags = 0;
994
995         if (num_entries >  MAX_LOOKUP_SIDS) {
996                 num_entries = MAX_LOOKUP_SIDS;
997                 DEBUG(5,("_lsa_LookupNames: truncating name lookup list to %d\n",
998                         num_entries));
999         }
1000
1001         flags = lsa_lookup_level_to_flags(r->in.level);
1002
1003         domains = TALLOC_ZERO_P(p->mem_ctx, struct lsa_RefDomainList);
1004         if (!domains) {
1005                 return NT_STATUS_NO_MEMORY;
1006         }
1007
1008         if (num_entries) {
1009                 rids = TALLOC_ZERO_ARRAY(p->mem_ctx, struct lsa_TranslatedSid,
1010                                          num_entries);
1011                 if (!rids) {
1012                         return NT_STATUS_NO_MEMORY;
1013                 }
1014         } else {
1015                 rids = NULL;
1016         }
1017
1018         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&handle)) {
1019                 status = NT_STATUS_INVALID_HANDLE;
1020                 goto done;
1021         }
1022
1023         if (handle->type != LSA_HANDLE_POLICY_TYPE) {
1024                 return NT_STATUS_INVALID_HANDLE;
1025         }
1026
1027         /* check if the user has enough rights */
1028         if (!(handle->access & LSA_POLICY_LOOKUP_NAMES)) {
1029                 status = NT_STATUS_ACCESS_DENIED;
1030                 goto done;
1031         }
1032
1033         /* set up the LSA Lookup RIDs response */
1034         become_root(); /* lookup_name can require root privs */
1035         status = lookup_lsa_rids(p->mem_ctx, domains, rids, num_entries,
1036                                  names, flags, &mapped_count);
1037         unbecome_root();
1038
1039 done:
1040
1041         if (NT_STATUS_IS_OK(status) && (num_entries != 0) ) {
1042                 if (mapped_count == 0) {
1043                         status = NT_STATUS_NONE_MAPPED;
1044                 } else if (mapped_count != num_entries) {
1045                         status = STATUS_SOME_UNMAPPED;
1046                 }
1047         }
1048
1049         *r->out.count = mapped_count;
1050         *r->out.domains = domains;
1051         r->out.sids->sids = rids;
1052         r->out.sids->count = num_entries;
1053
1054         return status;
1055 }
1056
1057 /***************************************************************************
1058  _lsa_LookupNames2
1059  ***************************************************************************/
1060
1061 NTSTATUS _lsa_LookupNames2(pipes_struct *p,
1062                            struct lsa_LookupNames2 *r)
1063 {
1064         NTSTATUS status;
1065         struct lsa_LookupNames q;
1066         struct lsa_TransSidArray2 *sid_array2 = r->in.sids;
1067         struct lsa_TransSidArray *sid_array = NULL;
1068         uint32_t i;
1069
1070         sid_array = TALLOC_ZERO_P(p->mem_ctx, struct lsa_TransSidArray);
1071         if (!sid_array) {
1072                 return NT_STATUS_NO_MEMORY;
1073         }
1074
1075         q.in.handle             = r->in.handle;
1076         q.in.num_names          = r->in.num_names;
1077         q.in.names              = r->in.names;
1078         q.in.level              = r->in.level;
1079         q.in.sids               = sid_array;
1080         q.in.count              = r->in.count;
1081         /* we do not know what this is for */
1082         /*                      = r->in.unknown1; */
1083         /*                      = r->in.unknown2; */
1084
1085         q.out.domains           = r->out.domains;
1086         q.out.sids              = sid_array;
1087         q.out.count             = r->out.count;
1088
1089         status = _lsa_LookupNames(p, &q);
1090
1091         sid_array2->count = sid_array->count;
1092         sid_array2->sids = TALLOC_ARRAY(p->mem_ctx, struct lsa_TranslatedSid2, sid_array->count);
1093         if (!sid_array2->sids) {
1094                 return NT_STATUS_NO_MEMORY;
1095         }
1096
1097         for (i=0; i<sid_array->count; i++) {
1098                 sid_array2->sids[i].sid_type  = sid_array->sids[i].sid_type;
1099                 sid_array2->sids[i].rid       = sid_array->sids[i].rid;
1100                 sid_array2->sids[i].sid_index = sid_array->sids[i].sid_index;
1101                 sid_array2->sids[i].unknown   = 0;
1102         }
1103
1104         r->out.sids = sid_array2;
1105
1106         return status;
1107 }
1108
1109 /***************************************************************************
1110  _lsa_LookupNames3
1111  ***************************************************************************/
1112
1113 NTSTATUS _lsa_LookupNames3(pipes_struct *p,
1114                            struct lsa_LookupNames3 *r)
1115 {
1116         NTSTATUS status;
1117         struct lsa_info *handle;
1118         struct lsa_String *names = r->in.names;
1119         uint32 num_entries = r->in.num_names;
1120         struct lsa_RefDomainList *domains = NULL;
1121         struct lsa_TranslatedSid3 *trans_sids = NULL;
1122         uint32 mapped_count = 0;
1123         int flags = 0;
1124         bool check_policy = true;
1125
1126         switch (p->hdr_req.opnum) {
1127                 case NDR_LSA_LOOKUPNAMES4:
1128                         check_policy = false;
1129                         break;
1130                 case NDR_LSA_LOOKUPNAMES3:
1131                 default:
1132                         check_policy = true;
1133         }
1134
1135         if (num_entries >  MAX_LOOKUP_SIDS) {
1136                 num_entries = MAX_LOOKUP_SIDS;
1137                 DEBUG(5,("_lsa_LookupNames3: truncating name lookup list to %d\n", num_entries));
1138         }
1139
1140         /* Probably the lookup_level is some sort of bitmask. */
1141         if (r->in.level == 1) {
1142                 flags = LOOKUP_NAME_ALL;
1143         }
1144
1145         domains = TALLOC_ZERO_P(p->mem_ctx, struct lsa_RefDomainList);
1146         if (!domains) {
1147                 return NT_STATUS_NO_MEMORY;
1148         }
1149
1150         if (num_entries) {
1151                 trans_sids = TALLOC_ZERO_ARRAY(p->mem_ctx, struct lsa_TranslatedSid3,
1152                                                num_entries);
1153                 if (!trans_sids) {
1154                         return NT_STATUS_NO_MEMORY;
1155                 }
1156         } else {
1157                 trans_sids = NULL;
1158         }
1159
1160         if (check_policy) {
1161
1162                 if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&handle)) {
1163                         status = NT_STATUS_INVALID_HANDLE;
1164                         goto done;
1165                 }
1166
1167                 if (handle->type != LSA_HANDLE_POLICY_TYPE) {
1168                         return NT_STATUS_INVALID_HANDLE;
1169                 }
1170
1171                 /* check if the user has enough rights */
1172                 if (!(handle->access & LSA_POLICY_LOOKUP_NAMES)) {
1173                         status = NT_STATUS_ACCESS_DENIED;
1174                         goto done;
1175                 }
1176         }
1177
1178         /* set up the LSA Lookup SIDs response */
1179         become_root(); /* lookup_name can require root privs */
1180         status = lookup_lsa_sids(p->mem_ctx, domains, trans_sids, num_entries,
1181                                  names, flags, &mapped_count);
1182         unbecome_root();
1183
1184 done:
1185
1186         if (NT_STATUS_IS_OK(status)) {
1187                 if (mapped_count == 0) {
1188                         status = NT_STATUS_NONE_MAPPED;
1189                 } else if (mapped_count != num_entries) {
1190                         status = STATUS_SOME_UNMAPPED;
1191                 }
1192         }
1193
1194         *r->out.count = mapped_count;
1195         *r->out.domains = domains;
1196         r->out.sids->sids = trans_sids;
1197         r->out.sids->count = num_entries;
1198
1199         return status;
1200 }
1201
1202 /***************************************************************************
1203  _lsa_LookupNames4
1204  ***************************************************************************/
1205
1206 NTSTATUS _lsa_LookupNames4(pipes_struct *p,
1207                            struct lsa_LookupNames4 *r)
1208 {
1209         struct lsa_LookupNames3 q;
1210
1211         /* No policy handle on this call. Restrict to crypto connections. */
1212         if (p->auth.auth_type != PIPE_AUTH_TYPE_SCHANNEL) {
1213                 DEBUG(0,("_lsa_lookup_names4: client %s not using schannel for netlogon\n",
1214                         get_remote_machine_name() ));
1215                 return NT_STATUS_INVALID_PARAMETER;
1216         }
1217
1218         q.in.handle             = NULL;
1219         q.in.num_names          = r->in.num_names;
1220         q.in.names              = r->in.names;
1221         q.in.level              = r->in.level;
1222         q.in.lookup_options     = r->in.lookup_options;
1223         q.in.client_revision    = r->in.client_revision;
1224         q.in.sids               = r->in.sids;
1225         q.in.count              = r->in.count;
1226
1227         q.out.domains           = r->out.domains;
1228         q.out.sids              = r->out.sids;
1229         q.out.count             = r->out.count;
1230
1231         return _lsa_LookupNames3(p, &q);
1232 }
1233
1234 /***************************************************************************
1235  _lsa_close. Also weird - needs to check if lsa handle is correct. JRA.
1236  ***************************************************************************/
1237
1238 NTSTATUS _lsa_Close(pipes_struct *p, struct lsa_Close *r)
1239 {
1240         if (!find_policy_by_hnd(p, r->in.handle, NULL)) {
1241                 return NT_STATUS_INVALID_HANDLE;
1242         }
1243
1244         close_policy_hnd(p, r->in.handle);
1245         ZERO_STRUCTP(r->out.handle);
1246         return NT_STATUS_OK;
1247 }
1248
1249 /***************************************************************************
1250  ***************************************************************************/
1251
1252 NTSTATUS _lsa_OpenSecret(pipes_struct *p, struct lsa_OpenSecret *r)
1253 {
1254         return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1255 }
1256
1257 /***************************************************************************
1258  ***************************************************************************/
1259
1260 NTSTATUS _lsa_OpenTrustedDomain(pipes_struct *p, struct lsa_OpenTrustedDomain *r)
1261 {
1262         return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1263 }
1264
1265 /***************************************************************************
1266  ***************************************************************************/
1267
1268 NTSTATUS _lsa_CreateTrustedDomain(pipes_struct *p, struct lsa_CreateTrustedDomain *r)
1269 {
1270         return NT_STATUS_ACCESS_DENIED;
1271 }
1272
1273 /***************************************************************************
1274  ***************************************************************************/
1275
1276 NTSTATUS _lsa_CreateSecret(pipes_struct *p, struct lsa_CreateSecret *r)
1277 {
1278         return NT_STATUS_ACCESS_DENIED;
1279 }
1280
1281 /***************************************************************************
1282  ***************************************************************************/
1283
1284 NTSTATUS _lsa_SetSecret(pipes_struct *p, struct lsa_SetSecret *r)
1285 {
1286         return NT_STATUS_ACCESS_DENIED;
1287 }
1288
1289 /***************************************************************************
1290  _lsa_DeleteObject
1291  ***************************************************************************/
1292
1293 NTSTATUS _lsa_DeleteObject(pipes_struct *p,
1294                            struct lsa_DeleteObject *r)
1295 {
1296         NTSTATUS status;
1297         struct lsa_info *info = NULL;
1298
1299         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&info)) {
1300                 return NT_STATUS_INVALID_HANDLE;
1301         }
1302
1303         if (!(info->access & STD_RIGHT_DELETE_ACCESS)) {
1304                 return NT_STATUS_ACCESS_DENIED;
1305         }
1306
1307         status = privilege_delete_account(&info->sid);
1308         if (!NT_STATUS_IS_OK(status)) {
1309                 DEBUG(10,("_lsa_DeleteObject: privilege_delete_account gave: %s\n",
1310                         nt_errstr(status)));
1311         }
1312
1313         return status;
1314 }
1315
1316 /***************************************************************************
1317  _lsa_EnumPrivs
1318  ***************************************************************************/
1319
1320 NTSTATUS _lsa_EnumPrivs(pipes_struct *p,
1321                         struct lsa_EnumPrivs *r)
1322 {
1323         struct lsa_info *handle;
1324         uint32 i;
1325         uint32 enum_context = *r->in.resume_handle;
1326         int num_privs = count_all_privileges();
1327         struct lsa_PrivEntry *entries = NULL;
1328         LUID_ATTR luid;
1329
1330         /* remember that the enum_context starts at 0 and not 1 */
1331
1332         if ( enum_context >= num_privs )
1333                 return NT_STATUS_NO_MORE_ENTRIES;
1334
1335         DEBUG(10,("_lsa_EnumPrivs: enum_context:%d total entries:%d\n",
1336                 enum_context, num_privs));
1337
1338         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&handle))
1339                 return NT_STATUS_INVALID_HANDLE;
1340
1341         if (handle->type != LSA_HANDLE_POLICY_TYPE) {
1342                 return NT_STATUS_INVALID_HANDLE;
1343         }
1344
1345         /* check if the user has enough rights
1346            I don't know if it's the right one. not documented.  */
1347
1348         if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
1349                 return NT_STATUS_ACCESS_DENIED;
1350
1351         if (num_privs) {
1352                 entries = TALLOC_ZERO_ARRAY(p->mem_ctx, struct lsa_PrivEntry, num_privs);
1353                 if (!entries) {
1354                         return NT_STATUS_NO_MEMORY;
1355                 }
1356         } else {
1357                 entries = NULL;
1358         }
1359
1360         for (i = 0; i < num_privs; i++) {
1361                 if( i < enum_context) {
1362
1363                         init_lsa_StringLarge(&entries[i].name, NULL);
1364
1365                         entries[i].luid.low = 0;
1366                         entries[i].luid.high = 0;
1367                 } else {
1368
1369                         init_lsa_StringLarge(&entries[i].name, privs[i].name);
1370
1371                         luid = get_privilege_luid( &privs[i].se_priv );
1372
1373                         entries[i].luid.low = luid.luid.low;
1374                         entries[i].luid.high = luid.luid.high;
1375                 }
1376         }
1377
1378         enum_context = num_privs;
1379
1380         *r->out.resume_handle = enum_context;
1381         r->out.privs->count = num_privs;
1382         r->out.privs->privs = entries;
1383
1384         return NT_STATUS_OK;
1385 }
1386
1387 /***************************************************************************
1388  _lsa_LookupPrivDisplayName
1389  ***************************************************************************/
1390
1391 NTSTATUS _lsa_LookupPrivDisplayName(pipes_struct *p,
1392                                     struct lsa_LookupPrivDisplayName *r)
1393 {
1394         struct lsa_info *handle;
1395         const char *description;
1396         struct lsa_StringLarge *lsa_name;
1397
1398         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&handle))
1399                 return NT_STATUS_INVALID_HANDLE;
1400
1401         if (handle->type != LSA_HANDLE_POLICY_TYPE) {
1402                 return NT_STATUS_INVALID_HANDLE;
1403         }
1404
1405         /* check if the user has enough rights */
1406
1407         /*
1408          * I don't know if it's the right one. not documented.
1409          */
1410         if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
1411                 return NT_STATUS_ACCESS_DENIED;
1412
1413         DEBUG(10,("_lsa_LookupPrivDisplayName: name = %s\n", r->in.name->string));
1414
1415         description = get_privilege_dispname(r->in.name->string);
1416         if (!description) {
1417                 DEBUG(10,("_lsa_LookupPrivDisplayName: doesn't exist\n"));
1418                 return NT_STATUS_NO_SUCH_PRIVILEGE;
1419         }
1420
1421         DEBUG(10,("_lsa_LookupPrivDisplayName: display name = %s\n", description));
1422
1423         lsa_name = TALLOC_ZERO_P(p->mem_ctx, struct lsa_StringLarge);
1424         if (!lsa_name) {
1425                 return NT_STATUS_NO_MEMORY;
1426         }
1427
1428         init_lsa_StringLarge(lsa_name, description);
1429
1430         *r->out.returned_language_id = r->in.language_id;
1431         *r->out.disp_name = lsa_name;
1432
1433         return NT_STATUS_OK;
1434 }
1435
1436 /***************************************************************************
1437  _lsa_EnumAccounts
1438  ***************************************************************************/
1439
1440 NTSTATUS _lsa_EnumAccounts(pipes_struct *p,
1441                            struct lsa_EnumAccounts *r)
1442 {
1443         struct lsa_info *handle;
1444         DOM_SID *sid_list;
1445         int i, j, num_entries;
1446         NTSTATUS status;
1447         struct lsa_SidPtr *sids = NULL;
1448
1449         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&handle))
1450                 return NT_STATUS_INVALID_HANDLE;
1451
1452         if (handle->type != LSA_HANDLE_POLICY_TYPE) {
1453                 return NT_STATUS_INVALID_HANDLE;
1454         }
1455
1456         if (!(handle->access & LSA_POLICY_VIEW_LOCAL_INFORMATION))
1457                 return NT_STATUS_ACCESS_DENIED;
1458
1459         sid_list = NULL;
1460         num_entries = 0;
1461
1462         /* The only way we can currently find out all the SIDs that have been
1463            privileged is to scan all privileges */
1464
1465         status = privilege_enumerate_accounts(&sid_list, &num_entries);
1466         if (!NT_STATUS_IS_OK(status)) {
1467                 return status;
1468         }
1469
1470         if (*r->in.resume_handle >= num_entries) {
1471                 return NT_STATUS_NO_MORE_ENTRIES;
1472         }
1473
1474         if (num_entries - *r->in.resume_handle) {
1475                 sids = TALLOC_ZERO_ARRAY(p->mem_ctx, struct lsa_SidPtr,
1476                                          num_entries - *r->in.resume_handle);
1477                 if (!sids) {
1478                         talloc_free(sid_list);
1479                         return NT_STATUS_NO_MEMORY;
1480                 }
1481
1482                 for (i = *r->in.resume_handle, j = 0; i < num_entries; i++, j++) {
1483                         sids[j].sid = sid_dup_talloc(p->mem_ctx, &sid_list[i]);
1484                         if (!sids[j].sid) {
1485                                 talloc_free(sid_list);
1486                                 return NT_STATUS_NO_MEMORY;
1487                         }
1488                 }
1489         }
1490
1491         talloc_free(sid_list);
1492
1493         *r->out.resume_handle = num_entries;
1494         r->out.sids->num_sids = num_entries;
1495         r->out.sids->sids = sids;
1496
1497         return NT_STATUS_OK;
1498 }
1499
1500 /***************************************************************************
1501  _lsa_GetUserName
1502  ***************************************************************************/
1503
1504 NTSTATUS _lsa_GetUserName(pipes_struct *p,
1505                           struct lsa_GetUserName *r)
1506 {
1507         const char *username, *domname;
1508         struct lsa_String *account_name = NULL;
1509         struct lsa_String *authority_name = NULL;
1510
1511         if (r->in.account_name &&
1512            *r->in.account_name) {
1513                 return NT_STATUS_INVALID_PARAMETER;
1514         }
1515
1516         if (r->in.authority_name &&
1517            *r->in.authority_name) {
1518                 return NT_STATUS_INVALID_PARAMETER;
1519         }
1520
1521         if (p->server_info->guest) {
1522                 /*
1523                  * I'm 99% sure this is not the right place to do this,
1524                  * global_sid_Anonymous should probably be put into the token
1525                  * instead of the guest id -- vl
1526                  */
1527                 if (!lookup_sid(p->mem_ctx, &global_sid_Anonymous,
1528                                 &domname, &username, NULL)) {
1529                         return NT_STATUS_NO_MEMORY;
1530                 }
1531         } else {
1532                 username = p->server_info->sanitized_username;
1533                 domname = pdb_get_domain(p->server_info->sam_account);
1534         }
1535
1536         account_name = TALLOC_P(p->mem_ctx, struct lsa_String);
1537         if (!account_name) {
1538                 return NT_STATUS_NO_MEMORY;
1539         }
1540         init_lsa_String(account_name, username);
1541
1542         if (r->out.authority_name) {
1543                 authority_name = TALLOC_P(p->mem_ctx, struct lsa_String);
1544                 if (!authority_name) {
1545                         return NT_STATUS_NO_MEMORY;
1546                 }
1547                 init_lsa_String(authority_name, domname);
1548         }
1549
1550         *r->out.account_name = account_name;
1551         if (r->out.authority_name) {
1552                 *r->out.authority_name = authority_name;
1553         }
1554
1555         return NT_STATUS_OK;
1556 }
1557
1558 /***************************************************************************
1559  _lsa_CreateAccount
1560  ***************************************************************************/
1561
1562 NTSTATUS _lsa_CreateAccount(pipes_struct *p,
1563                             struct lsa_CreateAccount *r)
1564 {
1565         struct lsa_info *handle;
1566         struct lsa_info *info;
1567
1568         /* find the connection policy handle. */
1569         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&handle))
1570                 return NT_STATUS_INVALID_HANDLE;
1571
1572         if (handle->type != LSA_HANDLE_POLICY_TYPE) {
1573                 return NT_STATUS_INVALID_HANDLE;
1574         }
1575
1576         /* check if the user has enough rights */
1577
1578         /*
1579          * I don't know if it's the right one. not documented.
1580          * but guessed with rpcclient.
1581          */
1582         if (!(handle->access & LSA_POLICY_CREATE_ACCOUNT))
1583                 return NT_STATUS_ACCESS_DENIED;
1584
1585         if ( is_privileged_sid( r->in.sid ) )
1586                 return NT_STATUS_OBJECT_NAME_COLLISION;
1587
1588         /* associate the user/group SID with the (unique) handle. */
1589
1590         info = TALLOC_ZERO_P(p->mem_ctx, struct lsa_info);
1591         if (info == NULL) {
1592                 return NT_STATUS_NO_MEMORY;
1593         }
1594
1595         info->sid = *r->in.sid;
1596         info->access = r->in.access_mask;
1597         info->type = LSA_HANDLE_ACCOUNT_TYPE;
1598
1599         /* get a (unique) handle.  open a policy on it. */
1600         if (!create_policy_hnd(p, r->out.acct_handle, info))
1601                 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1602
1603         return privilege_create_account( &info->sid );
1604 }
1605
1606 /***************************************************************************
1607  _lsa_OpenAccount
1608  ***************************************************************************/
1609
1610 NTSTATUS _lsa_OpenAccount(pipes_struct *p,
1611                           struct lsa_OpenAccount *r)
1612 {
1613         struct lsa_info *handle;
1614         struct lsa_info *info;
1615         SEC_DESC *psd = NULL;
1616         size_t sd_size;
1617         uint32_t des_access = r->in.access_mask;
1618         uint32_t acc_granted;
1619         NTSTATUS status;
1620
1621         /* find the connection policy handle. */
1622         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&handle))
1623                 return NT_STATUS_INVALID_HANDLE;
1624
1625         if (handle->type != LSA_HANDLE_POLICY_TYPE) {
1626                 return NT_STATUS_INVALID_HANDLE;
1627         }
1628
1629         /* des_access is for the account here, not the policy
1630          * handle - so don't check against policy handle. */
1631
1632         /* Work out max allowed. */
1633         map_max_allowed_access(p->server_info->ptok,
1634                                &p->server_info->utok,
1635                                &des_access);
1636
1637         /* map the generic bits to the lsa account ones */
1638         se_map_generic(&des_access, &lsa_account_mapping);
1639
1640         /* get the generic lsa account SD until we store it */
1641         status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size,
1642                                 &lsa_account_mapping,
1643                                 r->in.sid, LSA_ACCOUNT_ALL_ACCESS);
1644         if (!NT_STATUS_IS_OK(status)) {
1645                 return status;
1646         }
1647
1648         status = access_check_object(psd, p->server_info->ptok,
1649                 NULL, 0, des_access,
1650                 &acc_granted, "_lsa_OpenAccount" );
1651
1652         if (!NT_STATUS_IS_OK(status)) {
1653                 return status;
1654         }
1655
1656         /* TODO: Fis the parsing routine before reenabling this check! */
1657         #if 0
1658         if (!lookup_sid(&handle->sid, dom_name, name, &type))
1659                 return NT_STATUS_ACCESS_DENIED;
1660         #endif
1661         /* associate the user/group SID with the (unique) handle. */
1662         info = TALLOC_ZERO_P(p->mem_ctx, struct lsa_info);
1663         if (info == NULL) {
1664                 return NT_STATUS_NO_MEMORY;
1665         }
1666
1667         info->sid = *r->in.sid;
1668         info->access = acc_granted;
1669         info->type = LSA_HANDLE_ACCOUNT_TYPE;
1670
1671         /* get a (unique) handle.  open a policy on it. */
1672         if (!create_policy_hnd(p, r->out.acct_handle, info))
1673                 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1674
1675         return NT_STATUS_OK;
1676 }
1677
1678 /***************************************************************************
1679  _lsa_EnumPrivsAccount
1680  For a given SID, enumerate all the privilege this account has.
1681  ***************************************************************************/
1682
1683 NTSTATUS _lsa_EnumPrivsAccount(pipes_struct *p,
1684                                struct lsa_EnumPrivsAccount *r)
1685 {
1686         NTSTATUS status = NT_STATUS_OK;
1687         struct lsa_info *info=NULL;
1688         SE_PRIV mask;
1689         PRIVILEGE_SET privileges;
1690         struct lsa_PrivilegeSet *priv_set = NULL;
1691         struct lsa_LUIDAttribute *luid_attrs = NULL;
1692         int i;
1693
1694         /* find the connection policy handle. */
1695         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&info))
1696                 return NT_STATUS_INVALID_HANDLE;
1697
1698         if (info->type != LSA_HANDLE_ACCOUNT_TYPE) {
1699                 return NT_STATUS_INVALID_HANDLE;
1700         }
1701
1702         if (!(info->access & LSA_ACCOUNT_VIEW))
1703                 return NT_STATUS_ACCESS_DENIED;
1704
1705         get_privileges_for_sids(&mask, &info->sid, 1);
1706
1707         privilege_set_init( &privileges );
1708
1709         priv_set = TALLOC_ZERO_P(p->mem_ctx, struct lsa_PrivilegeSet);
1710         if (!priv_set) {
1711                 status = NT_STATUS_NO_MEMORY;
1712                 goto done;
1713         }
1714
1715         if ( se_priv_to_privilege_set( &privileges, &mask ) ) {
1716
1717                 DEBUG(10,("_lsa_EnumPrivsAccount: %s has %d privileges\n",
1718                           sid_string_dbg(&info->sid),
1719                           privileges.count));
1720
1721                 luid_attrs = TALLOC_ZERO_ARRAY(p->mem_ctx,
1722                                                struct lsa_LUIDAttribute,
1723                                                privileges.count);
1724                 if (!luid_attrs) {
1725                         status = NT_STATUS_NO_MEMORY;
1726                         goto done;
1727                 }
1728
1729                 for (i=0; i<privileges.count; i++) {
1730                         luid_attrs[i].luid.low = privileges.set[i].luid.low;
1731                         luid_attrs[i].luid.high = privileges.set[i].luid.high;
1732                         luid_attrs[i].attribute = privileges.set[i].attr;
1733                 }
1734
1735                 priv_set->count = privileges.count;
1736                 priv_set->unknown = 0;
1737                 priv_set->set = luid_attrs;
1738
1739         } else {
1740                 priv_set->count = 0;
1741                 priv_set->unknown = 0;
1742                 priv_set->set = NULL;
1743         }
1744
1745         *r->out.privs = priv_set;
1746
1747  done:
1748         privilege_set_free( &privileges );
1749
1750         return status;
1751 }
1752
1753 /***************************************************************************
1754  _lsa_GetSystemAccessAccount
1755  ***************************************************************************/
1756
1757 NTSTATUS _lsa_GetSystemAccessAccount(pipes_struct *p,
1758                                      struct lsa_GetSystemAccessAccount *r)
1759 {
1760         NTSTATUS status;
1761         struct lsa_info *info = NULL;
1762         struct lsa_EnumPrivsAccount e;
1763         struct lsa_PrivilegeSet *privset;
1764
1765         /* find the connection policy handle. */
1766
1767         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&info))
1768                 return NT_STATUS_INVALID_HANDLE;
1769
1770         if (info->type != LSA_HANDLE_ACCOUNT_TYPE) {
1771                 return NT_STATUS_INVALID_HANDLE;
1772         }
1773
1774         if (!(info->access & LSA_ACCOUNT_VIEW))
1775                 return NT_STATUS_ACCESS_DENIED;
1776
1777         privset = talloc_zero(p->mem_ctx, struct lsa_PrivilegeSet);
1778         if (!privset) {
1779                 return NT_STATUS_NO_MEMORY;
1780         }
1781
1782         e.in.handle = r->in.handle;
1783         e.out.privs = &privset;
1784
1785         status = _lsa_EnumPrivsAccount(p, &e);
1786         if (!NT_STATUS_IS_OK(status)) {
1787                 DEBUG(10,("_lsa_GetSystemAccessAccount: "
1788                         "failed to call _lsa_EnumPrivsAccount(): %s\n",
1789                         nt_errstr(status)));
1790                 return status;
1791         }
1792
1793         /* Samba4 would iterate over the privset to merge the policy mode bits,
1794          * not sure samba3 can do the same here, so just return what we did in
1795          * the past - gd */
1796
1797         /*
1798           0x01 -> Log on locally
1799           0x02 -> Access this computer from network
1800           0x04 -> Log on as a batch job
1801           0x10 -> Log on as a service
1802
1803           they can be ORed together
1804         */
1805
1806         *r->out.access_mask = LSA_POLICY_MODE_INTERACTIVE |
1807                               LSA_POLICY_MODE_NETWORK;
1808
1809         return NT_STATUS_OK;
1810 }
1811
1812 /***************************************************************************
1813   update the systemaccount information
1814  ***************************************************************************/
1815
1816 NTSTATUS _lsa_SetSystemAccessAccount(pipes_struct *p,
1817                                      struct lsa_SetSystemAccessAccount *r)
1818 {
1819         struct lsa_info *info=NULL;
1820         GROUP_MAP map;
1821
1822         /* find the connection policy handle. */
1823         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&info))
1824                 return NT_STATUS_INVALID_HANDLE;
1825
1826         if (info->type != LSA_HANDLE_ACCOUNT_TYPE) {
1827                 return NT_STATUS_INVALID_HANDLE;
1828         }
1829
1830         if (!(info->access & LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS)) {
1831                 return NT_STATUS_ACCESS_DENIED;
1832         }
1833
1834         if (!pdb_getgrsid(&map, info->sid))
1835                 return NT_STATUS_NO_SUCH_GROUP;
1836
1837         return pdb_update_group_mapping_entry(&map);
1838 }
1839
1840 /***************************************************************************
1841  _lsa_AddPrivilegesToAccount
1842  For a given SID, add some privileges.
1843  ***************************************************************************/
1844
1845 NTSTATUS _lsa_AddPrivilegesToAccount(pipes_struct *p,
1846                                      struct lsa_AddPrivilegesToAccount *r)
1847 {
1848         struct lsa_info *info = NULL;
1849         SE_PRIV mask;
1850         struct lsa_PrivilegeSet *set = NULL;
1851
1852         /* find the connection policy handle. */
1853         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&info))
1854                 return NT_STATUS_INVALID_HANDLE;
1855
1856         if (info->type != LSA_HANDLE_ACCOUNT_TYPE) {
1857                 return NT_STATUS_INVALID_HANDLE;
1858         }
1859
1860         if (!(info->access & LSA_ACCOUNT_ADJUST_PRIVILEGES)) {
1861                 return NT_STATUS_ACCESS_DENIED;
1862         }
1863
1864         set = r->in.privs;
1865         if ( !privilege_set_to_se_priv( &mask, set ) )
1866                 return NT_STATUS_NO_SUCH_PRIVILEGE;
1867
1868         if ( !grant_privilege( &info->sid, &mask ) ) {
1869                 DEBUG(3,("_lsa_AddPrivilegesToAccount: grant_privilege(%s) failed!\n",
1870                          sid_string_dbg(&info->sid) ));
1871                 DEBUG(3,("Privilege mask:\n"));
1872                 dump_se_priv( DBGC_ALL, 3, &mask );
1873                 return NT_STATUS_NO_SUCH_PRIVILEGE;
1874         }
1875
1876         return NT_STATUS_OK;
1877 }
1878
1879 /***************************************************************************
1880  _lsa_RemovePrivilegesFromAccount
1881  For a given SID, remove some privileges.
1882  ***************************************************************************/
1883
1884 NTSTATUS _lsa_RemovePrivilegesFromAccount(pipes_struct *p,
1885                                           struct lsa_RemovePrivilegesFromAccount *r)
1886 {
1887         struct lsa_info *info = NULL;
1888         SE_PRIV mask;
1889         struct lsa_PrivilegeSet *set = NULL;
1890
1891         /* find the connection policy handle. */
1892         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&info))
1893                 return NT_STATUS_INVALID_HANDLE;
1894
1895         if (info->type != LSA_HANDLE_ACCOUNT_TYPE) {
1896                 return NT_STATUS_INVALID_HANDLE;
1897         }
1898
1899         if (!(info->access & LSA_ACCOUNT_ADJUST_PRIVILEGES)) {
1900                 return NT_STATUS_ACCESS_DENIED;
1901         }
1902
1903         set = r->in.privs;
1904
1905         if ( !privilege_set_to_se_priv( &mask, set ) )
1906                 return NT_STATUS_NO_SUCH_PRIVILEGE;
1907
1908         if ( !revoke_privilege( &info->sid, &mask ) ) {
1909                 DEBUG(3,("_lsa_RemovePrivilegesFromAccount: revoke_privilege(%s) failed!\n",
1910                          sid_string_dbg(&info->sid) ));
1911                 DEBUG(3,("Privilege mask:\n"));
1912                 dump_se_priv( DBGC_ALL, 3, &mask );
1913                 return NT_STATUS_NO_SUCH_PRIVILEGE;
1914         }
1915
1916         return NT_STATUS_OK;
1917 }
1918
1919 /***************************************************************************
1920  _lsa_QuerySecurity
1921  ***************************************************************************/
1922
1923 NTSTATUS _lsa_QuerySecurity(pipes_struct *p,
1924                             struct lsa_QuerySecurity *r)
1925 {
1926         struct lsa_info *handle=NULL;
1927         SEC_DESC *psd = NULL;
1928         size_t sd_size;
1929         NTSTATUS status;
1930
1931         /* find the connection policy handle. */
1932         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&handle))
1933                 return NT_STATUS_INVALID_HANDLE;
1934
1935         if (handle->type == LSA_HANDLE_POLICY_TYPE) {
1936                 status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size,
1937                                 &lsa_policy_mapping, NULL, 0);
1938         } else if (handle->type == LSA_HANDLE_ACCOUNT_TYPE) {
1939                 status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size,
1940                                 &lsa_account_mapping,
1941                                 &handle->sid, LSA_ACCOUNT_ALL_ACCESS);
1942         } else {
1943                 status = NT_STATUS_INVALID_HANDLE;
1944         }
1945
1946         if (!NT_STATUS_IS_OK(status)) {
1947                 return status;
1948         }
1949
1950         switch (r->in.sec_info) {
1951         case 1:
1952                 /* SD contains only the owner */
1953                 if((*r->out.sdbuf = make_sec_desc_buf(p->mem_ctx, sd_size, psd)) == NULL)
1954                         return NT_STATUS_NO_MEMORY;
1955                 break;
1956         case 4:
1957                 /* SD contains only the ACL */
1958                 if((*r->out.sdbuf = make_sec_desc_buf(p->mem_ctx, sd_size, psd)) == NULL)
1959                         return NT_STATUS_NO_MEMORY;
1960                 break;
1961         default:
1962                 return NT_STATUS_INVALID_LEVEL;
1963         }
1964
1965         return status;
1966 }
1967
1968 /***************************************************************************
1969  _lsa_AddAccountRights
1970  ***************************************************************************/
1971
1972 NTSTATUS _lsa_AddAccountRights(pipes_struct *p,
1973                                struct lsa_AddAccountRights *r)
1974 {
1975         struct lsa_info *info = NULL;
1976         int i = 0;
1977         uint32_t acc_granted = 0;
1978         SEC_DESC *psd = NULL;
1979         size_t sd_size;
1980         DOM_SID sid;
1981         NTSTATUS status;
1982
1983         /* find the connection policy handle. */
1984         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&info))
1985                 return NT_STATUS_INVALID_HANDLE;
1986
1987         if (info->type != LSA_HANDLE_POLICY_TYPE) {
1988                 return NT_STATUS_INVALID_HANDLE;
1989         }
1990
1991         /* get the generic lsa account SD for this SID until we store it */
1992         status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size,
1993                                 &lsa_account_mapping,
1994                                 r->in.sid, LSA_ACCOUNT_ALL_ACCESS);
1995         if (!NT_STATUS_IS_OK(status)) {
1996                 return status;
1997         }
1998
1999         /*
2000          * From the MS DOCs. If the sid doesn't exist, ask for LSA_POLICY_CREATE_ACCOUNT
2001          * on the policy handle. If it does, ask for
2002          * LSA_ACCOUNT_ADJUST_PRIVILEGES|LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS|LSA_ACCOUNT_VIEW,
2003          * on the account sid. We don't check here so just use the latter. JRA.
2004          */
2005
2006         status = access_check_object(psd, p->server_info->ptok,
2007                 NULL, 0, LSA_ACCOUNT_ADJUST_PRIVILEGES|LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS|LSA_ACCOUNT_VIEW,
2008                 &acc_granted, "_lsa_AddAccountRights" );
2009
2010         if (!NT_STATUS_IS_OK(status)) {
2011                 return status;
2012         }
2013
2014         /* according to an NT4 PDC, you can add privileges to SIDs even without
2015            call_lsa_create_account() first.  And you can use any arbitrary SID. */
2016
2017         sid_copy( &sid, r->in.sid );
2018
2019         for ( i=0; i < r->in.rights->count; i++ ) {
2020
2021                 const char *privname = r->in.rights->names[i].string;
2022
2023                 /* only try to add non-null strings */
2024
2025                 if ( !privname )
2026                         continue;
2027
2028                 if ( !grant_privilege_by_name( &sid, privname ) ) {
2029                         DEBUG(2,("_lsa_AddAccountRights: Failed to add privilege [%s]\n",
2030                                 privname ));
2031                         return NT_STATUS_NO_SUCH_PRIVILEGE;
2032                 }
2033         }
2034
2035         return NT_STATUS_OK;
2036 }
2037
2038 /***************************************************************************
2039  _lsa_RemoveAccountRights
2040  ***************************************************************************/
2041
2042 NTSTATUS _lsa_RemoveAccountRights(pipes_struct *p,
2043                                   struct lsa_RemoveAccountRights *r)
2044 {
2045         struct lsa_info *info = NULL;
2046         int i = 0;
2047         SEC_DESC *psd = NULL;
2048         size_t sd_size;
2049         DOM_SID sid;
2050         const char *privname = NULL;
2051         uint32_t acc_granted = 0;
2052         NTSTATUS status;
2053
2054         /* find the connection policy handle. */
2055         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&info))
2056                 return NT_STATUS_INVALID_HANDLE;
2057
2058         if (info->type != LSA_HANDLE_POLICY_TYPE) {
2059                 return NT_STATUS_INVALID_HANDLE;
2060         }
2061
2062         /* get the generic lsa account SD for this SID until we store it */
2063         status = make_lsa_object_sd(p->mem_ctx, &psd, &sd_size,
2064                                 &lsa_account_mapping,
2065                                 r->in.sid, LSA_ACCOUNT_ALL_ACCESS);
2066         if (!NT_STATUS_IS_OK(status)) {
2067                 return status;
2068         }
2069
2070         /*
2071          * From the MS DOCs. We need
2072          * LSA_ACCOUNT_ADJUST_PRIVILEGES|LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS|LSA_ACCOUNT_VIEW
2073          * and DELETE on the account sid.
2074          */
2075
2076         status = access_check_object(psd, p->server_info->ptok,
2077                 NULL, 0, LSA_ACCOUNT_ADJUST_PRIVILEGES|LSA_ACCOUNT_ADJUST_SYSTEM_ACCESS|
2078                         LSA_ACCOUNT_VIEW|STD_RIGHT_DELETE_ACCESS,
2079                 &acc_granted, "_lsa_AddAccountRights" );
2080
2081         if (!NT_STATUS_IS_OK(status)) {
2082                 return status;
2083         }
2084
2085         sid_copy( &sid, r->in.sid );
2086
2087         if ( r->in.remove_all ) {
2088                 if ( !revoke_all_privileges( &sid ) )
2089                         return NT_STATUS_ACCESS_DENIED;
2090
2091                 return NT_STATUS_OK;
2092         }
2093
2094         for ( i=0; i < r->in.rights->count; i++ ) {
2095
2096                 privname = r->in.rights->names[i].string;
2097
2098                 /* only try to add non-null strings */
2099
2100                 if ( !privname )
2101                         continue;
2102
2103                 if ( !revoke_privilege_by_name( &sid, privname ) ) {
2104                         DEBUG(2,("_lsa_RemoveAccountRights: Failed to revoke privilege [%s]\n",
2105                                 privname ));
2106                         return NT_STATUS_NO_SUCH_PRIVILEGE;
2107                 }
2108         }
2109
2110         return NT_STATUS_OK;
2111 }
2112
2113 /*******************************************************************
2114 ********************************************************************/
2115
2116 static NTSTATUS init_lsa_right_set(TALLOC_CTX *mem_ctx,
2117                                    struct lsa_RightSet *r,
2118                                    PRIVILEGE_SET *privileges)
2119 {
2120         uint32 i;
2121         const char *privname;
2122         const char **privname_array = NULL;
2123         int num_priv = 0;
2124
2125         for (i=0; i<privileges->count; i++) {
2126
2127                 privname = luid_to_privilege_name(&privileges->set[i].luid);
2128                 if (privname) {
2129                         if (!add_string_to_array(mem_ctx, privname,
2130                                                  &privname_array, &num_priv)) {
2131                                 return NT_STATUS_NO_MEMORY;
2132                         }
2133                 }
2134         }
2135
2136         if (num_priv) {
2137
2138                 r->names = TALLOC_ZERO_ARRAY(mem_ctx, struct lsa_StringLarge,
2139                                              num_priv);
2140                 if (!r->names) {
2141                         return NT_STATUS_NO_MEMORY;
2142                 }
2143
2144                 for (i=0; i<num_priv; i++) {
2145                         init_lsa_StringLarge(&r->names[i], privname_array[i]);
2146                 }
2147
2148                 r->count = num_priv;
2149         }
2150
2151         return NT_STATUS_OK;
2152 }
2153
2154 /***************************************************************************
2155  _lsa_EnumAccountRights
2156  ***************************************************************************/
2157
2158 NTSTATUS _lsa_EnumAccountRights(pipes_struct *p,
2159                                 struct lsa_EnumAccountRights *r)
2160 {
2161         NTSTATUS status;
2162         struct lsa_info *info = NULL;
2163         DOM_SID sid;
2164         PRIVILEGE_SET privileges;
2165         SE_PRIV mask;
2166
2167         /* find the connection policy handle. */
2168
2169         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&info))
2170                 return NT_STATUS_INVALID_HANDLE;
2171
2172         if (info->type != LSA_HANDLE_POLICY_TYPE) {
2173                 return NT_STATUS_INVALID_HANDLE;
2174         }
2175
2176         if (!(info->access & LSA_ACCOUNT_VIEW)) {
2177                 return NT_STATUS_ACCESS_DENIED;
2178         }
2179
2180         /* according to an NT4 PDC, you can add privileges to SIDs even without
2181            call_lsa_create_account() first.  And you can use any arbitrary SID. */
2182
2183         sid_copy( &sid, r->in.sid );
2184
2185         /* according to MS-LSAD 3.1.4.5.10 it is required to return
2186          * NT_STATUS_OBJECT_NAME_NOT_FOUND if the account sid was not found in
2187          * the lsa database */
2188
2189         if (!get_privileges_for_sids(&mask, &sid, 1)) {
2190                 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
2191         }
2192
2193         status = privilege_set_init(&privileges);
2194         if (!NT_STATUS_IS_OK(status)) {
2195                 return status;
2196         }
2197
2198         se_priv_to_privilege_set(&privileges, &mask);
2199
2200         DEBUG(10,("_lsa_EnumAccountRights: %s has %d privileges\n",
2201                   sid_string_dbg(&sid), privileges.count));
2202
2203         status = init_lsa_right_set(p->mem_ctx, r->out.rights, &privileges);
2204
2205         privilege_set_free( &privileges );
2206
2207         return status;
2208 }
2209
2210 /***************************************************************************
2211  _lsa_LookupPrivValue
2212  ***************************************************************************/
2213
2214 NTSTATUS _lsa_LookupPrivValue(pipes_struct *p,
2215                               struct lsa_LookupPrivValue *r)
2216 {
2217         struct lsa_info *info = NULL;
2218         const char *name = NULL;
2219         LUID_ATTR priv_luid;
2220         SE_PRIV mask;
2221
2222         /* find the connection policy handle. */
2223
2224         if (!find_policy_by_hnd(p, r->in.handle, (void **)(void *)&info))
2225                 return NT_STATUS_INVALID_HANDLE;
2226
2227         if (info->type != LSA_HANDLE_POLICY_TYPE) {
2228                 return NT_STATUS_INVALID_HANDLE;
2229         }
2230
2231         if (!(info->access & LSA_POLICY_LOOKUP_NAMES))
2232                 return NT_STATUS_ACCESS_DENIED;
2233
2234         name = r->in.name->string;
2235
2236         DEBUG(10,("_lsa_lookup_priv_value: name = %s\n", name));
2237
2238         if ( !se_priv_from_name( name, &mask ) )
2239                 return NT_STATUS_NO_SUCH_PRIVILEGE;
2240
2241         priv_luid = get_privilege_luid( &mask );
2242
2243         r->out.luid->low = priv_luid.luid.low;
2244         r->out.luid->high = priv_luid.luid.high;
2245
2246         return NT_STATUS_OK;
2247 }
2248
2249 /*
2250  * From here on the server routines are just dummy ones to make smbd link with
2251  * librpc/gen_ndr/srv_lsa.c. These routines are actually never called, we are
2252  * pulling the server stubs across one by one.
2253  */
2254
2255 NTSTATUS _lsa_Delete(pipes_struct *p, struct lsa_Delete *r)
2256 {
2257         p->rng_fault_state = True;
2258         return NT_STATUS_NOT_IMPLEMENTED;
2259 }
2260
2261 NTSTATUS _lsa_SetSecObj(pipes_struct *p, struct lsa_SetSecObj *r)
2262 {
2263         p->rng_fault_state = True;
2264         return NT_STATUS_NOT_IMPLEMENTED;
2265 }
2266
2267 NTSTATUS _lsa_ChangePassword(pipes_struct *p, struct lsa_ChangePassword *r)
2268 {
2269         p->rng_fault_state = True;
2270         return NT_STATUS_NOT_IMPLEMENTED;
2271 }
2272
2273 NTSTATUS _lsa_SetInfoPolicy(pipes_struct *p, struct lsa_SetInfoPolicy *r)
2274 {
2275         p->rng_fault_state = True;
2276         return NT_STATUS_NOT_IMPLEMENTED;
2277 }
2278
2279 NTSTATUS _lsa_ClearAuditLog(pipes_struct *p, struct lsa_ClearAuditLog *r)
2280 {
2281         p->rng_fault_state = True;
2282         return NT_STATUS_NOT_IMPLEMENTED;
2283 }
2284
2285 NTSTATUS _lsa_GetQuotasForAccount(pipes_struct *p, struct lsa_GetQuotasForAccount *r)
2286 {
2287         p->rng_fault_state = True;
2288         return NT_STATUS_NOT_IMPLEMENTED;
2289 }
2290
2291 NTSTATUS _lsa_SetQuotasForAccount(pipes_struct *p, struct lsa_SetQuotasForAccount *r)
2292 {
2293         p->rng_fault_state = True;
2294         return NT_STATUS_NOT_IMPLEMENTED;
2295 }
2296
2297 NTSTATUS _lsa_QueryTrustedDomainInfo(pipes_struct *p, struct lsa_QueryTrustedDomainInfo *r)
2298 {
2299         p->rng_fault_state = True;
2300         return NT_STATUS_NOT_IMPLEMENTED;
2301 }
2302
2303 NTSTATUS _lsa_SetInformationTrustedDomain(pipes_struct *p, struct lsa_SetInformationTrustedDomain *r)
2304 {
2305         p->rng_fault_state = True;
2306         return NT_STATUS_NOT_IMPLEMENTED;
2307 }
2308
2309 NTSTATUS _lsa_QuerySecret(pipes_struct *p, struct lsa_QuerySecret *r)
2310 {
2311         p->rng_fault_state = True;
2312         return NT_STATUS_NOT_IMPLEMENTED;
2313 }
2314
2315 NTSTATUS _lsa_LookupPrivName(pipes_struct *p, struct lsa_LookupPrivName *r)
2316 {
2317         p->rng_fault_state = True;
2318         return NT_STATUS_NOT_IMPLEMENTED;
2319 }
2320
2321 NTSTATUS _lsa_EnumAccountsWithUserRight(pipes_struct *p, struct lsa_EnumAccountsWithUserRight *r)
2322 {
2323         p->rng_fault_state = True;
2324         return NT_STATUS_NOT_IMPLEMENTED;
2325 }
2326
2327 NTSTATUS _lsa_QueryTrustedDomainInfoBySid(pipes_struct *p, struct lsa_QueryTrustedDomainInfoBySid *r)
2328 {
2329         p->rng_fault_state = True;
2330         return NT_STATUS_NOT_IMPLEMENTED;
2331 }
2332
2333 NTSTATUS _lsa_SetTrustedDomainInfo(pipes_struct *p, struct lsa_SetTrustedDomainInfo *r)
2334 {
2335         p->rng_fault_state = True;
2336         return NT_STATUS_NOT_IMPLEMENTED;
2337 }
2338
2339 NTSTATUS _lsa_DeleteTrustedDomain(pipes_struct *p, struct lsa_DeleteTrustedDomain *r)
2340 {
2341         p->rng_fault_state = True;
2342         return NT_STATUS_NOT_IMPLEMENTED;
2343 }
2344
2345 NTSTATUS _lsa_StorePrivateData(pipes_struct *p, struct lsa_StorePrivateData *r)
2346 {
2347         p->rng_fault_state = True;
2348         return NT_STATUS_NOT_IMPLEMENTED;
2349 }
2350
2351 NTSTATUS _lsa_RetrievePrivateData(pipes_struct *p, struct lsa_RetrievePrivateData *r)
2352 {
2353         p->rng_fault_state = True;
2354         return NT_STATUS_NOT_IMPLEMENTED;
2355 }
2356
2357 NTSTATUS _lsa_QueryInfoPolicy2(pipes_struct *p,
2358                                struct lsa_QueryInfoPolicy2 *r2)
2359 {
2360         struct lsa_QueryInfoPolicy r;
2361
2362         if ((pdb_capabilities() & PDB_CAP_ADS) == 0) {
2363                 p->rng_fault_state = True;
2364                 return NT_STATUS_NOT_IMPLEMENTED;
2365         }
2366
2367         ZERO_STRUCT(r);
2368         r.in.handle = r2->in.handle;
2369         r.in.level = r2->in.level;
2370         r.out.info = r2->out.info;
2371
2372         return _lsa_QueryInfoPolicy(p, &r);
2373 }
2374
2375 NTSTATUS _lsa_SetInfoPolicy2(pipes_struct *p, struct lsa_SetInfoPolicy2 *r)
2376 {
2377         p->rng_fault_state = True;
2378         return NT_STATUS_NOT_IMPLEMENTED;
2379 }
2380
2381 NTSTATUS _lsa_QueryTrustedDomainInfoByName(pipes_struct *p, struct lsa_QueryTrustedDomainInfoByName *r)
2382 {
2383         p->rng_fault_state = True;
2384         return NT_STATUS_NOT_IMPLEMENTED;
2385 }
2386
2387 NTSTATUS _lsa_SetTrustedDomainInfoByName(pipes_struct *p, struct lsa_SetTrustedDomainInfoByName *r)
2388 {
2389         p->rng_fault_state = True;
2390         return NT_STATUS_NOT_IMPLEMENTED;
2391 }
2392
2393 NTSTATUS _lsa_EnumTrustedDomainsEx(pipes_struct *p, struct lsa_EnumTrustedDomainsEx *r)
2394 {
2395         p->rng_fault_state = True;
2396         return NT_STATUS_NOT_IMPLEMENTED;
2397 }
2398
2399 NTSTATUS _lsa_CreateTrustedDomainEx(pipes_struct *p, struct lsa_CreateTrustedDomainEx *r)
2400 {
2401         p->rng_fault_state = True;
2402         return NT_STATUS_NOT_IMPLEMENTED;
2403 }
2404
2405 NTSTATUS _lsa_CloseTrustedDomainEx(pipes_struct *p, struct lsa_CloseTrustedDomainEx *r)
2406 {
2407         p->rng_fault_state = True;
2408         return NT_STATUS_NOT_IMPLEMENTED;
2409 }
2410
2411 NTSTATUS _lsa_QueryDomainInformationPolicy(pipes_struct *p, struct lsa_QueryDomainInformationPolicy *r)
2412 {
2413         p->rng_fault_state = True;
2414         return NT_STATUS_NOT_IMPLEMENTED;
2415 }
2416
2417 NTSTATUS _lsa_SetDomainInformationPolicy(pipes_struct *p, struct lsa_SetDomainInformationPolicy *r)
2418 {
2419         p->rng_fault_state = True;
2420         return NT_STATUS_NOT_IMPLEMENTED;
2421 }
2422
2423 NTSTATUS _lsa_OpenTrustedDomainByName(pipes_struct *p, struct lsa_OpenTrustedDomainByName *r)
2424 {
2425         p->rng_fault_state = True;
2426         return NT_STATUS_NOT_IMPLEMENTED;
2427 }
2428
2429 NTSTATUS _lsa_TestCall(pipes_struct *p, struct lsa_TestCall *r)
2430 {
2431         p->rng_fault_state = True;
2432         return NT_STATUS_NOT_IMPLEMENTED;
2433 }
2434
2435 NTSTATUS _lsa_CreateTrustedDomainEx2(pipes_struct *p, struct lsa_CreateTrustedDomainEx2 *r)
2436 {
2437         p->rng_fault_state = True;
2438         return NT_STATUS_NOT_IMPLEMENTED;
2439 }
2440
2441 NTSTATUS _lsa_CREDRWRITE(pipes_struct *p, struct lsa_CREDRWRITE *r)
2442 {
2443         p->rng_fault_state = True;
2444         return NT_STATUS_NOT_IMPLEMENTED;
2445 }
2446
2447 NTSTATUS _lsa_CREDRREAD(pipes_struct *p, struct lsa_CREDRREAD *r)
2448 {
2449         p->rng_fault_state = True;
2450         return NT_STATUS_NOT_IMPLEMENTED;
2451 }
2452
2453 NTSTATUS _lsa_CREDRENUMERATE(pipes_struct *p, struct lsa_CREDRENUMERATE *r)
2454 {
2455         p->rng_fault_state = True;
2456         return NT_STATUS_NOT_IMPLEMENTED;
2457 }
2458
2459 NTSTATUS _lsa_CREDRWRITEDOMAINCREDENTIALS(pipes_struct *p, struct lsa_CREDRWRITEDOMAINCREDENTIALS *r)
2460 {
2461         p->rng_fault_state = True;
2462         return NT_STATUS_NOT_IMPLEMENTED;
2463 }
2464
2465 NTSTATUS _lsa_CREDRREADDOMAINCREDENTIALS(pipes_struct *p, struct lsa_CREDRREADDOMAINCREDENTIALS *r)
2466 {
2467         p->rng_fault_state = True;
2468         return NT_STATUS_NOT_IMPLEMENTED;
2469 }
2470
2471 NTSTATUS _lsa_CREDRDELETE(pipes_struct *p, struct lsa_CREDRDELETE *r)
2472 {
2473         p->rng_fault_state = True;
2474         return NT_STATUS_NOT_IMPLEMENTED;
2475 }
2476
2477 NTSTATUS _lsa_CREDRGETTARGETINFO(pipes_struct *p, struct lsa_CREDRGETTARGETINFO *r)
2478 {
2479         p->rng_fault_state = True;
2480         return NT_STATUS_NOT_IMPLEMENTED;
2481 }
2482
2483 NTSTATUS _lsa_CREDRPROFILELOADED(pipes_struct *p, struct lsa_CREDRPROFILELOADED *r)
2484 {
2485         p->rng_fault_state = True;
2486         return NT_STATUS_NOT_IMPLEMENTED;
2487 }
2488
2489 NTSTATUS _lsa_CREDRGETSESSIONTYPES(pipes_struct *p, struct lsa_CREDRGETSESSIONTYPES *r)
2490 {
2491         p->rng_fault_state = True;
2492         return NT_STATUS_NOT_IMPLEMENTED;
2493 }
2494
2495 NTSTATUS _lsa_LSARREGISTERAUDITEVENT(pipes_struct *p, struct lsa_LSARREGISTERAUDITEVENT *r)
2496 {
2497         p->rng_fault_state = True;
2498         return NT_STATUS_NOT_IMPLEMENTED;
2499 }
2500
2501 NTSTATUS _lsa_LSARGENAUDITEVENT(pipes_struct *p, struct lsa_LSARGENAUDITEVENT *r)
2502 {
2503         p->rng_fault_state = True;
2504         return NT_STATUS_NOT_IMPLEMENTED;
2505 }
2506
2507 NTSTATUS _lsa_LSARUNREGISTERAUDITEVENT(pipes_struct *p, struct lsa_LSARUNREGISTERAUDITEVENT *r)
2508 {
2509         p->rng_fault_state = True;
2510         return NT_STATUS_NOT_IMPLEMENTED;
2511 }
2512
2513 NTSTATUS _lsa_lsaRQueryForestTrustInformation(pipes_struct *p, struct lsa_lsaRQueryForestTrustInformation *r)
2514 {
2515         p->rng_fault_state = True;
2516         return NT_STATUS_NOT_IMPLEMENTED;
2517 }
2518
2519 NTSTATUS _lsa_LSARSETFORESTTRUSTINFORMATION(pipes_struct *p, struct lsa_LSARSETFORESTTRUSTINFORMATION *r)
2520 {
2521         p->rng_fault_state = True;
2522         return NT_STATUS_NOT_IMPLEMENTED;
2523 }
2524
2525 NTSTATUS _lsa_CREDRRENAME(pipes_struct *p, struct lsa_CREDRRENAME *r)
2526 {
2527         p->rng_fault_state = True;
2528         return NT_STATUS_NOT_IMPLEMENTED;
2529 }
2530
2531 NTSTATUS _lsa_LSAROPENPOLICYSCE(pipes_struct *p, struct lsa_LSAROPENPOLICYSCE *r)
2532 {
2533         p->rng_fault_state = True;
2534         return NT_STATUS_NOT_IMPLEMENTED;
2535 }
2536
2537 NTSTATUS _lsa_LSARADTREGISTERSECURITYEVENTSOURCE(pipes_struct *p, struct lsa_LSARADTREGISTERSECURITYEVENTSOURCE *r)
2538 {
2539         p->rng_fault_state = True;
2540         return NT_STATUS_NOT_IMPLEMENTED;
2541 }
2542
2543 NTSTATUS _lsa_LSARADTUNREGISTERSECURITYEVENTSOURCE(pipes_struct *p, struct lsa_LSARADTUNREGISTERSECURITYEVENTSOURCE *r)
2544 {
2545         p->rng_fault_state = True;
2546         return NT_STATUS_NOT_IMPLEMENTED;
2547 }
2548
2549 NTSTATUS _lsa_LSARADTREPORTSECURITYEVENT(pipes_struct *p, struct lsa_LSARADTREPORTSECURITYEVENT *r)
2550 {
2551         p->rng_fault_state = True;
2552         return NT_STATUS_NOT_IMPLEMENTED;
2553 }