first pass at updating head branch to be to be the same as the SAMBA_2_0 branch
[kai/samba.git] / source / rpc_parse / parse_creds.c
1 /* 
2  *  Unix SMB/Netbios implementation.
3  *  Version 1.9.
4  *  RPC Pipe client / server routines
5  *  Copyright (C) Andrew Tgrpsgell              1992-1999,
6  *  Copyright (C) Luke Kenneth Casson Leighton 1996-1999,
7  *  Copyright (C) Paul Ashton                  1997-1999.
8  *  
9  *  This program is free software; you can redistribute it and/or modify
10  *  it under the terms of the GNU General Public License as published by
11  *  the Free Software Foundation; either version 2 of the License, or
12  *  (at your option) any later version.
13  *  
14  *  This program is distributed in the hope that it will be useful,
15  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  *  GNU General Public License for more details.
18  *  
19  *  You should have received a copy of the GNU General Public License
20  *  along with this program; if not, write to the Free Software
21  *  Foundation, Inc., 675 Mass Ave, Cambgrpsge, MA 02139, USA.
22  */
23
24
25 #include "includes.h"
26
27 extern int DEBUGLEVEL;
28
29
30 /*******************************************************************
31 makes a CREDS_UNIX structure.
32 ********************************************************************/
33 BOOL make_creds_unix(CREDS_UNIX *r_u, const char* user_name,
34                                 const char* requested_name,
35                                 const char* real_name,
36                                 BOOL guest)
37 {
38         if (r_u == NULL) return False;
39
40         DEBUG(5,("make_creds_unix\n"));
41
42         fstrcpy(r_u->user_name     , user_name);
43         fstrcpy(r_u->requested_name, requested_name);
44         fstrcpy(r_u->real_name     , real_name);
45         r_u->guest = guest;
46
47         return True;
48 }
49
50 /*******************************************************************
51 reads or writes a structure.
52 ********************************************************************/
53 BOOL creds_io_unix(char *desc, CREDS_UNIX *r_u, prs_struct *ps, int depth)
54 {
55         if (r_u == NULL) return False;
56
57         prs_debug(ps, depth, desc, "creds_io_unix");
58         depth++;
59
60         prs_align(ps);
61         prs_string("user_name", ps, depth,   r_u->user_name, strlen(r_u->user_name), sizeof(r_u->user_name));
62         prs_align(ps);
63         prs_string("requested_name", ps, depth,   r_u->requested_name, strlen(r_u->requested_name), sizeof(r_u->requested_name));
64         prs_align(ps);
65         prs_string("real_name", ps, depth,   r_u->real_name, strlen(r_u->real_name), sizeof(r_u->real_name));
66         prs_align(ps);
67         prs_uint32("guest", ps, depth, &(r_u->guest));
68         return True;
69 }
70
71
72 /*******************************************************************
73 frees a structure.
74 ********************************************************************/
75 void creds_free_unix(CREDS_UNIX *r_u)
76 {
77 }
78
79 /*******************************************************************
80 makes a CREDS_UNIX_SEC structure.
81 ********************************************************************/
82 BOOL make_creds_unix_sec(CREDS_UNIX_SEC *r_u,
83                 uint32 uid, uint32 gid, uint32 num_grps, gid_t *grps)
84 {
85         int i;
86         if (r_u == NULL) return False;
87
88         DEBUG(5,("make_creds_unix_sec\n"));
89
90         r_u->uid      = uid;
91         r_u->gid      = gid;
92         r_u->num_grps = num_grps;
93         r_u->grps = (uint32*)Realloc(NULL, sizeof(r_u->grps[0]) *
94                                        r_u->num_grps);
95         if (r_u->grps == NULL && num_grps != 0)
96         {
97                 return False;
98         }
99         for (i = 0; i < num_grps; i++)
100         {
101                 r_u->grps[i] = (gid_t)grps[i];
102         }
103
104         return True;
105 }
106
107 /*******************************************************************
108 reads or writes a structure.
109 ********************************************************************/
110 BOOL creds_io_unix_sec(char *desc, CREDS_UNIX_SEC *r_u, prs_struct *ps, int depth)
111 {
112         uint32 i;
113
114         if (r_u == NULL) return False;
115
116         prs_debug(ps, depth, desc, "creds_io_unix_sec");
117         depth++;
118
119         prs_align(ps);
120
121         prs_uint32("uid", ps, depth, &(r_u->uid));
122         prs_uint32("gid", ps, depth, &(r_u->gid));
123         prs_uint32("num_grps", ps, depth, &(r_u->num_grps));
124         if (r_u->num_grps != 0)
125         {
126                 r_u->grps = (uint32*)Realloc(r_u->grps,
127                                        sizeof(r_u->grps[0]) *
128                                        r_u->num_grps);
129                 if (r_u->grps == NULL)
130                 {
131                         creds_free_unix_sec(r_u);
132                         return False;
133                 }
134         }
135         for (i = 0; i < r_u->num_grps; i++)
136         {
137                 prs_uint32("", ps, depth, &(r_u->grps[i]));
138         }
139         return True;
140 }
141
142
143 /*******************************************************************
144 frees a structure.
145 ********************************************************************/
146 void creds_free_unix_sec(CREDS_UNIX_SEC *r_u)
147 {
148         if (r_u->grps != NULL)
149         {
150                 free(r_u->grps);
151                 r_u->grps = NULL;
152         }
153 }
154
155 /*******************************************************************
156 makes a CREDS_NT_SEC structure.
157 ********************************************************************/
158 BOOL make_creds_nt_sec(CREDS_NT_SEC *r_u,
159                 DOM_SID *sid, uint32 num_grps, uint32 *grps)
160 {
161         int i;
162         if (r_u == NULL) return False;
163
164         DEBUG(5,("make_creds_unix_sec\n"));
165
166         sid_copy(&r_u->sid, sid);
167         r_u->num_grps = num_grps;
168         r_u->grp_rids = (uint32*)Realloc(NULL, sizeof(r_u->grp_rids[0]) *
169                                        r_u->num_grps);
170
171         if (r_u->grp_rids == NULL && num_grps != 0)
172         {
173                 return False;
174         }
175         for (i = 0; i < num_grps; i++)
176         {
177                 r_u->grp_rids[i] = grps[i];
178         }
179
180         return True;
181 }
182
183 /*******************************************************************
184 reads or writes a structure.
185 ********************************************************************/
186 BOOL creds_io_nt_sec(char *desc, CREDS_NT_SEC *r_u, prs_struct *ps, int depth)
187 {
188         int i;
189         if (r_u == NULL) return False;
190
191         prs_debug(ps, depth, desc, "creds_io_nt");
192         depth++;
193
194         prs_align(ps);
195
196         smb_io_dom_sid ("sid", &r_u->sid, ps, depth);
197         prs_align(ps);
198
199         prs_uint32("num_grps", ps, depth, &(r_u->num_grps));
200         if (r_u->num_grps != 0)
201         {
202                 r_u->grp_rids = (uint32*)Realloc(r_u->grp_rids,
203                                        sizeof(r_u->grp_rids[0]) *
204                                        r_u->num_grps);
205                 if (r_u->grp_rids == NULL)
206                 {
207                         creds_free_nt_sec(r_u);
208                         return False;
209                 }
210         }
211         for (i = 0; i < r_u->num_grps; i++)
212         {
213                 prs_uint32("", ps, depth, &(r_u->grp_rids[i]));
214         }
215
216         return True;
217 }
218
219 /*******************************************************************
220 frees a structure.
221 ********************************************************************/
222 void creds_free_nt_sec(CREDS_NT_SEC *r_u)
223 {
224         if (r_u->grp_rids != NULL)
225         {
226                 free(r_u->grp_rids);
227                 r_u->grp_rids = NULL;
228         }
229 }
230
231 /*******************************************************************
232 reads or writes a structure.
233 ********************************************************************/
234 BOOL creds_io_pwd_info(char *desc, struct pwd_info *pwd, prs_struct *ps, int depth)
235 {
236         if (pwd == NULL) return False;
237
238         prs_debug(ps, depth, desc, "creds_io_pwd_info");
239         depth++;
240
241         prs_align(ps);
242
243         prs_uint32("nullpwd", ps, depth, &(pwd->null_pwd));
244         if (pwd->null_pwd)
245         {
246                 return True;
247         }
248         
249         prs_uint32("cleartext", ps, depth, &(pwd->cleartext));
250         if (pwd->cleartext)
251         {
252                 prs_string("password", ps, depth,   pwd->password, strlen(pwd->password), sizeof(pwd->password));
253                 prs_align(ps);
254                 return True;
255         }
256         prs_uint32("crypted", ps, depth, &(pwd->crypted));
257                 
258         prs_uint8s(False, "smb_lm_pwd", ps, depth, (char*)&pwd->smb_lm_pwd, sizeof(pwd->smb_lm_pwd));
259         prs_align(ps);
260         prs_uint8s(False, "smb_nt_pwd", ps, depth, (char*)&pwd->smb_nt_pwd, sizeof(pwd->smb_nt_pwd));
261         prs_align(ps);
262
263         prs_uint8s(False, "smb_lm_owf", ps, depth, (char*)&pwd->smb_lm_owf, sizeof(pwd->smb_lm_owf));
264         prs_align(ps);
265         prs_uint32("nt_owf_len", ps, depth, &(pwd->nt_owf_len));
266         if (pwd->nt_owf_len > sizeof(pwd->smb_nt_owf))
267         {
268                 return False;
269         }
270         prs_uint8s(False, "smb_nt_owf", ps, depth, (char*)&pwd->smb_nt_owf, pwd->nt_owf_len);
271         prs_align(ps);
272
273         prs_uint8s(False, "lm_cli_chal", ps, depth, (char*)&pwd->lm_cli_chal, sizeof(pwd->lm_cli_chal));
274         prs_align(ps);
275         prs_uint32("nt_cli_chal_len", ps, depth, &(pwd->nt_cli_chal_len));
276
277         if (pwd->nt_cli_chal_len > sizeof(pwd->nt_cli_chal))
278         {
279                 return False;
280         }
281         prs_uint8s(False, "nt_cli_chal", ps, depth, (char*)&pwd->nt_cli_chal, pwd->nt_cli_chal_len);
282         prs_align(ps);
283
284         return True;
285 }
286
287 /*******************************************************************
288 reads or writes a structure.
289 ********************************************************************/
290 BOOL creds_io_nt(char *desc, CREDS_NT *r_u, prs_struct *ps, int depth)
291 {
292         if (r_u == NULL) return False;
293
294         prs_debug(ps, depth, desc, "creds_io_nt");
295         depth++;
296
297         prs_align(ps);
298
299         /* lkclXXXX CHEAT!!!!!!!! */
300         prs_string("user_name", ps, depth,   r_u->user_name, strlen(r_u->user_name), sizeof(r_u->user_name));
301         prs_align(ps);
302         prs_string("domain", ps, depth,   r_u->domain, strlen(r_u->domain), sizeof(r_u->domain));
303         prs_align(ps);
304
305         creds_io_pwd_info("pwd", &r_u->pwd, ps, depth);
306         prs_align(ps);
307
308         prs_uint32("ntlmssp", ps, depth, &(r_u->ntlmssp_flags));
309
310         return True;
311 }
312
313 /*******************************************************************
314 frees a structure.
315 ********************************************************************/
316 void creds_free_nt(CREDS_NT *r_u)
317 {
318 }
319
320 /*******************************************************************
321 reads or writes a structure.
322 ********************************************************************/
323 BOOL creds_io_hybrid(char *desc, CREDS_HYBRID *r_u, prs_struct *ps, int depth)
324 {
325         if (r_u == NULL) return False;
326
327         prs_debug(ps, depth, desc, "creds_io_hybrid");
328         depth++;
329
330         prs_align(ps);
331
332         prs_uint32("reuse", ps, depth, &(r_u->reuse));
333         prs_uint32("ptr_ntc", ps, depth, &(r_u->ptr_ntc));
334         prs_uint32("ptr_uxc", ps, depth, &(r_u->ptr_uxc));
335         prs_uint32("ptr_nts", ps, depth, &(r_u->ptr_nts));
336         prs_uint32("ptr_uxs", ps, depth, &(r_u->ptr_uxs));
337         if (r_u->ptr_ntc != 0)
338         {
339                 if (!creds_io_nt  ("ntc", &r_u->ntc, ps, depth)) return False;
340         }
341         if (r_u->ptr_uxc != 0)
342         {
343                 if (!creds_io_unix("uxc", &r_u->uxc, ps, depth)) return False;
344         }
345         if (r_u->ptr_nts != 0)
346         {
347                 if (!creds_io_nt_sec  ("nts", &r_u->nts, ps, depth)) return False;
348         }
349         if (r_u->ptr_uxs != 0)
350         {
351                 if (!creds_io_unix_sec("uxs", &r_u->uxs, ps, depth)) return False;
352         }
353         return True;
354 }
355
356 void copy_unix_creds(CREDS_UNIX *to, const CREDS_UNIX *from)
357 {
358         if (from == NULL)
359         {
360                 to->user_name[0] = 0;
361                 return;
362         }
363         fstrcpy(to->user_name, from->user_name);
364 };
365
366 void copy_nt_sec_creds(CREDS_NT_SEC *to, const CREDS_NT_SEC *from)
367 {
368         if (from == NULL)
369         {
370                 ZERO_STRUCTP(to);
371                 return;
372         }
373         memcpy(&to, &from, sizeof(*from));
374 };
375
376 void copy_unix_sec_creds(CREDS_UNIX_SEC *to, const CREDS_UNIX_SEC *from)
377 {
378         if (from == NULL)
379         {
380                 to->uid = -1;
381                 to->gid = -1;
382                 to->num_grps = 0;
383                 to->grps = NULL;
384                 return;
385         }
386         to->uid = from->uid;
387         to->gid = from->gid;
388         to->num_grps = 0;
389         to->grps = NULL;
390
391         if (from->num_grps != 0)
392         {
393                 size_t size = from->num_grps * sizeof(from->grps[0]);
394                 to->grps = (uint32*)malloc(size);
395                 if (to->grps == NULL)
396                 {
397                         return;
398                 }
399                 to->num_grps = from->num_grps;
400                 memcpy(to->grps, from->grps, size);
401         }
402 };
403
404 void copy_nt_creds(struct ntuser_creds *to,
405                                 const struct ntuser_creds *from)
406 {
407         if (from == NULL)
408         {
409                 to->domain[0] = 0;
410                 to->user_name[0] = 0;
411                 pwd_set_nullpwd(&to->pwd);
412                 to->ntlmssp_flags = 0;
413
414                 return;
415         }
416         safe_strcpy(to->domain   , from->domain   , sizeof(from->domain   )-1);
417         safe_strcpy(to->user_name, from->user_name, sizeof(from->user_name)-1);
418         memcpy(&to->pwd, &from->pwd, sizeof(from->pwd));
419         to->ntlmssp_flags = from->ntlmssp_flags;
420 };
421
422 void copy_user_creds(struct user_creds *to,
423                                 const struct user_creds *from)
424 {
425         ZERO_STRUCTP(to);
426         if (from == NULL)
427         {
428                 to->ptr_ntc = 0;
429                 to->ptr_uxc = 0;
430                 to->ptr_nts = 0;
431                 to->ptr_uxs = 0;
432                 copy_nt_creds(&to->ntc, NULL);
433                 copy_unix_creds(&to->uxc, NULL);
434                 copy_nt_sec_creds(&to->nts, NULL);
435                 copy_unix_sec_creds(&to->uxs, NULL);
436                 to->reuse = False;
437                 return;
438         }
439         to->ptr_nts = from->ptr_nts;
440         to->ptr_uxs = from->ptr_uxs;
441         to->ptr_ntc = from->ptr_ntc;
442         to->ptr_uxc = from->ptr_uxc;
443         if (to->ptr_ntc != 0)
444         {
445                 copy_nt_creds(&to->ntc, &from->ntc);
446         }
447         if (to->ptr_uxc != 0)
448         {
449                 copy_unix_creds(&to->uxc, &from->uxc);
450         }
451         if (to->ptr_ntc != 0)
452         {
453                 copy_nt_sec_creds(&to->nts, &from->nts);
454         }
455         if (to->ptr_uxc != 0)
456         {
457                 copy_unix_sec_creds(&to->uxs, &from->uxs);
458         }
459         to->reuse = from->reuse;
460 };
461
462 void free_user_creds(struct user_creds *creds)
463 {
464         creds_free_unix(&creds->uxc);
465         creds_free_nt  (&creds->ntc);
466         creds_free_unix_sec(&creds->uxs);
467         creds_free_nt_sec  (&creds->nts);
468 }
469
470 /*******************************************************************
471 reads or writes a structure.
472 ********************************************************************/
473 BOOL creds_io_cmd(char *desc, CREDS_CMD *r_u, prs_struct *ps, int depth)
474 {
475         if (r_u == NULL) return False;
476
477         prs_debug(ps, depth, desc, "creds_io_cmd");
478         depth++;
479
480         prs_align(ps);
481
482         prs_uint16("version", ps, depth, &(r_u->version));
483         prs_uint16("command", ps, depth, &(r_u->command));
484
485         prs_string("name   ", ps, depth,   r_u->name, strlen(r_u->name), sizeof(r_u->name));
486         prs_align(ps);
487         
488         prs_uint32("ptr_creds", ps, depth, &(r_u->ptr_creds));
489         if (r_u->ptr_creds != 0)
490         {
491                 if (!creds_io_hybrid("creds", r_u->cred, ps, depth))
492                 {
493                         return False;
494                 }
495         }
496
497
498         return True;
499 }
500
501
502 BOOL create_ntuser_creds( prs_struct *ps,
503                                 const char* name, 
504                                 uint16 version, uint16 command,
505                                 const struct ntuser_creds *ntu,
506                                 BOOL reuse)
507 {
508         CREDS_CMD cmd;
509         struct user_creds usr;
510
511         ZERO_STRUCT(cmd);
512         ZERO_STRUCT(usr);
513
514         DEBUG(10,("create_user_creds: %s %d %d\n",
515                 name, version, command));
516
517         usr.reuse = reuse;
518
519         fstrcpy(cmd.name, name);
520         cmd.version = version;
521         cmd.command = command;
522         cmd.ptr_creds = ntu != NULL ? 1 : 0;
523         cmd.cred = &usr;
524
525         if (ntu != NULL)
526         {
527                 copy_nt_creds(&usr.ntc, ntu);
528                 usr.ptr_ntc = 1;
529         }
530         else
531         {
532                 usr.ptr_ntc = 0;
533         }
534                 
535         prs_init(ps, 1024, 4, 0, False);
536
537         ps->offset = 4;
538         return creds_io_cmd("creds", &cmd, ps, 0);
539 }
540
541 BOOL create_user_creds( prs_struct *ps,
542                                 const char* name, 
543                                 uint16 version, uint16 command,
544                                 const struct user_creds *usr)
545 {
546         CREDS_CMD cmd;
547
548         ZERO_STRUCT(cmd);
549
550         DEBUG(10,("create_user_creds: %s %d %d\n",
551                 name, version, command));
552
553         fstrcpy(cmd.name, name);
554         cmd.version = version;
555         cmd.command = command;
556         cmd.ptr_creds = usr != NULL ? 1 : 0;
557         cmd.cred = usr;
558
559         prs_init(ps, 1024, 4, 0, False);
560
561         ps->offset = 4;
562         return creds_io_cmd("creds", &cmd, ps, 0);
563 }