2 Unix SMB/CIFS implementation.
4 endpoint server for the lsarpc pipe
6 Copyright (C) Andrew Tridgell 2004
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
24 #include "librpc/gen_ndr/ndr_lsa.h"
25 #include "librpc/gen_ndr/ndr_samr.h"
26 #include "rpc_server/dcerpc_server.h"
27 #include "rpc_server/common/common.h"
28 #include "lib/ldb/include/ldb.h"
31 this type allows us to distinguish handle types
40 state associated with a lsa_OpenPolicy() operation
42 struct lsa_policy_state {
44 struct sidmap_context *sidmap;
46 const char *domain_dn;
47 const char *builtin_dn;
48 const char *domain_name;
49 struct dom_sid *domain_sid;
50 struct dom_sid *builtin_sid;
55 state associated with a lsa_OpenAccount() operation
57 struct lsa_account_state {
58 struct lsa_policy_state *policy;
60 struct dom_sid *account_sid;
61 const char *account_sid_str;
62 const char *account_name;
67 destroy an open policy. This closes the database connection
69 static void lsa_Policy_destroy(struct dcesrv_connection *conn, struct dcesrv_handle *h)
71 struct lsa_policy_state *state = h->data;
76 destroy an open account.
78 static void lsa_Account_destroy(struct dcesrv_connection *conn, struct dcesrv_handle *h)
80 struct lsa_account_state *astate = h->data;
87 static NTSTATUS lsa_Close(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
90 struct dcesrv_handle *h;
92 *r->out.handle = *r->in.handle;
94 DCESRV_PULL_HANDLE(h, r->in.handle, DCESRV_HANDLE_ANY);
96 /* this causes the callback samr_XXX_destroy() to be called by
97 the handle destroy code which destroys the state associated
99 dcesrv_handle_destroy(dce_call->conn, h);
101 ZERO_STRUCTP(r->out.handle);
110 static NTSTATUS lsa_Delete(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
111 struct lsa_Delete *r)
113 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
120 static NTSTATUS lsa_EnumPrivs(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
121 struct lsa_EnumPrivs *r)
123 struct dcesrv_handle *h;
124 struct lsa_policy_state *state;
126 const char *privname;
128 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
132 i = *r->in.resume_handle;
135 while ((privname = sec_privilege_name(i)) &&
136 r->out.privs->count < r->in.max_count) {
137 struct lsa_PrivEntry *e;
139 r->out.privs->privs = talloc_realloc_p(r->out.privs,
141 struct lsa_PrivEntry,
142 r->out.privs->count+1);
143 if (r->out.privs->privs == NULL) {
144 return NT_STATUS_NO_MEMORY;
146 e = &r->out.privs->privs[r->out.privs->count];
149 e->name.string = privname;
150 r->out.privs->count++;
154 *r->in.resume_handle = i;
163 static NTSTATUS lsa_QuerySecurity(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
164 struct lsa_QuerySecurity *r)
166 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
173 static NTSTATUS lsa_SetSecObj(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
174 struct lsa_SetSecObj *r)
176 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
183 static NTSTATUS lsa_ChangePassword(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
184 struct lsa_ChangePassword *r)
186 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
193 static NTSTATUS lsa_OpenPolicy2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
194 struct lsa_OpenPolicy2 *r)
196 struct lsa_policy_state *state;
197 struct dcesrv_handle *handle;
200 ZERO_STRUCTP(r->out.handle);
202 state = talloc_p(dce_call->conn, struct lsa_policy_state);
204 return NT_STATUS_NO_MEMORY;
207 /* make sure the sam database is accessible */
208 state->sam_ctx = samdb_connect(state);
209 if (state->sam_ctx == NULL) {
211 return NT_STATUS_INVALID_SYSTEM_SERVICE;
214 state->sidmap = sidmap_open(state);
215 if (state->sidmap == NULL) {
217 return NT_STATUS_INVALID_SYSTEM_SERVICE;
220 /* work out the domain_dn - useful for so many calls its worth
222 state->domain_dn = samdb_search_string(state->sam_ctx, state, NULL,
223 "dn", "(&(objectClass=domain)(!(objectclass=builtinDomain)))");
224 if (!state->domain_dn) {
226 return NT_STATUS_NO_SUCH_DOMAIN;
229 /* work out the builtin_dn - useful for so many calls its worth
231 state->builtin_dn = samdb_search_string(state->sam_ctx, state, NULL,
232 "dn", "objectClass=builtinDomain");
233 if (!state->builtin_dn) {
235 return NT_STATUS_NO_SUCH_DOMAIN;
238 sid_str = samdb_search_string(state->sam_ctx, state, NULL,
239 "objectSid", "dn=%s", state->domain_dn);
242 return NT_STATUS_NO_SUCH_DOMAIN;
245 state->domain_sid = dom_sid_parse_talloc(state, sid_str);
246 if (!state->domain_sid) {
248 return NT_STATUS_NO_SUCH_DOMAIN;
251 state->builtin_sid = dom_sid_parse_talloc(state, SID_BUILTIN);
252 if (!state->builtin_sid) {
254 return NT_STATUS_NO_SUCH_DOMAIN;
257 state->domain_name = samdb_search_string(state->sam_ctx, state, NULL,
258 "name", "dn=%s", state->domain_dn);
259 if (!state->domain_name) {
261 return NT_STATUS_NO_SUCH_DOMAIN;
265 handle = dcesrv_handle_new(dce_call->conn, LSA_HANDLE_POLICY);
268 return NT_STATUS_NO_MEMORY;
271 handle->data = state;
272 handle->destroy = lsa_Policy_destroy;
274 state->access_mask = r->in.access_mask;
275 *r->out.handle = handle->wire_handle;
277 /* note that we have completely ignored the attr element of
278 the OpenPolicy. As far as I can tell, this is what w2k3
286 a wrapper around lsa_OpenPolicy2
288 static NTSTATUS lsa_OpenPolicy(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
289 struct lsa_OpenPolicy *r)
291 struct lsa_OpenPolicy2 r2;
293 r2.in.system_name = NULL;
294 r2.in.attr = r->in.attr;
295 r2.in.access_mask = r->in.access_mask;
296 r2.out.handle = r->out.handle;
298 return lsa_OpenPolicy2(dce_call, mem_ctx, &r2);
305 fill in the AccountDomain info
307 static NTSTATUS lsa_info_AccountDomain(struct lsa_policy_state *state, TALLOC_CTX *mem_ctx,
308 struct lsa_DomainInfo *info)
310 const char * const attrs[] = { "objectSid", "name", NULL};
312 struct ldb_message **res;
314 ret = samdb_search(state->sam_ctx, mem_ctx, NULL, &res, attrs,
315 "dn=%s", state->domain_dn);
317 return NT_STATUS_INTERNAL_DB_CORRUPTION;
320 info->name.string = samdb_result_string(res[0], "name", NULL);
321 info->sid = samdb_result_dom_sid(mem_ctx, res[0], "objectSid");
327 fill in the DNS domain info
329 static NTSTATUS lsa_info_DNS(struct lsa_policy_state *state, TALLOC_CTX *mem_ctx,
330 struct lsa_DnsDomainInfo *info)
332 const char * const attrs[] = { "name", "dnsDomain", "objectGUID", "objectSid", NULL };
334 struct ldb_message **res;
336 ret = samdb_search(state->sam_ctx, mem_ctx, NULL, &res, attrs,
337 "dn=%s", state->domain_dn);
339 return NT_STATUS_INTERNAL_DB_CORRUPTION;
342 info->name.string = samdb_result_string(res[0], "name", NULL);
343 info->dns_domain.string = samdb_result_string(res[0], "dnsDomain", NULL);
344 info->dns_forest.string = samdb_result_string(res[0], "dnsDomain", NULL);
345 info->domain_guid = samdb_result_guid(res[0], "objectGUID");
346 info->sid = samdb_result_dom_sid(mem_ctx, res[0], "objectSid");
354 static NTSTATUS lsa_QueryInfoPolicy2(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
355 struct lsa_QueryInfoPolicy2 *r)
357 struct lsa_policy_state *state;
358 struct dcesrv_handle *h;
362 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
366 r->out.info = talloc_p(mem_ctx, union lsa_PolicyInformation);
368 return NT_STATUS_NO_MEMORY;
371 ZERO_STRUCTP(r->out.info);
373 switch (r->in.level) {
374 case LSA_POLICY_INFO_DOMAIN:
375 case LSA_POLICY_INFO_ACCOUNT_DOMAIN:
376 return lsa_info_AccountDomain(state, mem_ctx, &r->out.info->account_domain);
378 case LSA_POLICY_INFO_DNS:
379 return lsa_info_DNS(state, mem_ctx, &r->out.info->dns);
382 return NT_STATUS_INVALID_INFO_CLASS;
388 static NTSTATUS lsa_QueryInfoPolicy(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
389 struct lsa_QueryInfoPolicy *r)
391 struct lsa_QueryInfoPolicy2 r2;
394 r2.in.handle = r->in.handle;
395 r2.in.level = r->in.level;
397 status = lsa_QueryInfoPolicy2(dce_call, mem_ctx, &r2);
399 r->out.info = r2.out.info;
407 static NTSTATUS lsa_SetInfoPolicy(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
408 struct lsa_SetInfoPolicy *r)
410 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
417 static NTSTATUS lsa_ClearAuditLog(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
418 struct lsa_ClearAuditLog *r)
420 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
427 static NTSTATUS lsa_CreateAccount(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
428 struct lsa_CreateAccount *r)
430 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
437 static NTSTATUS lsa_EnumAccounts(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
438 struct lsa_EnumAccounts *r)
440 struct dcesrv_handle *h;
441 struct lsa_policy_state *state;
443 struct ldb_message **res;
444 const char * const attrs[] = { "objectSid", NULL};
447 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
451 ret = samdb_search(state->sam_ctx, mem_ctx, state->builtin_dn, &res, attrs, "objectClass=group");
453 return NT_STATUS_NO_SUCH_USER;
456 if (*r->in.resume_handle >= ret) {
457 return NT_STATUS_NO_MORE_ENTRIES;
460 count = ret - *r->in.resume_handle;
461 if (count > r->in.num_entries) {
462 count = r->in.num_entries;
466 return NT_STATUS_NO_MORE_ENTRIES;
469 r->out.sids->sids = talloc_array_p(r->out.sids, struct lsa_SidPtr, count);
470 if (r->out.sids->sids == NULL) {
471 return NT_STATUS_NO_MEMORY;
474 for (i=0;i<count;i++) {
477 sidstr = samdb_result_string(res[i + *r->in.resume_handle], "objectSid", NULL);
478 if (sidstr == NULL) {
479 return NT_STATUS_NO_MEMORY;
481 r->out.sids->sids[i].sid = dom_sid_parse_talloc(r->out.sids->sids, sidstr);
482 if (r->out.sids->sids[i].sid == NULL) {
483 return NT_STATUS_NO_MEMORY;
487 r->out.sids->num_sids = count;
488 *r->out.resume_handle = count + *r->in.resume_handle;
496 lsa_CreateTrustedDomain
498 static NTSTATUS lsa_CreateTrustedDomain(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
499 struct lsa_CreateTrustedDomain *r)
501 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
508 static NTSTATUS lsa_EnumTrustDom(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
509 struct lsa_EnumTrustDom *r)
511 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
516 return the authority name and authority sid, given a sid
518 static NTSTATUS lsa_authority_name(struct lsa_policy_state *state,
519 TALLOC_CTX *mem_ctx, struct dom_sid *sid,
520 const char **authority_name,
521 struct dom_sid **authority_sid)
523 if (dom_sid_in_domain(state->domain_sid, sid)) {
524 *authority_name = state->domain_name;
525 *authority_sid = state->domain_sid;
529 if (dom_sid_in_domain(state->builtin_sid, sid)) {
530 *authority_name = "BUILTIN";
531 *authority_sid = state->builtin_sid;
535 *authority_sid = dom_sid_dup(mem_ctx, sid);
536 if (*authority_sid == NULL) {
537 return NT_STATUS_NO_MEMORY;
539 (*authority_sid)->num_auths = 0;
540 *authority_name = dom_sid_string(mem_ctx, *authority_sid);
541 if (*authority_name == NULL) {
542 return NT_STATUS_NO_MEMORY;
549 add to the lsa_RefDomainList for LookupSids and LookupNames
551 static NTSTATUS lsa_authority_list(struct lsa_policy_state *state, TALLOC_CTX *mem_ctx,
553 struct lsa_RefDomainList *domains,
557 const char *authority_name;
558 struct dom_sid *authority_sid;
561 /* work out the authority name */
562 status = lsa_authority_name(state, mem_ctx, sid,
563 &authority_name, &authority_sid);
564 if (!NT_STATUS_IS_OK(status)) {
568 /* see if we've already done this authority name */
569 for (i=0;i<domains->count;i++) {
570 if (strcmp(authority_name, domains->domains[i].name.string) == 0) {
576 domains->domains = talloc_realloc_p(domains,
578 struct lsa_TrustInformation,
580 if (domains->domains == NULL) {
581 return NT_STATUS_NO_MEMORY;
583 domains->domains[i].name.string = authority_name;
584 domains->domains[i].sid = authority_sid;
592 lookup a name for 1 SID
594 static NTSTATUS lsa_lookup_sid(struct lsa_policy_state *state, TALLOC_CTX *mem_ctx,
595 struct dom_sid *sid, const char *sid_str,
596 const char **name, uint32_t *atype)
599 struct ldb_message **res;
600 const char * const attrs[] = { "sAMAccountName", "sAMAccountType", NULL};
603 ret = samdb_search(state->sam_ctx, mem_ctx, NULL, &res, attrs,
604 "objectSid=%s", sid_str);
606 *name = ldb_msg_find_string(res[0], "sAMAccountName", NULL);
608 return NT_STATUS_NO_MEMORY;
611 *atype = samdb_result_uint(res[0], "sAMAccountType", 0);
616 status = sidmap_allocated_sid_lookup(state->sidmap, mem_ctx, sid, name, atype);
625 static NTSTATUS lsa_LookupSids2(struct dcesrv_call_state *dce_call,
627 struct lsa_LookupSids2 *r)
629 struct lsa_policy_state *state;
630 struct dcesrv_handle *h;
632 NTSTATUS status = NT_STATUS_OK;
634 r->out.domains = NULL;
636 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
640 r->out.domains = talloc_zero_p(mem_ctx, struct lsa_RefDomainList);
641 if (r->out.domains == NULL) {
642 return NT_STATUS_NO_MEMORY;
645 r->out.names = talloc_zero_p(mem_ctx, struct lsa_TransNameArray2);
646 if (r->out.names == NULL) {
647 return NT_STATUS_NO_MEMORY;
652 r->out.names->names = talloc_array_p(r->out.names, struct lsa_TranslatedName2,
653 r->in.sids->num_sids);
654 if (r->out.names->names == NULL) {
655 return NT_STATUS_NO_MEMORY;
658 for (i=0;i<r->in.sids->num_sids;i++) {
659 struct dom_sid *sid = r->in.sids->sids[i].sid;
660 char *sid_str = dom_sid_string(mem_ctx, sid);
662 uint32_t atype, rtype, sid_index;
665 r->out.names->count++;
668 r->out.names->names[i].sid_type = SID_NAME_UNKNOWN;
669 r->out.names->names[i].name.string = sid_str;
670 r->out.names->names[i].sid_index = 0xFFFFFFFF;
671 r->out.names->names[i].unknown = 0;
673 if (sid_str == NULL) {
674 r->out.names->names[i].name.string = "(SIDERROR)";
675 status = STATUS_SOME_UNMAPPED;
679 /* work out the authority name */
680 status2 = lsa_authority_list(state, mem_ctx, sid, r->out.domains, &sid_index);
681 if (!NT_STATUS_IS_OK(status2)) {
685 status2 = lsa_lookup_sid(state, mem_ctx, sid, sid_str,
687 if (!NT_STATUS_IS_OK(status2)) {
688 status = STATUS_SOME_UNMAPPED;
692 rtype = samdb_atype_map(atype);
693 if (rtype == SID_NAME_UNKNOWN) {
694 status = STATUS_SOME_UNMAPPED;
698 r->out.names->names[i].sid_type = rtype;
699 r->out.names->names[i].name.string = name;
700 r->out.names->names[i].sid_index = sid_index;
701 r->out.names->names[i].unknown = 0;
711 static NTSTATUS lsa_LookupSids(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
712 struct lsa_LookupSids *r)
714 struct lsa_LookupSids2 r2;
718 r2.in.handle = r->in.handle;
719 r2.in.sids = r->in.sids;
721 r2.in.level = r->in.level;
722 r2.in.count = r->in.count;
725 r2.out.count = r->out.count;
727 status = lsa_LookupSids2(dce_call, mem_ctx, &r2);
728 if (dce_call->fault_code != 0) {
732 r->out.domains = r2.out.domains;
733 r->out.names = talloc_p(mem_ctx, struct lsa_TransNameArray);
734 if (r->out.names == NULL) {
735 return NT_STATUS_NO_MEMORY;
737 r->out.names->count = r2.out.names->count;
738 r->out.names->names = talloc_array_p(r->out.names, struct lsa_TranslatedName,
739 r->out.names->count);
740 if (r->out.names->names == NULL) {
741 return NT_STATUS_NO_MEMORY;
743 for (i=0;i<r->out.names->count;i++) {
744 r->out.names->names[i].sid_type = r2.out.names->names[i].sid_type;
745 r->out.names->names[i].name.string = r2.out.names->names[i].name.string;
746 r->out.names->names[i].sid_index = r2.out.names->names[i].sid_index;
756 static NTSTATUS lsa_CreateSecret(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
757 struct lsa_CreateSecret *r)
759 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
766 static NTSTATUS lsa_OpenAccount(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
767 struct lsa_OpenAccount *r)
769 struct dcesrv_handle *h, *ah;
770 struct lsa_policy_state *state;
771 struct lsa_account_state *astate;
773 ZERO_STRUCTP(r->out.acct_handle);
775 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
779 astate = talloc_p(dce_call->conn, struct lsa_account_state);
780 if (astate == NULL) {
781 return NT_STATUS_NO_MEMORY;
784 astate->account_sid = dom_sid_dup(astate, r->in.sid);
785 if (astate->account_sid == NULL) {
787 return NT_STATUS_NO_MEMORY;
790 astate->account_sid_str = dom_sid_string(astate, astate->account_sid);
791 if (astate->account_sid_str == NULL) {
793 return NT_STATUS_NO_MEMORY;
796 /* check it really exists */
797 astate->account_name = samdb_search_string(state->sam_ctx, astate,
798 NULL, "sAMAccountName",
799 "objectSid=%s", astate->account_sid_str);
800 if (astate->account_name == NULL) {
802 return NT_STATUS_NO_SUCH_USER;
805 astate->policy = talloc_reference(astate, state);
806 astate->access_mask = r->in.access_mask;
808 ah = dcesrv_handle_new(dce_call->conn, LSA_HANDLE_ACCOUNT);
811 return NT_STATUS_NO_MEMORY;
815 ah->destroy = lsa_Account_destroy;
817 *r->out.acct_handle = ah->wire_handle;
826 static NTSTATUS lsa_EnumPrivsAccount(struct dcesrv_call_state *dce_call,
828 struct lsa_EnumPrivsAccount *r)
830 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
835 lsa_AddPrivilegesToAccount
837 static NTSTATUS lsa_AddPrivilegesToAccount(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
838 struct lsa_AddPrivilegesToAccount *r)
840 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
845 lsa_RemovePrivilegesFromAccount
847 static NTSTATUS lsa_RemovePrivilegesFromAccount(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
848 struct lsa_RemovePrivilegesFromAccount *r)
850 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
855 lsa_GetQuotasForAccount
857 static NTSTATUS lsa_GetQuotasForAccount(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
858 struct lsa_GetQuotasForAccount *r)
860 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
865 lsa_SetQuotasForAccount
867 static NTSTATUS lsa_SetQuotasForAccount(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
868 struct lsa_SetQuotasForAccount *r)
870 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
875 lsa_GetSystemAccessAccount
877 static NTSTATUS lsa_GetSystemAccessAccount(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
878 struct lsa_GetSystemAccessAccount *r)
880 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
885 lsa_SetSystemAccessAccount
887 static NTSTATUS lsa_SetSystemAccessAccount(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
888 struct lsa_SetSystemAccessAccount *r)
890 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
895 lsa_OpenTrustedDomain
897 static NTSTATUS lsa_OpenTrustedDomain(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
898 struct lsa_OpenTrustedDomain *r)
900 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
905 lsa_QueryTrustedDomainInfo
907 static NTSTATUS lsa_QueryTrustedDomainInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
908 struct lsa_QueryTrustedDomainInfo *r)
910 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
915 lsa_SetInformationTrustedDomain
917 static NTSTATUS lsa_SetInformationTrustedDomain(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
918 struct lsa_SetInformationTrustedDomain *r)
920 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
927 static NTSTATUS lsa_OpenSecret(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
928 struct lsa_OpenSecret *r)
930 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
937 static NTSTATUS lsa_SetSecret(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
938 struct lsa_SetSecret *r)
940 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
947 static NTSTATUS lsa_QuerySecret(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
948 struct lsa_QuerySecret *r)
950 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
957 static NTSTATUS lsa_LookupPrivValue(struct dcesrv_call_state *dce_call,
959 struct lsa_LookupPrivValue *r)
961 struct dcesrv_handle *h;
962 struct lsa_policy_state *state;
965 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
969 id = sec_privilege_id(r->in.name->string);
971 return NT_STATUS_NO_SUCH_PRIVILEGE;
974 r->out.luid->low = id;
975 r->out.luid->high = 0;
984 static NTSTATUS lsa_LookupPrivName(struct dcesrv_call_state *dce_call,
986 struct lsa_LookupPrivName *r)
988 struct dcesrv_handle *h;
989 struct lsa_policy_state *state;
990 const char *privname;
992 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
996 if (r->in.luid->high != 0) {
997 return NT_STATUS_NO_SUCH_PRIVILEGE;
1000 privname = sec_privilege_name(r->in.luid->low);
1001 if (privname == NULL) {
1002 return NT_STATUS_NO_SUCH_PRIVILEGE;
1005 r->out.name = talloc_p(mem_ctx, struct lsa_String);
1006 if (r->out.name == NULL) {
1007 return NT_STATUS_NO_MEMORY;
1009 r->out.name->string = privname;
1011 return NT_STATUS_OK;
1016 lsa_LookupPrivDisplayName
1018 static NTSTATUS lsa_LookupPrivDisplayName(struct dcesrv_call_state *dce_call,
1019 TALLOC_CTX *mem_ctx,
1020 struct lsa_LookupPrivDisplayName *r)
1022 struct dcesrv_handle *h;
1023 struct lsa_policy_state *state;
1026 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
1030 id = sec_privilege_id(r->in.name->string);
1032 return NT_STATUS_NO_SUCH_PRIVILEGE;
1035 r->out.disp_name = talloc_p(mem_ctx, struct lsa_String);
1036 if (r->out.disp_name == NULL) {
1037 return NT_STATUS_NO_MEMORY;
1040 r->out.disp_name->string = sec_privilege_display_name(id, r->in.language_id);
1041 if (r->out.disp_name->string == NULL) {
1042 return NT_STATUS_INTERNAL_ERROR;
1045 return NT_STATUS_OK;
1052 static NTSTATUS lsa_DeleteObject(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1053 struct lsa_DeleteObject *r)
1055 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1060 lsa_EnumAccountsWithUserRight
1062 static NTSTATUS lsa_EnumAccountsWithUserRight(struct dcesrv_call_state *dce_call,
1063 TALLOC_CTX *mem_ctx,
1064 struct lsa_EnumAccountsWithUserRight *r)
1066 struct dcesrv_handle *h;
1067 struct lsa_policy_state *state;
1069 struct ldb_message **res;
1070 const char * const attrs[] = { "objectSid", NULL};
1071 const char *privname;
1073 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
1077 if (r->in.name == NULL) {
1078 return NT_STATUS_NO_SUCH_PRIVILEGE;
1081 privname = r->in.name->string;
1082 if (sec_privilege_id(privname) == -1) {
1083 return NT_STATUS_NO_SUCH_PRIVILEGE;
1086 ret = samdb_search(state->sam_ctx, mem_ctx, NULL, &res, attrs,
1087 "privilege=%s", privname);
1089 return NT_STATUS_NO_SUCH_USER;
1092 r->out.sids->sids = talloc_array_p(r->out.sids, struct lsa_SidPtr, ret);
1093 if (r->out.sids->sids == NULL) {
1094 return NT_STATUS_NO_MEMORY;
1096 for (i=0;i<ret;i++) {
1098 sidstr = samdb_result_string(res[i], "objectSid", NULL);
1099 if (sidstr == NULL) {
1100 return NT_STATUS_NO_MEMORY;
1102 r->out.sids->sids[i].sid = dom_sid_parse_talloc(r->out.sids->sids,
1104 if (r->out.sids->sids[i].sid == NULL) {
1105 return NT_STATUS_NO_MEMORY;
1108 r->out.sids->num_sids = ret;
1110 return NT_STATUS_OK;
1115 lsa_EnumAccountRights
1117 static NTSTATUS lsa_EnumAccountRights(struct dcesrv_call_state *dce_call,
1118 TALLOC_CTX *mem_ctx,
1119 struct lsa_EnumAccountRights *r)
1121 struct dcesrv_handle *h;
1122 struct lsa_policy_state *state;
1124 struct ldb_message **res;
1125 const char * const attrs[] = { "privilege", NULL};
1127 struct ldb_message_element *el;
1129 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
1133 sidstr = dom_sid_string(mem_ctx, r->in.sid);
1134 if (sidstr == NULL) {
1135 return NT_STATUS_NO_MEMORY;
1138 ret = samdb_search(state->sam_ctx, mem_ctx, NULL, &res, attrs,
1139 "objectSid=%s", sidstr);
1141 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1144 el = ldb_msg_find_element(res[0], "privilege");
1145 if (el == NULL || el->num_values == 0) {
1146 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1149 r->out.rights->count = el->num_values;
1150 r->out.rights->names = talloc_array_p(r->out.rights,
1151 struct lsa_String, r->out.rights->count);
1152 if (r->out.rights->names == NULL) {
1153 return NT_STATUS_NO_MEMORY;
1156 for (i=0;i<el->num_values;i++) {
1157 r->out.rights->names[i].string = el->values[i].data;
1160 return NT_STATUS_OK;
1165 helper for lsa_AddAccountRights and lsa_RemoveAccountRights
1167 static NTSTATUS lsa_AddRemoveAccountRights(struct dcesrv_call_state *dce_call,
1168 TALLOC_CTX *mem_ctx,
1169 struct lsa_policy_state *state,
1171 const struct dom_sid *sid,
1172 const struct lsa_RightSet *rights)
1175 struct ldb_message msg;
1176 struct ldb_message_element el;
1180 sidstr = dom_sid_string(mem_ctx, sid);
1181 if (sidstr == NULL) {
1182 return NT_STATUS_NO_MEMORY;
1185 dn = samdb_search_string(state->sam_ctx, mem_ctx, NULL, "dn",
1186 "objectSid=%s", sidstr);
1188 return NT_STATUS_NO_SUCH_USER;
1191 msg.dn = talloc_strdup(mem_ctx, dn);
1192 if (msg.dn == NULL) {
1193 return NT_STATUS_NO_MEMORY;
1195 msg.num_elements = 1;
1197 el.flags = ldb_flag;
1198 el.name = talloc_strdup(mem_ctx, "privilege");
1199 if (el.name == NULL) {
1200 return NT_STATUS_NO_MEMORY;
1202 el.num_values = rights->count;
1203 el.values = talloc_array_p(mem_ctx, struct ldb_val, el.num_values);
1204 if (el.values == NULL) {
1205 return NT_STATUS_NO_MEMORY;
1207 for (i=0;i<el.num_values;i++) {
1208 if (sec_privilege_id(rights->names[i].string) == -1) {
1209 return NT_STATUS_NO_SUCH_PRIVILEGE;
1211 el.values[i].length = strlen(rights->names[i].string);
1212 el.values[i].data = talloc_strdup(mem_ctx, rights->names[i].string);
1213 if (el.values[i].data == NULL) {
1214 return NT_STATUS_NO_MEMORY;
1218 ret = samdb_modify(state->sam_ctx, mem_ctx, &msg);
1220 if (ldb_flag == LDB_FLAG_MOD_DELETE) {
1221 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1223 return NT_STATUS_UNEXPECTED_IO_ERROR;
1226 return NT_STATUS_OK;
1230 lsa_AddAccountRights
1232 static NTSTATUS lsa_AddAccountRights(struct dcesrv_call_state *dce_call,
1233 TALLOC_CTX *mem_ctx,
1234 struct lsa_AddAccountRights *r)
1236 struct dcesrv_handle *h;
1237 struct lsa_policy_state *state;
1239 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
1243 return lsa_AddRemoveAccountRights(dce_call, mem_ctx, state,
1245 r->in.sid, r->in.rights);
1250 lsa_RemoveAccountRights
1252 static NTSTATUS lsa_RemoveAccountRights(struct dcesrv_call_state *dce_call,
1253 TALLOC_CTX *mem_ctx,
1254 struct lsa_RemoveAccountRights *r)
1256 struct dcesrv_handle *h;
1257 struct lsa_policy_state *state;
1259 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
1263 return lsa_AddRemoveAccountRights(dce_call, mem_ctx, state,
1264 LDB_FLAG_MOD_DELETE,
1265 r->in.sid, r->in.rights);
1270 lsa_QueryTrustedDomainInfoBySid
1272 static NTSTATUS lsa_QueryTrustedDomainInfoBySid(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1273 struct lsa_QueryTrustedDomainInfoBySid *r)
1275 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1280 lsa_SetTrustDomainInfo
1282 static NTSTATUS lsa_SetTrustDomainInfo(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1283 struct lsa_SetTrustDomainInfo *r)
1285 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1290 lsa_DeleteTrustDomain
1292 static NTSTATUS lsa_DeleteTrustDomain(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1293 struct lsa_DeleteTrustDomain *r)
1295 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1300 lsa_StorePrivateData
1302 static NTSTATUS lsa_StorePrivateData(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1303 struct lsa_StorePrivateData *r)
1305 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1310 lsa_RetrievePrivateData
1312 static NTSTATUS lsa_RetrievePrivateData(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1313 struct lsa_RetrievePrivateData *r)
1315 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1322 static NTSTATUS lsa_GetUserName(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1323 struct lsa_GetUserName *r)
1325 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1331 static NTSTATUS lsa_SetInfoPolicy2(struct dcesrv_call_state *dce_call,
1332 TALLOC_CTX *mem_ctx,
1333 struct lsa_SetInfoPolicy2 *r)
1335 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1339 lsa_QueryTrustedDomainInfoByName
1341 static NTSTATUS lsa_QueryTrustedDomainInfoByName(struct dcesrv_call_state *dce_call,
1342 TALLOC_CTX *mem_ctx,
1343 struct lsa_QueryTrustedDomainInfoByName *r)
1345 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1349 lsa_SetTrustedDomainInfoByName
1351 static NTSTATUS lsa_SetTrustedDomainInfoByName(struct dcesrv_call_state *dce_call,
1352 TALLOC_CTX *mem_ctx,
1353 struct lsa_SetTrustedDomainInfoByName *r)
1355 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1359 lsa_EnumTrustedDomainsEx
1361 static NTSTATUS lsa_EnumTrustedDomainsEx(struct dcesrv_call_state *dce_call,
1362 TALLOC_CTX *mem_ctx,
1363 struct lsa_EnumTrustedDomainsEx *r)
1365 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1369 lsa_CreateTrustedDomainEx
1371 static NTSTATUS lsa_CreateTrustedDomainEx(struct dcesrv_call_state *dce_call,
1372 TALLOC_CTX *mem_ctx,
1373 struct lsa_CreateTrustedDomainEx *r)
1375 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1379 lsa_CloseTrustedDomainEx
1381 static NTSTATUS lsa_CloseTrustedDomainEx(struct dcesrv_call_state *dce_call,
1382 TALLOC_CTX *mem_ctx,
1383 struct lsa_CloseTrustedDomainEx *r)
1385 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1389 lsa_QueryDomainInformationPolicy
1391 static NTSTATUS lsa_QueryDomainInformationPolicy(struct dcesrv_call_state *dce_call,
1392 TALLOC_CTX *mem_ctx,
1393 struct lsa_QueryDomainInformationPolicy *r)
1395 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1399 lsa_SetDomInfoPolicy
1401 static NTSTATUS lsa_SetDomInfoPolicy(struct dcesrv_call_state *dce_call,
1402 TALLOC_CTX *mem_ctx,
1403 struct lsa_SetDomInfoPolicy *r)
1405 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1409 lsa_OpenTrustedDomainByName
1411 static NTSTATUS lsa_OpenTrustedDomainByName(struct dcesrv_call_state *dce_call,
1412 TALLOC_CTX *mem_ctx,
1413 struct lsa_OpenTrustedDomainByName *r)
1415 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1421 static NTSTATUS lsa_TestCall(struct dcesrv_call_state *dce_call,
1422 TALLOC_CTX *mem_ctx,
1423 struct lsa_TestCall *r)
1425 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1429 lookup a SID for 1 name
1431 static NTSTATUS lsa_lookup_name(struct lsa_policy_state *state, TALLOC_CTX *mem_ctx,
1432 const char *name, struct dom_sid **sid, uint32_t *atype)
1435 struct ldb_message **res;
1436 const char * const attrs[] = { "objectSid", "sAMAccountType", NULL};
1438 ret = samdb_search(state->sam_ctx, mem_ctx, NULL, &res, attrs, "sAMAccountName=%s", name);
1440 const char *sid_str = ldb_msg_find_string(res[0], "objectSid", NULL);
1441 if (sid_str == NULL) {
1442 return NT_STATUS_INVALID_SID;
1445 *sid = dom_sid_parse_talloc(mem_ctx, sid_str);
1447 return NT_STATUS_INVALID_SID;
1450 *atype = samdb_result_uint(res[0], "sAMAccountType", 0);
1452 return NT_STATUS_OK;
1455 /* need to add a call into sidmap to check for a allocated sid */
1457 return NT_STATUS_INVALID_SID;
1463 static NTSTATUS lsa_LookupNames2(struct dcesrv_call_state *dce_call,
1464 TALLOC_CTX *mem_ctx,
1465 struct lsa_LookupNames2 *r)
1467 struct lsa_policy_state *state;
1468 struct dcesrv_handle *h;
1470 NTSTATUS status = NT_STATUS_OK;
1472 r->out.domains = NULL;
1474 DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY);
1478 r->out.domains = talloc_zero_p(mem_ctx, struct lsa_RefDomainList);
1479 if (r->out.domains == NULL) {
1480 return NT_STATUS_NO_MEMORY;
1483 r->out.sids = talloc_zero_p(mem_ctx, struct lsa_TransSidArray2);
1484 if (r->out.sids == NULL) {
1485 return NT_STATUS_NO_MEMORY;
1490 r->out.sids->sids = talloc_array_p(r->out.sids, struct lsa_TranslatedSid2,
1492 if (r->out.sids->sids == NULL) {
1493 return NT_STATUS_NO_MEMORY;
1496 for (i=0;i<r->in.num_names;i++) {
1497 const char *name = r->in.names[i].string;
1498 struct dom_sid *sid;
1499 uint32_t atype, rtype, sid_index;
1502 r->out.sids->count++;
1505 r->out.sids->sids[i].sid_type = SID_NAME_UNKNOWN;
1506 r->out.sids->sids[i].rid = 0xFFFFFFFF;
1507 r->out.sids->sids[i].sid_index = 0xFFFFFFFF;
1508 r->out.sids->sids[i].unknown = 0;
1510 status2 = lsa_lookup_name(state, mem_ctx, name, &sid, &atype);
1511 if (!NT_STATUS_IS_OK(status2) || sid->num_auths == 0) {
1512 status = STATUS_SOME_UNMAPPED;
1516 rtype = samdb_atype_map(atype);
1517 if (rtype == SID_NAME_UNKNOWN) {
1518 status = STATUS_SOME_UNMAPPED;
1522 status2 = lsa_authority_list(state, mem_ctx, sid, r->out.domains, &sid_index);
1523 if (!NT_STATUS_IS_OK(status2)) {
1527 r->out.sids->sids[i].sid_type = rtype;
1528 r->out.sids->sids[i].rid = sid->sub_auths[sid->num_auths-1];
1529 r->out.sids->sids[i].sid_index = sid_index;
1530 r->out.sids->sids[i].unknown = 0;
1539 static NTSTATUS lsa_LookupNames(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
1540 struct lsa_LookupNames *r)
1542 struct lsa_LookupNames2 r2;
1546 r2.in.handle = r->in.handle;
1547 r2.in.num_names = r->in.num_names;
1548 r2.in.names = r->in.names;
1550 r2.in.level = r->in.level;
1551 r2.in.count = r->in.count;
1554 r2.out.count = r->out.count;
1556 status = lsa_LookupNames2(dce_call, mem_ctx, &r2);
1557 if (dce_call->fault_code != 0) {
1561 r->out.domains = r2.out.domains;
1562 r->out.sids = talloc_p(mem_ctx, struct lsa_TransSidArray);
1563 if (r->out.sids == NULL) {
1564 return NT_STATUS_NO_MEMORY;
1566 r->out.sids->count = r2.out.sids->count;
1567 r->out.sids->sids = talloc_array_p(r->out.sids, struct lsa_TranslatedSid,
1568 r->out.sids->count);
1569 if (r->out.sids->sids == NULL) {
1570 return NT_STATUS_NO_MEMORY;
1572 for (i=0;i<r->out.sids->count;i++) {
1573 r->out.sids->sids[i].sid_type = r2.out.sids->sids[i].sid_type;
1574 r->out.sids->sids[i].rid = r2.out.sids->sids[i].rid;
1575 r->out.sids->sids[i].sid_index = r2.out.sids->sids[i].sid_index;
1584 lsa_CreateTrustedDomainEx2
1586 static NTSTATUS lsa_CreateTrustedDomainEx2(struct dcesrv_call_state *dce_call,
1587 TALLOC_CTX *mem_ctx,
1588 struct lsa_CreateTrustedDomainEx2 *r)
1590 DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
1593 /* include the generated boilerplate */
1594 #include "librpc/gen_ndr/ndr_lsa_s.c"