s3: add missing prototype for auth_wbc_init().
[ira/wip.git] / source3 / winbindd / winbindd_reconnect.c
1 /* 
2    Unix SMB/CIFS implementation.
3
4    Wrapper around winbindd_rpc.c to centralize retry logic.
5
6    Copyright (C) Volker Lendecke 2005
7    
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 3 of the License, or
11    (at your option) any later version.
12    
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.
17    
18    You should have received a copy of the GNU General Public License
19    along with this program.  If not, see <http://www.gnu.org/licenses/>.
20 */
21
22 #include "includes.h"
23 #include "winbindd.h"
24
25 #undef DBGC_CLASS
26 #define DBGC_CLASS DBGC_WINBIND
27
28 extern struct winbindd_methods msrpc_methods;
29
30 /* List all users */
31 static NTSTATUS query_user_list(struct winbindd_domain *domain,
32                                 TALLOC_CTX *mem_ctx,
33                                 uint32 *num_entries, 
34                                 WINBIND_USERINFO **info)
35 {
36         NTSTATUS result;
37
38         result = msrpc_methods.query_user_list(domain, mem_ctx,
39                                                num_entries, info);
40
41         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
42                 result = msrpc_methods.query_user_list(domain, mem_ctx,
43                                                        num_entries, info);
44         return result;
45 }
46
47 /* list all domain groups */
48 static NTSTATUS enum_dom_groups(struct winbindd_domain *domain,
49                                 TALLOC_CTX *mem_ctx,
50                                 uint32 *num_entries, 
51                                 struct acct_info **info)
52 {
53         NTSTATUS result;
54
55         result = msrpc_methods.enum_dom_groups(domain, mem_ctx,
56                                                num_entries, info);
57
58         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
59                 result = msrpc_methods.enum_dom_groups(domain, mem_ctx,
60                                                        num_entries, info);
61         return result;
62 }
63
64 /* List all domain groups */
65
66 static NTSTATUS enum_local_groups(struct winbindd_domain *domain,
67                                   TALLOC_CTX *mem_ctx,
68                                   uint32 *num_entries, 
69                                   struct acct_info **info)
70 {
71         NTSTATUS result;
72
73         result = msrpc_methods.enum_local_groups(domain, mem_ctx,
74                                                  num_entries, info);
75
76         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
77                 result = msrpc_methods.enum_local_groups(domain, mem_ctx,
78                                                          num_entries, info);
79
80         return result;
81 }
82
83 /* convert a single name to a sid in a domain */
84 static NTSTATUS name_to_sid(struct winbindd_domain *domain,
85                             TALLOC_CTX *mem_ctx,
86                             enum winbindd_cmd orig_cmd,
87                             const char *domain_name,
88                             const char *name,
89                             DOM_SID *sid,
90                             enum lsa_SidType *type)
91 {
92         NTSTATUS result;
93
94         result = msrpc_methods.name_to_sid(domain, mem_ctx, orig_cmd,
95                                            domain_name, name,
96                                            sid, type);
97
98         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
99                 result = msrpc_methods.name_to_sid(domain, mem_ctx, orig_cmd,
100                                                    domain_name, name,
101                                                    sid, type);
102
103         return result;
104 }
105
106 /*
107   convert a domain SID to a user or group name
108 */
109 static NTSTATUS sid_to_name(struct winbindd_domain *domain,
110                             TALLOC_CTX *mem_ctx,
111                             const DOM_SID *sid,
112                             char **domain_name,
113                             char **name,
114                             enum lsa_SidType *type)
115 {
116         NTSTATUS result;
117
118         result = msrpc_methods.sid_to_name(domain, mem_ctx, sid,
119                                            domain_name, name, type);
120
121         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
122                 result = msrpc_methods.sid_to_name(domain, mem_ctx, sid,
123                                                    domain_name, name, type);
124
125         return result;
126 }
127
128 static NTSTATUS rids_to_names(struct winbindd_domain *domain,
129                               TALLOC_CTX *mem_ctx,
130                               const DOM_SID *sid,
131                               uint32 *rids,
132                               size_t num_rids,
133                               char **domain_name,
134                               char ***names,
135                               enum lsa_SidType **types)
136 {
137         NTSTATUS result;
138
139         result = msrpc_methods.rids_to_names(domain, mem_ctx, sid,
140                                              rids, num_rids,
141                                              domain_name, names, types);
142         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL)) {
143                 result = msrpc_methods.rids_to_names(domain, mem_ctx, sid,
144                                                      rids, num_rids,
145                                                      domain_name, names,
146                                                      types);
147         }
148
149         return result;
150 }
151
152 /* Lookup user information from a rid or username. */
153 static NTSTATUS query_user(struct winbindd_domain *domain, 
154                            TALLOC_CTX *mem_ctx, 
155                            const DOM_SID *user_sid,
156                            WINBIND_USERINFO *user_info)
157 {
158         NTSTATUS result;
159
160         result = msrpc_methods.query_user(domain, mem_ctx, user_sid,
161                                           user_info);
162
163         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
164                 result = msrpc_methods.query_user(domain, mem_ctx, user_sid,
165                                                   user_info);
166
167         return result;
168 }
169
170 /* Lookup groups a user is a member of.  I wish Unix had a call like this! */
171 static NTSTATUS lookup_usergroups(struct winbindd_domain *domain,
172                                   TALLOC_CTX *mem_ctx,
173                                   const DOM_SID *user_sid,
174                                   uint32 *num_groups, DOM_SID **user_gids)
175 {
176         NTSTATUS result;
177
178         result = msrpc_methods.lookup_usergroups(domain, mem_ctx,
179                                                  user_sid, num_groups,
180                                                  user_gids);
181
182         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
183                 result = msrpc_methods.lookup_usergroups(domain, mem_ctx,
184                                                          user_sid, num_groups,
185                                                          user_gids);
186
187         return result;
188 }
189
190 static NTSTATUS lookup_useraliases(struct winbindd_domain *domain,
191                                    TALLOC_CTX *mem_ctx,
192                                    uint32 num_sids, const DOM_SID *sids,
193                                    uint32 *num_aliases, uint32 **alias_rids)
194 {
195         NTSTATUS result;
196
197         result = msrpc_methods.lookup_useraliases(domain, mem_ctx,
198                                                   num_sids, sids,
199                                                   num_aliases,
200                                                   alias_rids);
201
202         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
203                 result = msrpc_methods.lookup_useraliases(domain, mem_ctx,
204                                                           num_sids, sids,
205                                                           num_aliases,
206                                                           alias_rids);
207
208         return result;
209 }
210
211 /* Lookup group membership given a rid.   */
212 static NTSTATUS lookup_groupmem(struct winbindd_domain *domain,
213                                 TALLOC_CTX *mem_ctx,
214                                 const DOM_SID *group_sid, uint32 *num_names, 
215                                 DOM_SID **sid_mem, char ***names, 
216                                 uint32 **name_types)
217 {
218         NTSTATUS result;
219
220         result = msrpc_methods.lookup_groupmem(domain, mem_ctx,
221                                                group_sid, num_names,
222                                                sid_mem, names,
223                                                name_types);
224
225         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
226                 result = msrpc_methods.lookup_groupmem(domain, mem_ctx,
227                                                        group_sid, num_names,
228                                                        sid_mem, names,
229                                                        name_types);
230
231         return result;
232 }
233
234 /* find the sequence number for a domain */
235 static NTSTATUS sequence_number(struct winbindd_domain *domain, uint32 *seq)
236 {
237         NTSTATUS result;
238
239         result = msrpc_methods.sequence_number(domain, seq);
240
241         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
242                 result = msrpc_methods.sequence_number(domain, seq);
243
244         return result;
245 }
246
247 /* find the lockout policy of a domain */
248 static NTSTATUS lockout_policy(struct winbindd_domain *domain, 
249                                TALLOC_CTX *mem_ctx,
250                                struct samr_DomInfo12 *policy)
251 {
252         NTSTATUS result;
253
254         result = msrpc_methods.lockout_policy(domain, mem_ctx, policy);
255
256         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
257                 result = msrpc_methods.lockout_policy(domain, mem_ctx, policy);
258
259         return result;
260 }
261
262 /* find the password policy of a domain */
263 static NTSTATUS password_policy(struct winbindd_domain *domain, 
264                                 TALLOC_CTX *mem_ctx,
265                                 struct samr_DomInfo1 *policy)
266 {
267         NTSTATUS result;
268  
269         result = msrpc_methods.password_policy(domain, mem_ctx, policy);
270
271         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
272                 result = msrpc_methods.password_policy(domain, mem_ctx, policy);
273         
274         return result;
275 }
276
277 /* get a list of trusted domains */
278 static NTSTATUS trusted_domains(struct winbindd_domain *domain,
279                                 TALLOC_CTX *mem_ctx,
280                                 uint32 *num_domains,
281                                 char ***names,
282                                 char ***alt_names,
283                                 DOM_SID **dom_sids)
284 {
285         NTSTATUS result;
286
287         result = msrpc_methods.trusted_domains(domain, mem_ctx,
288                                                num_domains, names,
289                                                alt_names, dom_sids);
290
291         if (NT_STATUS_EQUAL(result, NT_STATUS_UNSUCCESSFUL))
292                 result = msrpc_methods.trusted_domains(domain, mem_ctx,
293                                                        num_domains, names,
294                                                        alt_names, dom_sids);
295
296         return result;
297 }
298
299 /* the rpc backend methods are exposed via this structure */
300 struct winbindd_methods reconnect_methods = {
301         False,
302         query_user_list,
303         enum_dom_groups,
304         enum_local_groups,
305         name_to_sid,
306         sid_to_name,
307         rids_to_names,
308         query_user,
309         lookup_usergroups,
310         lookup_useraliases,
311         lookup_groupmem,
312         sequence_number,
313         lockout_policy,
314         password_policy,
315         trusted_domains,
316 };