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