smbd: Pass "file_id" through share_entry_forall
[nivanova/samba-autobuild/.git] / source3 / winbindd / winbindd_reconnect_ads.c
1 /*
2    Unix SMB/CIFS implementation.
3
4    Wrapper around winbindd_ads.c to centralize retry logic.
5    Copyright (C) Christof Schmitt 2016
6
7    Based on winbindd_reconnect.c
8    Copyright (C) Volker Lendecke 2005
9
10    This program is free software; you can redistribute it and/or modify
11    it under the terms of the GNU General Public License as published by
12    the Free Software Foundation; either version 3 of the License, or
13    (at your option) any later version.
14
15    This program is distributed in the hope that it will be useful,
16    but WITHOUT ANY WARRANTY; without even the implied warranty of
17    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18    GNU General Public License for more details.
19
20    You should have received a copy of the GNU General Public License
21    along with this program.  If not, see <http://www.gnu.org/licenses/>.
22 */
23
24 #include "includes.h"
25 #include "winbindd.h"
26
27 #ifdef HAVE_ADS
28
29 #undef DBGC_CLASS
30 #define DBGC_CLASS DBGC_WINBIND
31
32 extern struct winbindd_methods ads_methods;
33
34 /* List all users */
35 static NTSTATUS query_user_list(struct winbindd_domain *domain,
36                                 TALLOC_CTX *mem_ctx,
37                                 uint32_t **rids)
38 {
39         NTSTATUS result;
40
41         result = ads_methods.query_user_list(domain, mem_ctx, rids);
42
43         if (reconnect_need_retry(result, domain)) {
44                 result = ads_methods.query_user_list(domain, mem_ctx, rids);
45         }
46
47         return result;
48 }
49
50 /* list all domain groups */
51 static NTSTATUS enum_dom_groups(struct winbindd_domain *domain,
52                                 TALLOC_CTX *mem_ctx,
53                                 uint32_t *num_entries,
54                                 struct wb_acct_info **info)
55 {
56         NTSTATUS result;
57
58         result = ads_methods.enum_dom_groups(domain, mem_ctx,
59                                              num_entries, info);
60
61         if (reconnect_need_retry(result, domain)) {
62                 result = ads_methods.enum_dom_groups(domain, mem_ctx,
63                                                      num_entries, info);
64         }
65
66         return result;
67 }
68
69 /* List all domain groups */
70 static NTSTATUS enum_local_groups(struct winbindd_domain *domain,
71                                   TALLOC_CTX *mem_ctx,
72                                   uint32_t *num_entries,
73                                   struct wb_acct_info **info)
74 {
75         NTSTATUS result;
76
77         result = ads_methods.enum_local_groups(domain, mem_ctx,
78                                                num_entries, info);
79
80         if (reconnect_need_retry(result, domain)) {
81                 result = ads_methods.enum_local_groups(domain, mem_ctx,
82                                                        num_entries, info);
83         }
84
85         return result;
86 }
87
88 /* convert a single name to a sid in a domain */
89 static NTSTATUS name_to_sid(struct winbindd_domain *domain,
90                             TALLOC_CTX *mem_ctx,
91                             const char *domain_name,
92                             const char *name,
93                             uint32_t flags,
94                             struct dom_sid *sid,
95                             enum lsa_SidType *type)
96 {
97         NTSTATUS result;
98
99         result = ads_methods.name_to_sid(domain, mem_ctx, domain_name, name,
100                                          flags, sid, type);
101
102         if (reconnect_need_retry(result, domain)) {
103                 result = ads_methods.name_to_sid(domain, mem_ctx,
104                                                  domain_name, name, flags,
105                                                  sid, type);
106         }
107
108         return result;
109 }
110
111 /*
112   convert a domain SID to a user or group name
113 */
114 static NTSTATUS sid_to_name(struct winbindd_domain *domain,
115                             TALLOC_CTX *mem_ctx,
116                             const struct dom_sid *sid,
117                             char **domain_name,
118                             char **name,
119                             enum lsa_SidType *type)
120 {
121         NTSTATUS result;
122
123         result = ads_methods.sid_to_name(domain, mem_ctx, sid,
124                                          domain_name, name, type);
125
126         if (reconnect_need_retry(result, domain))
127                 result = ads_methods.sid_to_name(domain, mem_ctx, sid,
128                                                  domain_name, name, type);
129
130         return result;
131 }
132
133 static NTSTATUS rids_to_names(struct winbindd_domain *domain,
134                               TALLOC_CTX *mem_ctx,
135                               const struct dom_sid *sid,
136                               uint32_t *rids,
137                               size_t num_rids,
138                               char **domain_name,
139                               char ***names,
140                               enum lsa_SidType **types)
141 {
142         NTSTATUS result;
143
144         result = ads_methods.rids_to_names(domain, mem_ctx, sid,
145                                            rids, num_rids,
146                                            domain_name, names, types);
147         if (reconnect_need_retry(result, domain)) {
148                 result = ads_methods.rids_to_names(domain, mem_ctx, sid,
149                                                    rids, num_rids, domain_name,
150                                                    names, types);
151         }
152
153         return result;
154 }
155
156 /* Lookup groups a user is a member of.  I wish Unix had a call like this! */
157 static NTSTATUS lookup_usergroups(struct winbindd_domain *domain,
158                                   TALLOC_CTX *mem_ctx,
159                                   const struct dom_sid *user_sid,
160                                   uint32_t *num_groups,
161                                   struct dom_sid **user_gids)
162 {
163         NTSTATUS result;
164
165         result = ads_methods.lookup_usergroups(domain, mem_ctx, user_sid,
166                                                num_groups, user_gids);
167
168         if (reconnect_need_retry(result, domain)) {
169                 result = ads_methods.lookup_usergroups(domain, mem_ctx,
170                                                        user_sid, num_groups,
171                                                        user_gids);
172         }
173
174         return result;
175 }
176
177 static NTSTATUS lookup_useraliases(struct winbindd_domain *domain,
178                                    TALLOC_CTX *mem_ctx,
179                                    uint32_t num_sids,
180                                    const struct dom_sid *sids,
181                                    uint32_t *num_aliases, uint32_t **alias_rids)
182 {
183         NTSTATUS result;
184
185         result = ads_methods.lookup_useraliases(domain, mem_ctx, num_sids, sids,
186                                                 num_aliases, alias_rids);
187
188         if (reconnect_need_retry(result, domain)) {
189                 result = ads_methods.lookup_useraliases(domain, mem_ctx,
190                                                         num_sids, sids,
191                                                         num_aliases,
192                                                         alias_rids);
193         }
194
195         return result;
196 }
197
198 /* Lookup group membership given a rid.   */
199 static NTSTATUS lookup_groupmem(struct winbindd_domain *domain,
200                                 TALLOC_CTX *mem_ctx,
201                                 const struct dom_sid *group_sid,
202                                 enum lsa_SidType type,
203                                 uint32_t *num_names,
204                                 struct dom_sid **sid_mem, char ***names,
205                                 uint32_t **name_types)
206 {
207         NTSTATUS result;
208
209         result = ads_methods.lookup_groupmem(domain, mem_ctx, group_sid, type,
210                                              num_names, sid_mem, names,
211                                              name_types);
212
213         if (reconnect_need_retry(result, domain)) {
214                 result = ads_methods.lookup_groupmem(domain, mem_ctx, group_sid,
215                                                      type, num_names, sid_mem,
216                                                      names, name_types);
217         }
218
219         return result;
220 }
221
222 /* find the sequence number for a domain */
223 static NTSTATUS sequence_number(struct winbindd_domain *domain, uint32_t *seq)
224 {
225         NTSTATUS result;
226
227         result = ads_methods.sequence_number(domain, seq);
228
229         if (reconnect_need_retry(result, domain)) {
230                 result = ads_methods.sequence_number(domain, seq);
231         }
232
233         return result;
234 }
235
236 /* find the lockout policy of a domain */
237 static NTSTATUS lockout_policy(struct winbindd_domain *domain,
238                                TALLOC_CTX *mem_ctx,
239                                struct samr_DomInfo12 *policy)
240 {
241         NTSTATUS result;
242
243         result = ads_methods.lockout_policy(domain, mem_ctx, policy);
244
245         if (reconnect_need_retry(result, domain)) {
246                 result = ads_methods.lockout_policy(domain, mem_ctx, policy);
247         }
248
249         return result;
250 }
251
252 /* find the password policy of a domain */
253 static NTSTATUS password_policy(struct winbindd_domain *domain,
254                                 TALLOC_CTX *mem_ctx,
255                                 struct samr_DomInfo1 *policy)
256 {
257         NTSTATUS result;
258
259         result = ads_methods.password_policy(domain, mem_ctx, policy);
260
261         if (reconnect_need_retry(result, domain)) {
262                 result = ads_methods.password_policy(domain, mem_ctx, policy);
263         }
264
265         return result;
266 }
267
268 /* get a list of trusted domains */
269 static NTSTATUS trusted_domains(struct winbindd_domain *domain,
270                                 TALLOC_CTX *mem_ctx,
271                                 struct netr_DomainTrustList *trusts)
272 {
273         NTSTATUS result;
274
275         result = ads_methods.trusted_domains(domain, mem_ctx, trusts);
276
277         if (reconnect_need_retry(result, domain)) {
278                 result = ads_methods.trusted_domains(domain, mem_ctx, trusts);
279         }
280
281         return result;
282 }
283
284 /* the rpc backend methods are exposed via this structure */
285 struct winbindd_methods reconnect_ads_methods = {
286         true,
287         query_user_list,
288         enum_dom_groups,
289         enum_local_groups,
290         name_to_sid,
291         sid_to_name,
292         rids_to_names,
293         lookup_usergroups,
294         lookup_useraliases,
295         lookup_groupmem,
296         sequence_number,
297         lockout_policy,
298         password_policy,
299         trusted_domains,
300 };
301
302 #endif