diff options
author | Andrew Tridgell <tridge@samba.org> | 2004-11-18 05:17:24 +0000 |
---|---|---|
committer | Gerald (Jerry) Carter <jerry@samba.org> | 2007-10-10 13:05:58 -0500 |
commit | 9b6c08a0d19929c8928e692de2156e81decc4048 (patch) | |
tree | 895d615f5f5bfd0bd528e46f43d816e20917345a /source4/rpc_server | |
parent | 0b691afe81c2778de30f20c03ab2a5f29473f799 (diff) | |
download | samba-9b6c08a0d19929c8928e692de2156e81decc4048.tar.gz samba-9b6c08a0d19929c8928e692de2156e81decc4048.tar.bz2 samba-9b6c08a0d19929c8928e692de2156e81decc4048.zip |
r3837: added support for LsaLookupSids in the LSA rpc server. This allows the GUI ACL editor on w2k to
correctly display names instead of SIDs.
(This used to be commit fdaa753578c7b80806d4040ed131f87ddbf988e0)
Diffstat (limited to 'source4/rpc_server')
-rw-r--r-- | source4/rpc_server/lsa/dcesrv_lsa.c | 126 |
1 files changed, 124 insertions, 2 deletions
diff --git a/source4/rpc_server/lsa/dcesrv_lsa.c b/source4/rpc_server/lsa/dcesrv_lsa.c index a1821963bf..ce9f9f39ff 100644 --- a/source4/rpc_server/lsa/dcesrv_lsa.c +++ b/source4/rpc_server/lsa/dcesrv_lsa.c @@ -22,8 +22,10 @@ #include "includes.h" #include "librpc/gen_ndr/ndr_lsa.h" +#include "librpc/gen_ndr/ndr_samr.h" #include "rpc_server/dcerpc_server.h" #include "rpc_server/common/common.h" +#include "lib/ldb/include/ldb.h" /* this type allows us to distinguish handle types @@ -384,9 +386,129 @@ static NTSTATUS lsa_LookupNames(struct dcesrv_call_state *dce_call, TALLOC_CTX * lsa_LookupSids */ static NTSTATUS lsa_LookupSids(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx, - struct lsa_LookupSids *r) + struct lsa_LookupSids *r) { - DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR); + struct lsa_policy_state *state; + struct dcesrv_handle *h; + int i; + NTSTATUS status = NT_STATUS_OK; + + r->out.domains = NULL; + + DCESRV_PULL_HANDLE(h, r->in.handle, LSA_HANDLE_POLICY); + + state = h->data; + + r->out.domains = talloc_zero_p(mem_ctx, struct lsa_RefDomainList); + if (r->out.domains == NULL) { + return NT_STATUS_NO_MEMORY; + } + + r->out.names = talloc_zero_p(mem_ctx, struct lsa_TransNameArray); + if (r->out.domains == NULL) { + return NT_STATUS_NO_MEMORY; + } + + *r->out.count = 0; + + r->out.names->names = talloc_array_p(r->out.names, struct lsa_TranslatedName, + r->in.sids->num_sids); + if (r->out.names->names == NULL) { + return NT_STATUS_NO_MEMORY; + } + + for (i=0;i<r->in.sids->num_sids;i++) { + const char * const attrs[] = { "sAMAccountName", "sAMAccountType", NULL}; + struct dom_sid *sid = r->in.sids->sids[i].sid; + char *sid_str = dom_sid_string(mem_ctx, sid); + int ret, j; + struct ldb_message **res; + const char *name, *authority_name; + struct dom_sid *authority_sid; + uint32_t atype, rtype; + const struct { + const char *sid_prefix; + const char *authority_name; + } authority_names[] = { + { "S-1-5", "NT AUTHORITY" } + }; + + r->out.names->count++; + (*r->out.count)++; + + r->out.names->names[i].sid_type = SID_NAME_UNKNOWN; + r->out.names->names[i].name.name = sid_str; + r->out.names->names[i].sid_index = 0xFFFFFFFF; + + if (sid_str == NULL) { + r->out.names->names[i].name.name = "(SIDERROR)"; + status = STATUS_SOME_UNMAPPED; + continue; + } + + /* work out the authority name */ + authority_name = talloc_strndup(mem_ctx, sid_str, 5); + authority_sid = dom_sid_parse_talloc(mem_ctx, authority_name); + if (!authority_name || !authority_sid) { + return NT_STATUS_NO_MEMORY; + } + for (j=0;j<ARRAY_SIZE(authority_names);j++) { + if (strncmp(sid_str, authority_names[j].sid_prefix, + strlen(authority_names[j].sid_prefix)) == 0) { + authority_name = authority_names[j].authority_name; + break; + } + } + + /* see if we've already done this authority name */ + for (j=0;j<r->out.domains->count;j++) { + if (strcmp(authority_name, r->out.domains->domains[j].name.name) == 0) { + break; + } + } + if (j == r->out.domains->count) { + r->out.domains->domains = talloc_realloc_p(r->out.domains, + r->out.domains->domains, + struct lsa_TrustInformation, + r->out.domains->count+1); + if (r->out.domains == NULL) { + return NT_STATUS_NO_MEMORY; + } + r->out.domains->domains[j].name.name = authority_name; + r->out.domains->domains[j].sid = authority_sid; + r->out.domains->count++; + } + + ret = samdb_search(state->sam_ctx, mem_ctx, NULL, &res, attrs, "objectSid=%s", sid_str); + if (ret != 1) { + status = STATUS_SOME_UNMAPPED; + continue; + } + + name = ldb_msg_find_string(res[0], "sAMAccountName", NULL); + if (name == NULL) { + status = STATUS_SOME_UNMAPPED; + continue; + } + + atype = samdb_result_uint(res[0], "sAMAccountType", 0); + if (atype == 0) { + status = STATUS_SOME_UNMAPPED; + continue; + } + + rtype = samdb_atype_map(atype); + if (rtype == SID_NAME_UNKNOWN) { + status = STATUS_SOME_UNMAPPED; + continue; + } + + r->out.names->names[i].sid_type = rtype; + r->out.names->names[i].name.name = name; + r->out.names->names[i].sid_index = 0; + } + + return status; } |