03c26a8021756abf40d4623cd33196933ff819a5
[metze/samba/wip.git] / source4 / auth / system_session.c
1 /* 
2    Unix SMB/CIFS implementation.
3    Authentication utility functions
4    Copyright (C) Andrew Tridgell 1992-1998
5    Copyright (C) Andrew Bartlett 2001-2010
6    Copyright (C) Jeremy Allison 2000-2001
7    Copyright (C) Rafal Szczesniak 2002
8    Copyright (C) Stefan Metzmacher 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 "libcli/security/security.h"
26 #include "auth/credentials/credentials.h"
27 #include "param/param.h"
28 #include "auth/auth.h" /* for auth_user_info_dc */
29 #include "auth/session.h"
30 #include "auth/system_session_proto.h"
31
32 #undef DBGC_CLASS
33 #define DBGC_CLASS DBGC_AUTH
34
35 /*
36   prevent the static system session being freed
37  */
38 static int system_session_destructor(struct auth_session_info *info)
39 {
40         return -1;
41 }
42
43 /* Create a security token for a session SYSTEM (the most
44  * trusted/privileged account), including the local machine account as
45  * the off-host credentials
46  */ 
47 _PUBLIC_ struct auth_session_info *system_session(struct loadparm_context *lp_ctx)
48 {
49         static struct auth_session_info *static_session;
50         NTSTATUS nt_status;
51
52         if (static_session) {
53                 return static_session;
54         }
55
56         /*
57          * Use NULL here, not the autofree context for this
58          * static pointer. The destructor prevents freeing this
59          * memory anyway.
60          */
61         nt_status = auth_system_session_info(NULL,
62                                              lp_ctx,
63                                              &static_session);
64         if (!NT_STATUS_IS_OK(nt_status)) {
65                 talloc_free(static_session);
66                 static_session = NULL;
67                 return NULL;
68         }
69         talloc_set_destructor(static_session, system_session_destructor);
70         return static_session;
71 }
72
73 NTSTATUS auth_system_session_info(TALLOC_CTX *parent_ctx, 
74                                   struct loadparm_context *lp_ctx,
75                                   struct auth_session_info **_session_info) 
76 {
77         NTSTATUS nt_status;
78         struct auth_user_info_dc *user_info_dc = NULL;
79         struct auth_session_info *session_info = NULL;
80         TALLOC_CTX *mem_ctx = talloc_new(parent_ctx);
81         
82         nt_status = auth_system_user_info_dc(mem_ctx, lpcfg_netbios_name(lp_ctx),
83                                             &user_info_dc);
84         if (!NT_STATUS_IS_OK(nt_status)) {
85                 talloc_free(mem_ctx);
86                 return nt_status;
87         }
88
89         /* references the user_info_dc into the session_info */
90         nt_status = auth_generate_session_info(parent_ctx, NULL, NULL, user_info_dc, AUTH_SESSION_INFO_SIMPLE_PRIVILEGES, &session_info);
91         talloc_free(mem_ctx);
92
93         NT_STATUS_NOT_OK_RETURN(nt_status);
94
95         session_info->credentials = cli_credentials_init(session_info);
96         if (!session_info->credentials) {
97                 return NT_STATUS_NO_MEMORY;
98         }
99
100         cli_credentials_set_conf(session_info->credentials, lp_ctx);
101
102         cli_credentials_set_machine_account_pending(session_info->credentials, lp_ctx);
103         *_session_info = session_info;
104
105         return NT_STATUS_OK;
106 }
107
108 NTSTATUS auth_system_user_info_dc(TALLOC_CTX *mem_ctx, const char *netbios_name,
109                                  struct auth_user_info_dc **_user_info_dc)
110 {
111         struct auth_user_info_dc *user_info_dc;
112         struct auth_user_info *info;
113
114         user_info_dc = talloc(mem_ctx, struct auth_user_info_dc);
115         NT_STATUS_HAVE_NO_MEMORY(user_info_dc);
116
117         /* This returns a pointer to a struct dom_sid, which is the
118          * same as a 1 element list of struct dom_sid */
119         user_info_dc->num_sids = 1;
120         user_info_dc->sids = dom_sid_parse_talloc(user_info_dc, SID_NT_SYSTEM);
121         NT_STATUS_HAVE_NO_MEMORY(user_info_dc->sids);
122
123         /* annoying, but the Anonymous really does have a session key, 
124            and it is all zeros! */
125         user_info_dc->user_session_key = data_blob_talloc(user_info_dc, NULL, 16);
126         NT_STATUS_HAVE_NO_MEMORY(user_info_dc->user_session_key.data);
127
128         user_info_dc->lm_session_key = data_blob_talloc(user_info_dc, NULL, 16);
129         NT_STATUS_HAVE_NO_MEMORY(user_info_dc->lm_session_key.data);
130
131         data_blob_clear(&user_info_dc->user_session_key);
132         data_blob_clear(&user_info_dc->lm_session_key);
133
134         user_info_dc->info = info = talloc_zero(user_info_dc, struct auth_user_info);
135         NT_STATUS_HAVE_NO_MEMORY(user_info_dc->info);
136
137         info->account_name = talloc_strdup(info, "SYSTEM");
138         NT_STATUS_HAVE_NO_MEMORY(info->account_name);
139
140         info->domain_name = talloc_strdup(info, "NT AUTHORITY");
141         NT_STATUS_HAVE_NO_MEMORY(info->domain_name);
142
143         info->full_name = talloc_strdup(info, "System");
144         NT_STATUS_HAVE_NO_MEMORY(info->full_name);
145
146         info->logon_script = talloc_strdup(info, "");
147         NT_STATUS_HAVE_NO_MEMORY(info->logon_script);
148
149         info->profile_path = talloc_strdup(info, "");
150         NT_STATUS_HAVE_NO_MEMORY(info->profile_path);
151
152         info->home_directory = talloc_strdup(info, "");
153         NT_STATUS_HAVE_NO_MEMORY(info->home_directory);
154
155         info->home_drive = talloc_strdup(info, "");
156         NT_STATUS_HAVE_NO_MEMORY(info->home_drive);
157
158         info->logon_server = talloc_strdup(info, netbios_name);
159         NT_STATUS_HAVE_NO_MEMORY(info->logon_server);
160
161         info->last_logon = 0;
162         info->last_logoff = 0;
163         info->acct_expiry = 0;
164         info->last_password_change = 0;
165         info->allow_password_change = 0;
166         info->force_password_change = 0;
167
168         info->logon_count = 0;
169         info->bad_password_count = 0;
170
171         info->acct_flags = ACB_NORMAL;
172
173         info->authenticated = true;
174
175         *_user_info_dc = user_info_dc;
176
177         return NT_STATUS_OK;
178 }
179
180
181 static NTSTATUS auth_domain_admin_user_info_dc(TALLOC_CTX *mem_ctx,
182                                               const char *netbios_name,
183                                               const char *domain_name,
184                                               struct dom_sid *domain_sid,
185                                               struct auth_user_info_dc **_user_info_dc)
186 {
187         struct auth_user_info_dc *user_info_dc;
188         struct auth_user_info *info;
189
190         user_info_dc = talloc(mem_ctx, struct auth_user_info_dc);
191         NT_STATUS_HAVE_NO_MEMORY(user_info_dc);
192
193         user_info_dc->num_sids = 7;
194         user_info_dc->sids = talloc_array(user_info_dc, struct dom_sid, user_info_dc->num_sids);
195
196         user_info_dc->sids[PRIMARY_USER_SID_INDEX] = *domain_sid;
197         sid_append_rid(&user_info_dc->sids[PRIMARY_USER_SID_INDEX], DOMAIN_RID_ADMINISTRATOR);
198
199         user_info_dc->sids[PRIMARY_GROUP_SID_INDEX] = *domain_sid;
200         sid_append_rid(&user_info_dc->sids[PRIMARY_GROUP_SID_INDEX], DOMAIN_RID_USERS);
201
202         user_info_dc->sids[2] = global_sid_Builtin_Administrators;
203
204         user_info_dc->sids[3] = *domain_sid;
205         sid_append_rid(&user_info_dc->sids[3], DOMAIN_RID_ADMINS);
206         user_info_dc->sids[4] = *domain_sid;
207         sid_append_rid(&user_info_dc->sids[4], DOMAIN_RID_ENTERPRISE_ADMINS);
208         user_info_dc->sids[5] = *domain_sid;
209         sid_append_rid(&user_info_dc->sids[5], DOMAIN_RID_POLICY_ADMINS);
210         user_info_dc->sids[6] = *domain_sid;
211         sid_append_rid(&user_info_dc->sids[6], DOMAIN_RID_SCHEMA_ADMINS);
212
213         /* What should the session key be?*/
214         user_info_dc->user_session_key = data_blob_talloc(user_info_dc, NULL, 16);
215         NT_STATUS_HAVE_NO_MEMORY(user_info_dc->user_session_key.data);
216
217         user_info_dc->lm_session_key = data_blob_talloc(user_info_dc, NULL, 16);
218         NT_STATUS_HAVE_NO_MEMORY(user_info_dc->lm_session_key.data);
219
220         data_blob_clear(&user_info_dc->user_session_key);
221         data_blob_clear(&user_info_dc->lm_session_key);
222
223         user_info_dc->info = info = talloc_zero(user_info_dc, struct auth_user_info);
224         NT_STATUS_HAVE_NO_MEMORY(user_info_dc->info);
225
226         info->account_name = talloc_strdup(info, "Administrator");
227         NT_STATUS_HAVE_NO_MEMORY(info->account_name);
228
229         info->domain_name = talloc_strdup(info, domain_name);
230         NT_STATUS_HAVE_NO_MEMORY(info->domain_name);
231
232         info->full_name = talloc_strdup(info, "Administrator");
233         NT_STATUS_HAVE_NO_MEMORY(info->full_name);
234
235         info->logon_script = talloc_strdup(info, "");
236         NT_STATUS_HAVE_NO_MEMORY(info->logon_script);
237
238         info->profile_path = talloc_strdup(info, "");
239         NT_STATUS_HAVE_NO_MEMORY(info->profile_path);
240
241         info->home_directory = talloc_strdup(info, "");
242         NT_STATUS_HAVE_NO_MEMORY(info->home_directory);
243
244         info->home_drive = talloc_strdup(info, "");
245         NT_STATUS_HAVE_NO_MEMORY(info->home_drive);
246
247         info->logon_server = talloc_strdup(info, netbios_name);
248         NT_STATUS_HAVE_NO_MEMORY(info->logon_server);
249
250         info->last_logon = 0;
251         info->last_logoff = 0;
252         info->acct_expiry = 0;
253         info->last_password_change = 0;
254         info->allow_password_change = 0;
255         info->force_password_change = 0;
256
257         info->logon_count = 0;
258         info->bad_password_count = 0;
259
260         info->acct_flags = ACB_NORMAL;
261
262         info->authenticated = true;
263
264         *_user_info_dc = user_info_dc;
265
266         return NT_STATUS_OK;
267 }
268
269 static NTSTATUS auth_domain_admin_session_info(TALLOC_CTX *parent_ctx,
270                                                struct loadparm_context *lp_ctx,
271                                                struct dom_sid *domain_sid,
272                                                struct auth_session_info **session_info)
273 {
274         NTSTATUS nt_status;
275         struct auth_user_info_dc *user_info_dc = NULL;
276         TALLOC_CTX *mem_ctx = talloc_new(parent_ctx);
277
278         NT_STATUS_HAVE_NO_MEMORY(mem_ctx);
279
280         nt_status = auth_domain_admin_user_info_dc(mem_ctx, lpcfg_netbios_name(lp_ctx),
281                                                   lpcfg_workgroup(lp_ctx), domain_sid,
282                                                   &user_info_dc);
283         if (!NT_STATUS_IS_OK(nt_status)) {
284                 talloc_free(mem_ctx);
285                 return nt_status;
286         }
287
288         nt_status = auth_generate_session_info(mem_ctx, NULL, NULL, user_info_dc,
289                                                AUTH_SESSION_INFO_SIMPLE_PRIVILEGES|AUTH_SESSION_INFO_AUTHENTICATED|AUTH_SESSION_INFO_DEFAULT_GROUPS,
290                                                session_info);
291         /* There is already a reference between the sesion_info and user_info_dc */
292         if (NT_STATUS_IS_OK(nt_status)) {
293                 talloc_steal(parent_ctx, *session_info);
294         }
295         talloc_free(mem_ctx);
296         return nt_status;
297 }
298
299 _PUBLIC_ struct auth_session_info *admin_session(TALLOC_CTX *mem_ctx, struct loadparm_context *lp_ctx, struct dom_sid *domain_sid)
300 {
301         NTSTATUS nt_status;
302         struct auth_session_info *session_info = NULL;
303         nt_status = auth_domain_admin_session_info(mem_ctx,
304                                                    lp_ctx,
305                                                    domain_sid,
306                                                    &session_info);
307         if (!NT_STATUS_IS_OK(nt_status)) {
308                 return NULL;
309         }
310         return session_info;
311 }
312
313 _PUBLIC_ NTSTATUS auth_anonymous_session_info(TALLOC_CTX *parent_ctx, 
314                                               struct loadparm_context *lp_ctx,
315                                               struct auth_session_info **_session_info) 
316 {
317         NTSTATUS nt_status;
318         struct auth_user_info_dc *user_info_dc = NULL;
319         struct auth_session_info *session_info = NULL;
320         TALLOC_CTX *mem_ctx = talloc_new(parent_ctx);
321         
322         nt_status = auth_anonymous_user_info_dc(mem_ctx,
323                                                lpcfg_netbios_name(lp_ctx),
324                                                &user_info_dc);
325         if (!NT_STATUS_IS_OK(nt_status)) {
326                 talloc_free(mem_ctx);
327                 return nt_status;
328         }
329
330         /* references the user_info_dc into the session_info */
331         nt_status = auth_generate_session_info(parent_ctx, NULL, NULL, user_info_dc, AUTH_SESSION_INFO_SIMPLE_PRIVILEGES, &session_info);
332         talloc_free(mem_ctx);
333
334         NT_STATUS_NOT_OK_RETURN(nt_status);
335
336         session_info->credentials = cli_credentials_init(session_info);
337         if (!session_info->credentials) {
338                 return NT_STATUS_NO_MEMORY;
339         }
340
341         cli_credentials_set_conf(session_info->credentials, lp_ctx);
342         cli_credentials_set_anonymous(session_info->credentials);
343         
344         *_session_info = session_info;
345
346         return NT_STATUS_OK;
347 }
348
349 _PUBLIC_ NTSTATUS auth_anonymous_user_info_dc(TALLOC_CTX *mem_ctx,
350                                     const char *netbios_name,
351                                     struct auth_user_info_dc **_user_info_dc)
352 {
353         struct auth_user_info_dc *user_info_dc;
354         struct auth_user_info *info;
355         user_info_dc = talloc(mem_ctx, struct auth_user_info_dc);
356         NT_STATUS_HAVE_NO_MEMORY(user_info_dc);
357
358         /* This returns a pointer to a struct dom_sid, which is the
359          * same as a 1 element list of struct dom_sid */
360         user_info_dc->num_sids = 1;
361         user_info_dc->sids = dom_sid_parse_talloc(user_info_dc, SID_NT_ANONYMOUS);
362         NT_STATUS_HAVE_NO_MEMORY(user_info_dc->sids);
363
364         /* annoying, but the Anonymous really does have a session key... */
365         user_info_dc->user_session_key = data_blob_talloc(user_info_dc, NULL, 16);
366         NT_STATUS_HAVE_NO_MEMORY(user_info_dc->user_session_key.data);
367
368         user_info_dc->lm_session_key = data_blob_talloc(user_info_dc, NULL, 16);
369         NT_STATUS_HAVE_NO_MEMORY(user_info_dc->lm_session_key.data);
370
371         /*  and it is all zeros! */
372         data_blob_clear(&user_info_dc->user_session_key);
373         data_blob_clear(&user_info_dc->lm_session_key);
374
375         user_info_dc->info = info = talloc_zero(user_info_dc, struct auth_user_info);
376         NT_STATUS_HAVE_NO_MEMORY(user_info_dc->info);
377
378         info->account_name = talloc_strdup(info, "ANONYMOUS LOGON");
379         NT_STATUS_HAVE_NO_MEMORY(info->account_name);
380
381         info->domain_name = talloc_strdup(info, "NT AUTHORITY");
382         NT_STATUS_HAVE_NO_MEMORY(info->domain_name);
383
384         info->full_name = talloc_strdup(info, "Anonymous Logon");
385         NT_STATUS_HAVE_NO_MEMORY(info->full_name);
386
387         info->logon_script = talloc_strdup(info, "");
388         NT_STATUS_HAVE_NO_MEMORY(info->logon_script);
389
390         info->profile_path = talloc_strdup(info, "");
391         NT_STATUS_HAVE_NO_MEMORY(info->profile_path);
392
393         info->home_directory = talloc_strdup(info, "");
394         NT_STATUS_HAVE_NO_MEMORY(info->home_directory);
395
396         info->home_drive = talloc_strdup(info, "");
397         NT_STATUS_HAVE_NO_MEMORY(info->home_drive);
398
399         info->logon_server = talloc_strdup(info, netbios_name);
400         NT_STATUS_HAVE_NO_MEMORY(info->logon_server);
401
402         info->last_logon = 0;
403         info->last_logoff = 0;
404         info->acct_expiry = 0;
405         info->last_password_change = 0;
406         info->allow_password_change = 0;
407         info->force_password_change = 0;
408
409         info->logon_count = 0;
410         info->bad_password_count = 0;
411
412         info->acct_flags = ACB_NORMAL;
413
414         info->authenticated = false;
415
416         *_user_info_dc = user_info_dc;
417
418         return NT_STATUS_OK;
419 }
420