2 Unix SMB/CIFS implementation.
4 Winbind rpc backend functions
6 Copyright (C) Tim Potter 2000-2001,2003
7 Copyright (C) Andrew Tridgell 2001
8 Copyright (C) Volker Lendecke 2005
9 Copyright (C) Guenther Deschner 2008 (pidl conversion)
11 This program is free software; you can redistribute it and/or modify
12 it under the terms of the GNU General Public License as published by
13 the Free Software Foundation; either version 3 of the License, or
14 (at your option) any later version.
16 This program is distributed in the hope that it will be useful,
17 but WITHOUT ANY WARRANTY; without even the implied warranty of
18 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 GNU General Public License for more details.
21 You should have received a copy of the GNU General Public License
22 along with this program. If not, see <http://www.gnu.org/licenses/>.
29 #define DBGC_CLASS DBGC_WINBIND
32 /* Query display info for a domain. This returns enough information plus a
33 bit extra to give an overview of domain users for the User Manager
35 static NTSTATUS query_user_list(struct winbindd_domain *domain,
38 WINBIND_USERINFO **info)
41 struct policy_handle dom_pol;
42 unsigned int i, start_idx;
44 struct rpc_pipe_client *cli;
46 DEBUG(3,("rpc: query_user_list\n"));
51 if ( !winbindd_can_contact_domain( domain ) ) {
52 DEBUG(10,("query_user_list: No incoming trust for domain %s\n",
57 result = cm_connect_sam(domain, mem_ctx, &cli, &dom_pol);
58 if (!NT_STATUS_IS_OK(result))
65 uint32 num_dom_users, j;
66 uint32 max_entries, max_size;
67 uint32_t total_size, returned_size;
69 union samr_DispInfo disp_info;
71 /* this next bit is copied from net_user_list_internal() */
73 get_query_dispinfo_params(loop_count, &max_entries,
76 result = rpccli_samr_QueryDisplayInfo(cli, mem_ctx,
85 num_dom_users = disp_info.info1.count;
86 start_idx += disp_info.info1.count;
89 *num_entries += num_dom_users;
91 *info = TALLOC_REALLOC_ARRAY(mem_ctx, *info, WINBIND_USERINFO,
95 return NT_STATUS_NO_MEMORY;
98 for (j = 0; j < num_dom_users; i++, j++) {
100 uint32_t rid = disp_info.info1.entries[j].rid;
102 (*info)[i].acct_name = talloc_strdup(mem_ctx,
103 disp_info.info1.entries[j].account_name.string);
104 (*info)[i].full_name = talloc_strdup(mem_ctx,
105 disp_info.info1.entries[j].full_name.string);
106 (*info)[i].homedir = NULL;
107 (*info)[i].shell = NULL;
108 sid_compose(&(*info)[i].user_sid, &domain->sid, rid);
110 /* For the moment we set the primary group for
111 every user to be the Domain Users group.
112 There are serious problems with determining
113 the actual primary group for large domains.
114 This should really be made into a 'winbind
115 force group' smb.conf parameter or
116 something like that. */
118 sid_compose(&(*info)[i].group_sid, &domain->sid,
119 DOMAIN_GROUP_RID_USERS);
122 } while (NT_STATUS_EQUAL(result, STATUS_MORE_ENTRIES));
127 /* list all domain groups */
128 static NTSTATUS enum_dom_groups(struct winbindd_domain *domain,
131 struct acct_info **info)
133 struct policy_handle dom_pol;
136 struct rpc_pipe_client *cli;
141 DEBUG(3,("rpc: enum_dom_groups\n"));
143 if ( !winbindd_can_contact_domain( domain ) ) {
144 DEBUG(10,("enum_domain_groups: No incoming trust for domain %s\n",
149 status = cm_connect_sam(domain, mem_ctx, &cli, &dom_pol);
150 if (!NT_STATUS_IS_OK(status))
154 struct samr_SamArray *sam_array = NULL;
156 TALLOC_CTX *mem_ctx2;
159 mem_ctx2 = talloc_init("enum_dom_groups[rpc]");
161 /* start is updated by this call. */
162 status = rpccli_samr_EnumDomainGroups(cli, mem_ctx2,
166 0xFFFF, /* buffer size? */
169 if (!NT_STATUS_IS_OK(status) &&
170 !NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES)) {
171 talloc_destroy(mem_ctx2);
175 (*info) = TALLOC_REALLOC_ARRAY(mem_ctx, *info,
177 (*num_entries) + count);
179 talloc_destroy(mem_ctx2);
180 return NT_STATUS_NO_MEMORY;
183 for (g=0; g < count; g++) {
185 fstrcpy((*info)[*num_entries + g].acct_name,
186 sam_array->entries[g].name.string);
187 (*info)[*num_entries + g].rid = sam_array->entries[g].idx;
190 (*num_entries) += count;
191 talloc_destroy(mem_ctx2);
192 } while (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES));
197 /* List all domain groups */
199 static NTSTATUS enum_local_groups(struct winbindd_domain *domain,
202 struct acct_info **info)
204 struct policy_handle dom_pol;
206 struct rpc_pipe_client *cli;
211 DEBUG(3,("rpc: enum_local_groups\n"));
213 if ( !winbindd_can_contact_domain( domain ) ) {
214 DEBUG(10,("enum_local_groups: No incoming trust for domain %s\n",
219 result = cm_connect_sam(domain, mem_ctx, &cli, &dom_pol);
220 if (!NT_STATUS_IS_OK(result))
224 struct samr_SamArray *sam_array = NULL;
225 uint32 count = 0, start = *num_entries;
226 TALLOC_CTX *mem_ctx2;
229 mem_ctx2 = talloc_init("enum_dom_local_groups[rpc]");
231 result = rpccli_samr_EnumDomainAliases(cli, mem_ctx2,
235 0xFFFF, /* buffer size? */
237 if (!NT_STATUS_IS_OK(result) &&
238 !NT_STATUS_EQUAL(result, STATUS_MORE_ENTRIES) )
240 talloc_destroy(mem_ctx2);
244 (*info) = TALLOC_REALLOC_ARRAY(mem_ctx, *info,
246 (*num_entries) + count);
248 talloc_destroy(mem_ctx2);
249 return NT_STATUS_NO_MEMORY;
252 for (g=0; g < count; g++) {
254 fstrcpy((*info)[*num_entries + g].acct_name,
255 sam_array->entries[g].name.string);
256 (*info)[*num_entries + g].rid = sam_array->entries[g].idx;
259 (*num_entries) += count;
260 talloc_destroy(mem_ctx2);
262 } while (NT_STATUS_EQUAL(result, STATUS_MORE_ENTRIES));
267 /* convert a single name to a sid in a domain */
268 static NTSTATUS msrpc_name_to_sid(struct winbindd_domain *domain,
270 enum winbindd_cmd original_cmd,
271 const char *domain_name,
274 enum lsa_SidType *type)
277 DOM_SID *sids = NULL;
278 enum lsa_SidType *types = NULL;
279 char *full_name = NULL;
280 struct rpc_pipe_client *cli;
281 struct policy_handle lsa_policy;
282 NTSTATUS name_map_status = NT_STATUS_UNSUCCESSFUL;
283 char *mapped_name = NULL;
284 unsigned int orig_timeout;
286 if (name == NULL || *name=='\0') {
287 full_name = talloc_asprintf(mem_ctx, "%s", domain_name);
288 } else if (domain_name == NULL || *domain_name == '\0') {
289 full_name = talloc_asprintf(mem_ctx, "%s", name);
291 full_name = talloc_asprintf(mem_ctx, "%s\\%s", domain_name, name);
294 DEBUG(0, ("talloc_asprintf failed!\n"));
295 return NT_STATUS_NO_MEMORY;
298 DEBUG(3,("rpc: name_to_sid name=%s\n", full_name));
300 name_map_status = normalize_name_unmap(mem_ctx, full_name,
303 /* Reset the full_name pointer if we mapped anytthing */
305 if (NT_STATUS_IS_OK(name_map_status) ||
306 NT_STATUS_EQUAL(name_map_status, NT_STATUS_FILE_RENAMED))
308 full_name = mapped_name;
311 DEBUG(3,("name_to_sid [rpc] %s for domain %s\n",
312 full_name?full_name:"", domain_name ));
314 result = cm_connect_lsa(domain, mem_ctx, &cli, &lsa_policy);
315 if (!NT_STATUS_IS_OK(result))
319 * This call can take a long time
320 * allow the server to time out.
321 * 35 seconds should do it.
323 orig_timeout = rpccli_set_timeout(cli, 35000);
325 result = rpccli_lsa_lookup_names(cli, mem_ctx, &lsa_policy, 1,
326 (const char**) &full_name, NULL, 1, &sids, &types);
328 /* And restore our original timeout. */
329 rpccli_set_timeout(cli, orig_timeout);
331 if (!NT_STATUS_IS_OK(result))
334 /* Return rid and type if lookup successful */
336 sid_copy(sid, &sids[0]);
343 convert a domain SID to a user or group name
345 static NTSTATUS msrpc_sid_to_name(struct winbindd_domain *domain,
350 enum lsa_SidType *type)
354 enum lsa_SidType *types = NULL;
356 struct rpc_pipe_client *cli;
357 struct policy_handle lsa_policy;
358 NTSTATUS name_map_status = NT_STATUS_UNSUCCESSFUL;
359 char *mapped_name = NULL;
360 unsigned int orig_timeout;
362 DEBUG(3,("sid_to_name [rpc] %s for domain %s\n", sid_string_dbg(sid),
365 result = cm_connect_lsa(domain, mem_ctx, &cli, &lsa_policy);
366 if (!NT_STATUS_IS_OK(result)) {
367 DEBUG(2,("msrpc_sid_to_name: cm_connect_lsa() failed (%s)\n",
374 * This call can take a long time
375 * allow the server to time out.
376 * 35 seconds should do it.
378 orig_timeout = rpccli_set_timeout(cli, 35000);
380 result = rpccli_lsa_lookup_sids(cli, mem_ctx, &lsa_policy,
381 1, sid, &domains, &names, &types);
383 /* And restore our original timeout. */
384 rpccli_set_timeout(cli, orig_timeout);
386 if (!NT_STATUS_IS_OK(result)) {
387 DEBUG(2,("msrpc_sid_to_name: rpccli_lsa_lookup_sids() failed (%s)\n",
392 *type = (enum lsa_SidType)types[0];
393 *domain_name = domains[0];
396 DEBUG(5,("Mapped sid to [%s]\\[%s]\n", domains[0], *name));
398 name_map_status = normalize_name_map(mem_ctx, domain, *name,
400 if (NT_STATUS_IS_OK(name_map_status) ||
401 NT_STATUS_EQUAL(name_map_status, NT_STATUS_FILE_RENAMED))
404 DEBUG(5,("returning mapped name -- %s\n", *name));
410 static NTSTATUS msrpc_rids_to_names(struct winbindd_domain *domain,
417 enum lsa_SidType **types)
421 struct rpc_pipe_client *cli;
422 struct policy_handle lsa_policy;
426 unsigned int orig_timeout;
428 DEBUG(3, ("rids_to_names [rpc] for domain %s\n", domain->name ));
431 sids = TALLOC_ARRAY(mem_ctx, DOM_SID, num_rids);
433 return NT_STATUS_NO_MEMORY;
439 for (i=0; i<num_rids; i++) {
440 if (!sid_compose(&sids[i], sid, rids[i])) {
441 return NT_STATUS_INTERNAL_ERROR;
445 result = cm_connect_lsa(domain, mem_ctx, &cli, &lsa_policy);
446 if (!NT_STATUS_IS_OK(result)) {
451 * This call can take a long time
452 * allow the server to time out.
453 * 35 seconds should do it.
455 orig_timeout = rpccli_set_timeout(cli, 35000);
457 result = rpccli_lsa_lookup_sids(cli, mem_ctx, &lsa_policy,
458 num_rids, sids, &domains,
461 /* And restore our original timeout. */
462 rpccli_set_timeout(cli, orig_timeout);
464 if (!NT_STATUS_IS_OK(result) &&
465 !NT_STATUS_EQUAL(result, STATUS_SOME_UNMAPPED)) {
470 for (i=0; i<num_rids; i++) {
471 NTSTATUS name_map_status = NT_STATUS_UNSUCCESSFUL;
472 char *mapped_name = NULL;
474 if ((*types)[i] != SID_NAME_UNKNOWN) {
475 name_map_status = normalize_name_map(mem_ctx,
479 if (NT_STATUS_IS_OK(name_map_status) ||
480 NT_STATUS_EQUAL(name_map_status, NT_STATUS_FILE_RENAMED))
482 ret_names[i] = mapped_name;
485 *domain_name = domains[i];
492 /* Lookup user information from a rid or username. */
493 static NTSTATUS query_user(struct winbindd_domain *domain,
495 const DOM_SID *user_sid,
496 WINBIND_USERINFO *user_info)
498 NTSTATUS result = NT_STATUS_UNSUCCESSFUL;
499 struct policy_handle dom_pol, user_pol;
500 union samr_UserInfo *info = NULL;
502 struct netr_SamInfo3 *user;
503 struct rpc_pipe_client *cli;
505 DEBUG(3,("rpc: query_user sid=%s\n", sid_string_dbg(user_sid)));
507 if (!sid_peek_check_rid(&domain->sid, user_sid, &user_rid))
508 return NT_STATUS_UNSUCCESSFUL;
510 user_info->homedir = NULL;
511 user_info->shell = NULL;
512 user_info->primary_gid = (gid_t)-1;
514 /* try netsamlogon cache first */
516 if ( (user = netsamlogon_cache_get( mem_ctx, user_sid )) != NULL )
519 DEBUG(5,("query_user: Cache lookup succeeded for %s\n",
520 sid_string_dbg(user_sid)));
522 sid_compose(&user_info->user_sid, &domain->sid, user->base.rid);
523 sid_compose(&user_info->group_sid, &domain->sid,
524 user->base.primary_gid);
526 user_info->acct_name = talloc_strdup(mem_ctx,
527 user->base.account_name.string);
528 user_info->full_name = talloc_strdup(mem_ctx,
529 user->base.full_name.string);
536 if ( !winbindd_can_contact_domain( domain ) ) {
537 DEBUG(10,("query_user: No incoming trust for domain %s\n",
542 if ( !winbindd_can_contact_domain( domain ) ) {
543 DEBUG(10,("query_user: No incoming trust for domain %s\n",
548 if ( !winbindd_can_contact_domain( domain ) ) {
549 DEBUG(10,("query_user: No incoming trust for domain %s\n",
554 /* no cache; hit the wire */
556 result = cm_connect_sam(domain, mem_ctx, &cli, &dom_pol);
557 if (!NT_STATUS_IS_OK(result))
560 /* Get user handle */
561 result = rpccli_samr_OpenUser(cli, mem_ctx,
563 SEC_FLAG_MAXIMUM_ALLOWED,
567 if (!NT_STATUS_IS_OK(result))
571 result = rpccli_samr_QueryUserInfo(cli, mem_ctx,
576 rpccli_samr_Close(cli, mem_ctx, &user_pol);
578 if (!NT_STATUS_IS_OK(result))
581 sid_compose(&user_info->user_sid, &domain->sid, user_rid);
582 sid_compose(&user_info->group_sid, &domain->sid,
583 info->info21.primary_gid);
584 user_info->acct_name = talloc_strdup(mem_ctx,
585 info->info21.account_name.string);
586 user_info->full_name = talloc_strdup(mem_ctx,
587 info->info21.full_name.string);
588 user_info->homedir = NULL;
589 user_info->shell = NULL;
590 user_info->primary_gid = (gid_t)-1;
595 /* Lookup groups a user is a member of. I wish Unix had a call like this! */
596 static NTSTATUS lookup_usergroups(struct winbindd_domain *domain,
598 const DOM_SID *user_sid,
599 uint32 *num_groups, DOM_SID **user_grpsids)
601 NTSTATUS result = NT_STATUS_UNSUCCESSFUL;
602 struct policy_handle dom_pol, user_pol;
603 uint32 des_access = SEC_FLAG_MAXIMUM_ALLOWED;
604 struct samr_RidWithAttributeArray *rid_array = NULL;
607 struct rpc_pipe_client *cli;
609 DEBUG(3,("rpc: lookup_usergroups sid=%s\n", sid_string_dbg(user_sid)));
611 if (!sid_peek_check_rid(&domain->sid, user_sid, &user_rid))
612 return NT_STATUS_UNSUCCESSFUL;
615 *user_grpsids = NULL;
617 /* so lets see if we have a cached user_info_3 */
618 result = lookup_usergroups_cached(domain, mem_ctx, user_sid,
619 num_groups, user_grpsids);
621 if (NT_STATUS_IS_OK(result)) {
625 if ( !winbindd_can_contact_domain( domain ) ) {
626 DEBUG(10,("lookup_usergroups: No incoming trust for domain %s\n",
629 /* Tell the cache manager not to remember this one */
631 return NT_STATUS_SYNCHRONIZATION_REQUIRED;
634 /* no cache; hit the wire */
636 result = cm_connect_sam(domain, mem_ctx, &cli, &dom_pol);
637 if (!NT_STATUS_IS_OK(result))
640 /* Get user handle */
641 result = rpccli_samr_OpenUser(cli, mem_ctx,
647 if (!NT_STATUS_IS_OK(result))
650 /* Query user rids */
651 result = rpccli_samr_GetGroupsForUser(cli, mem_ctx,
654 *num_groups = rid_array->count;
656 rpccli_samr_Close(cli, mem_ctx, &user_pol);
658 if (!NT_STATUS_IS_OK(result) || (*num_groups) == 0)
661 (*user_grpsids) = TALLOC_ARRAY(mem_ctx, DOM_SID, *num_groups);
662 if (!(*user_grpsids))
663 return NT_STATUS_NO_MEMORY;
665 for (i=0;i<(*num_groups);i++) {
666 sid_copy(&((*user_grpsids)[i]), &domain->sid);
667 sid_append_rid(&((*user_grpsids)[i]),
668 rid_array->rids[i].rid);
674 #define MAX_SAM_ENTRIES_W2K 0x400 /* 1024 */
676 static NTSTATUS msrpc_lookup_useraliases(struct winbindd_domain *domain,
678 uint32 num_sids, const DOM_SID *sids,
682 NTSTATUS result = NT_STATUS_UNSUCCESSFUL;
683 struct policy_handle dom_pol;
684 uint32 num_query_sids = 0;
686 struct rpc_pipe_client *cli;
687 struct samr_Ids alias_rids_query;
688 int rangesize = MAX_SAM_ENTRIES_W2K;
689 uint32 total_sids = 0;
695 DEBUG(3,("rpc: lookup_useraliases\n"));
697 if ( !winbindd_can_contact_domain( domain ) ) {
698 DEBUG(10,("msrpc_lookup_useraliases: No incoming trust for domain %s\n",
703 result = cm_connect_sam(domain, mem_ctx, &cli, &dom_pol);
704 if (!NT_STATUS_IS_OK(result))
709 struct lsa_SidArray sid_array;
711 ZERO_STRUCT(sid_array);
713 num_query_sids = MIN(num_sids - total_sids, rangesize);
715 DEBUG(10,("rpc: lookup_useraliases: entering query %d for %d sids\n",
716 num_queries, num_query_sids));
718 if (num_query_sids) {
719 sid_array.sids = TALLOC_ZERO_ARRAY(mem_ctx, struct lsa_SidPtr, num_query_sids);
720 if (sid_array.sids == NULL) {
721 return NT_STATUS_NO_MEMORY;
724 sid_array.sids = NULL;
727 for (i=0; i<num_query_sids; i++) {
728 sid_array.sids[i].sid = sid_dup_talloc(mem_ctx, &sids[total_sids++]);
729 if (!sid_array.sids[i].sid) {
730 TALLOC_FREE(sid_array.sids);
731 return NT_STATUS_NO_MEMORY;
734 sid_array.num_sids = num_query_sids;
737 result = rpccli_samr_GetAliasMembership(cli, mem_ctx,
742 if (!NT_STATUS_IS_OK(result)) {
745 TALLOC_FREE(sid_array.sids);
751 for (i=0; i<alias_rids_query.count; i++) {
752 size_t na = *num_aliases;
753 if (!add_rid_to_array_unique(mem_ctx, alias_rids_query.ids[i],
755 return NT_STATUS_NO_MEMORY;
760 TALLOC_FREE(sid_array.sids);
764 } while (total_sids < num_sids);
767 DEBUG(10,("rpc: lookup_useraliases: got %d aliases in %d queries "
768 "(rangesize: %d)\n", *num_aliases, num_queries, rangesize));
774 /* Lookup group membership given a rid. */
775 static NTSTATUS lookup_groupmem(struct winbindd_domain *domain,
777 const DOM_SID *group_sid, uint32 *num_names,
778 DOM_SID **sid_mem, char ***names,
781 NTSTATUS result = NT_STATUS_UNSUCCESSFUL;
782 uint32 i, total_names = 0;
783 struct policy_handle dom_pol, group_pol;
784 uint32 des_access = SEC_FLAG_MAXIMUM_ALLOWED;
785 uint32 *rid_mem = NULL;
788 struct rpc_pipe_client *cli;
789 unsigned int orig_timeout;
790 struct samr_RidTypeArray *rids = NULL;
792 DEBUG(10,("rpc: lookup_groupmem %s sid=%s\n", domain->name,
793 sid_string_dbg(group_sid)));
795 if ( !winbindd_can_contact_domain( domain ) ) {
796 DEBUG(10,("lookup_groupmem: No incoming trust for domain %s\n",
801 if (!sid_peek_check_rid(&domain->sid, group_sid, &group_rid))
802 return NT_STATUS_UNSUCCESSFUL;
806 result = cm_connect_sam(domain, mem_ctx, &cli, &dom_pol);
807 if (!NT_STATUS_IS_OK(result))
810 result = rpccli_samr_OpenGroup(cli, mem_ctx,
816 if (!NT_STATUS_IS_OK(result))
819 /* Step #1: Get a list of user rids that are the members of the
822 /* This call can take a long time - allow the server to time out.
823 35 seconds should do it. */
825 orig_timeout = rpccli_set_timeout(cli, 35000);
827 result = rpccli_samr_QueryGroupMember(cli, mem_ctx,
831 /* And restore our original timeout. */
832 rpccli_set_timeout(cli, orig_timeout);
834 rpccli_samr_Close(cli, mem_ctx, &group_pol);
836 if (!NT_STATUS_IS_OK(result))
839 *num_names = rids->count;
840 rid_mem = rids->rids;
849 /* Step #2: Convert list of rids into list of usernames. Do this
850 in bunches of ~1000 to avoid crashing NT4. It looks like there
851 is a buffer overflow or something like that lurking around
854 #define MAX_LOOKUP_RIDS 900
856 *names = TALLOC_ZERO_ARRAY(mem_ctx, char *, *num_names);
857 *name_types = TALLOC_ZERO_ARRAY(mem_ctx, uint32, *num_names);
858 *sid_mem = TALLOC_ZERO_ARRAY(mem_ctx, DOM_SID, *num_names);
860 for (j=0;j<(*num_names);j++)
861 sid_compose(&(*sid_mem)[j], &domain->sid, rid_mem[j]);
863 if (*num_names>0 && (!*names || !*name_types))
864 return NT_STATUS_NO_MEMORY;
866 for (i = 0; i < *num_names; i += MAX_LOOKUP_RIDS) {
867 int num_lookup_rids = MIN(*num_names - i, MAX_LOOKUP_RIDS);
868 struct lsa_Strings tmp_names;
869 struct samr_Ids tmp_types;
871 /* Lookup a chunk of rids */
873 result = rpccli_samr_LookupRids(cli, mem_ctx,
880 /* see if we have a real error (and yes the
881 STATUS_SOME_UNMAPPED is the one returned from 2k) */
883 if (!NT_STATUS_IS_OK(result) &&
884 !NT_STATUS_EQUAL(result, STATUS_SOME_UNMAPPED))
887 /* Copy result into array. The talloc system will take
888 care of freeing the temporary arrays later on. */
890 if (tmp_names.count != tmp_types.count) {
891 return NT_STATUS_UNSUCCESSFUL;
894 for (r=0; r<tmp_names.count; r++) {
895 if (tmp_types.ids[r] == SID_NAME_UNKNOWN) {
898 (*names)[total_names] = fill_domain_username_talloc(
899 mem_ctx, domain->name,
900 tmp_names.names[r].string, true);
901 (*name_types)[total_names] = tmp_types.ids[r];
906 *num_names = total_names;
915 static int get_ldap_seq(const char *server, int port, uint32 *seq)
919 const char *attrs[] = {"highestCommittedUSN", NULL};
920 LDAPMessage *res = NULL;
921 char **values = NULL;
924 *seq = DOM_SEQUENCE_NONE;
927 * Parameterised (5) second timeout on open. This is needed as the
928 * search timeout doesn't seem to apply to doing an open as well. JRA.
931 ldp = ldap_open_with_timeout(server, port, lp_ldap_timeout());
935 /* Timeout if no response within 20 seconds. */
939 if (ldap_search_st(ldp, "", LDAP_SCOPE_BASE, "(objectclass=*)",
940 CONST_DISCARD(char **, attrs), 0, &to, &res))
943 if (ldap_count_entries(ldp, res) != 1)
946 values = ldap_get_values(ldp, res, "highestCommittedUSN");
947 if (!values || !values[0])
950 *seq = atoi(values[0]);
956 ldap_value_free(values);
964 /**********************************************************************
965 Get the sequence number for a Windows AD native mode domain using
967 **********************************************************************/
969 static int get_ldap_sequence_number(struct winbindd_domain *domain, uint32 *seq)
972 char addr[INET6_ADDRSTRLEN];
974 print_sockaddr(addr, sizeof(addr), &domain->dcaddr);
975 if ((ret = get_ldap_seq(addr, LDAP_PORT, seq)) == 0) {
976 DEBUG(3, ("get_ldap_sequence_number: Retrieved sequence "
977 "number for Domain (%s) from DC (%s)\n",
978 domain->name, addr));
983 #endif /* HAVE_LDAP */
985 /* find the sequence number for a domain */
986 static NTSTATUS sequence_number(struct winbindd_domain *domain, uint32 *seq)
989 union samr_DomainInfo *info = NULL;
991 struct policy_handle dom_pol;
992 bool got_seq_num = False;
993 struct rpc_pipe_client *cli;
995 DEBUG(10,("rpc: fetch sequence_number for %s\n", domain->name));
997 if ( !winbindd_can_contact_domain( domain ) ) {
998 DEBUG(10,("sequence_number: No incoming trust for domain %s\n",
1001 return NT_STATUS_OK;
1004 *seq = DOM_SEQUENCE_NONE;
1006 if (!(mem_ctx = talloc_init("sequence_number[rpc]")))
1007 return NT_STATUS_NO_MEMORY;
1010 if ( domain->active_directory )
1014 DEBUG(8,("using get_ldap_seq() to retrieve the "
1015 "sequence number\n"));
1017 res = get_ldap_sequence_number( domain, seq );
1020 result = NT_STATUS_OK;
1021 DEBUG(10,("domain_sequence_number: LDAP for "
1022 "domain %s is %u\n",
1023 domain->name, *seq));
1027 DEBUG(10,("domain_sequence_number: failed to get LDAP "
1028 "sequence number for domain %s\n",
1031 #endif /* HAVE_LDAP */
1033 result = cm_connect_sam(domain, mem_ctx, &cli, &dom_pol);
1034 if (!NT_STATUS_IS_OK(result)) {
1038 /* Query domain info */
1040 result = rpccli_samr_QueryDomainInfo(cli, mem_ctx,
1045 if (NT_STATUS_IS_OK(result)) {
1046 *seq = info->info8.sequence_num;
1051 /* retry with info-level 2 in case the dc does not support info-level 8
1052 * (like all older samba2 and samba3 dc's) - Guenther */
1054 result = rpccli_samr_QueryDomainInfo(cli, mem_ctx,
1059 if (NT_STATUS_IS_OK(result)) {
1060 *seq = info->general.sequence_num;
1066 DEBUG(10,("domain_sequence_number: for domain %s is %u\n",
1067 domain->name, (unsigned)*seq));
1069 DEBUG(10,("domain_sequence_number: failed to get sequence "
1070 "number (%u) for domain %s\n",
1071 (unsigned)*seq, domain->name ));
1076 talloc_destroy(mem_ctx);
1081 /* get a list of trusted domains */
1082 static NTSTATUS trusted_domains(struct winbindd_domain *domain,
1083 TALLOC_CTX *mem_ctx,
1084 uint32 *num_domains,
1089 NTSTATUS result = NT_STATUS_UNSUCCESSFUL;
1090 uint32 enum_ctx = 0;
1091 struct rpc_pipe_client *cli;
1092 struct policy_handle lsa_policy;
1094 DEBUG(3,("rpc: trusted_domains\n"));
1101 result = cm_connect_lsa(domain, mem_ctx, &cli, &lsa_policy);
1102 if (!NT_STATUS_IS_OK(result))
1105 result = STATUS_MORE_ENTRIES;
1107 while (NT_STATUS_EQUAL(result, STATUS_MORE_ENTRIES)) {
1110 struct lsa_DomainList dom_list;
1112 result = rpccli_lsa_EnumTrustDom(cli, mem_ctx,
1118 if (!NT_STATUS_IS_OK(result) &&
1119 !NT_STATUS_EQUAL(result, STATUS_MORE_ENTRIES))
1122 start_idx = *num_domains;
1123 *num_domains += dom_list.count;
1124 *names = TALLOC_REALLOC_ARRAY(mem_ctx, *names,
1125 char *, *num_domains);
1126 *dom_sids = TALLOC_REALLOC_ARRAY(mem_ctx, *dom_sids,
1127 DOM_SID, *num_domains);
1128 *alt_names = TALLOC_REALLOC_ARRAY(mem_ctx, *alt_names,
1129 char *, *num_domains);
1130 if ((*names == NULL) || (*dom_sids == NULL) ||
1131 (*alt_names == NULL))
1132 return NT_STATUS_NO_MEMORY;
1134 for (i=0; i<dom_list.count; i++) {
1135 (*names)[start_idx+i] = CONST_DISCARD(char *, dom_list.domains[i].name.string);
1136 (*dom_sids)[start_idx+i] = *dom_list.domains[i].sid;
1137 (*alt_names)[start_idx+i] = talloc_strdup(mem_ctx, "");
1143 /* find the lockout policy for a domain */
1144 static NTSTATUS msrpc_lockout_policy(struct winbindd_domain *domain,
1145 TALLOC_CTX *mem_ctx,
1146 struct samr_DomInfo12 *lockout_policy)
1149 struct rpc_pipe_client *cli;
1150 struct policy_handle dom_pol;
1151 union samr_DomainInfo *info = NULL;
1153 DEBUG(10,("rpc: fetch lockout policy for %s\n", domain->name));
1155 if ( !winbindd_can_contact_domain( domain ) ) {
1156 DEBUG(10,("msrpc_lockout_policy: No incoming trust for domain %s\n",
1158 return NT_STATUS_NOT_SUPPORTED;
1161 result = cm_connect_sam(domain, mem_ctx, &cli, &dom_pol);
1162 if (!NT_STATUS_IS_OK(result)) {
1166 result = rpccli_samr_QueryDomainInfo(cli, mem_ctx,
1170 if (!NT_STATUS_IS_OK(result)) {
1174 *lockout_policy = info->info12;
1176 DEBUG(10,("msrpc_lockout_policy: lockout_threshold %d\n",
1177 info->info12.lockout_threshold));
1184 /* find the password policy for a domain */
1185 static NTSTATUS msrpc_password_policy(struct winbindd_domain *domain,
1186 TALLOC_CTX *mem_ctx,
1187 struct samr_DomInfo1 *password_policy)
1190 struct rpc_pipe_client *cli;
1191 struct policy_handle dom_pol;
1192 union samr_DomainInfo *info = NULL;
1194 DEBUG(10,("rpc: fetch password policy for %s\n", domain->name));
1196 if ( !winbindd_can_contact_domain( domain ) ) {
1197 DEBUG(10,("msrpc_password_policy: No incoming trust for domain %s\n",
1199 return NT_STATUS_NOT_SUPPORTED;
1202 result = cm_connect_sam(domain, mem_ctx, &cli, &dom_pol);
1203 if (!NT_STATUS_IS_OK(result)) {
1207 result = rpccli_samr_QueryDomainInfo(cli, mem_ctx,
1211 if (!NT_STATUS_IS_OK(result)) {
1215 *password_policy = info->info1;
1217 DEBUG(10,("msrpc_password_policy: min_length_password %d\n",
1218 info->info1.min_password_length));
1226 /* the rpc backend methods are exposed via this structure */
1227 struct winbindd_methods msrpc_methods = {
1234 msrpc_rids_to_names,
1237 msrpc_lookup_useraliases,
1240 msrpc_lockout_policy,
1241 msrpc_password_policy,