rpc_samr.h parse_samr.c srv_samr.c :
[samba.git] / source3 / rpc_parse / parse_samr.c
1 /* 
2  *  Unix SMB/Netbios implementation.
3  *  Version 1.9.
4  *  RPC Pipe client / server routines
5  *  Copyright (C) Andrew Tridgell              1992-1997,
6  *  Copyright (C) Luke Kenneth Casson Leighton 1996-1997,
7  *  Copyright (C) Paul Ashton                       1997.
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, Cambridge, MA 02139, USA.
22  */
23
24
25 #include "includes.h"
26
27 extern int DEBUGLEVEL;
28
29
30 /*******************************************************************
31 makes a SAMR_Q_CLOSE_HND structure.
32 ********************************************************************/
33 void make_samr_q_close_hnd(SAMR_Q_CLOSE_HND *q_c, POLICY_HND *hnd)
34 {
35         if (q_c == NULL || hnd == NULL) return;
36
37         DEBUG(5,("make_samr_q_close_hnd\n"));
38
39         memcpy(&(q_c->pol), hnd, sizeof(q_c->pol));
40 }
41
42 /*******************************************************************
43 reads or writes a structure.
44 ********************************************************************/
45 void samr_io_q_close_hnd(char *desc,  SAMR_Q_CLOSE_HND *q_u, prs_struct *ps, int depth)
46 {
47         if (q_u == NULL) return;
48
49         prs_debug(ps, depth, desc, "samr_io_q_close_hnd");
50         depth++;
51
52         prs_align(ps);
53
54         smb_io_pol_hnd("pol", &(q_u->pol), ps, depth); 
55         prs_align(ps);
56 }
57
58 /*******************************************************************
59 reads or writes a structure.
60 ********************************************************************/
61 void samr_io_r_close_hnd(char *desc,  SAMR_R_CLOSE_HND *r_u, prs_struct *ps, int depth)
62 {
63         if (r_u == NULL) return;
64
65         prs_debug(ps, depth, desc, "samr_io_r_close_hnd");
66         depth++;
67
68         prs_align(ps);
69
70         smb_io_pol_hnd("pol", &(r_u->pol), ps, depth); 
71         prs_align(ps);
72
73         prs_uint32("status", ps, depth, &(r_u->status));
74 }
75
76
77 /*******************************************************************
78 reads or writes a structure.
79 ********************************************************************/
80 void make_samr_q_open_domain(SAMR_Q_OPEN_DOMAIN *q_u,
81                                 POLICY_HND *connect_pol, uint32 rid,
82                                 DOM_SID *sid)
83 {
84         if (q_u == NULL) return;
85
86         DEBUG(5,("samr_make_samr_q_open_domain\n"));
87
88         memcpy(&q_u->connect_pol, connect_pol, sizeof(q_u->connect_pol));
89         q_u->rid = rid;
90         make_dom_sid2(&(q_u->dom_sid), sid);
91 }
92
93 /*******************************************************************
94 reads or writes a structure.
95 ********************************************************************/
96 void samr_io_q_open_domain(char *desc,  SAMR_Q_OPEN_DOMAIN *q_u, prs_struct *ps, int depth)
97 {
98         if (q_u == NULL) return;
99
100         prs_debug(ps, depth, desc, "samr_io_q_open_domain");
101         depth++;
102
103         prs_align(ps);
104
105         smb_io_pol_hnd("connect_pol", &(q_u->connect_pol), ps, depth); 
106         prs_align(ps);
107
108         prs_uint32("rid", ps, depth, &(q_u->rid));
109
110         smb_io_dom_sid2("sid", &(q_u->dom_sid), ps, depth); 
111         prs_align(ps);
112 }
113
114
115 /*******************************************************************
116 reads or writes a structure.
117 ********************************************************************/
118 void samr_io_r_open_domain(char *desc,  SAMR_R_OPEN_DOMAIN *r_u, prs_struct *ps, int depth)
119 {
120         if (r_u == NULL) return;
121
122         prs_debug(ps, depth, desc, "samr_io_r_open_domain");
123         depth++;
124
125         prs_align(ps);
126
127         smb_io_pol_hnd("domain_pol", &(r_u->domain_pol), ps, depth); 
128         prs_align(ps);
129
130         prs_uint32("status", ps, depth, &(r_u->status));
131 }
132
133 /*******************************************************************
134 reads or writes a structure.
135 ********************************************************************/
136 void make_samr_q_unknown_2c(SAMR_Q_UNKNOWN_2C *q_u, POLICY_HND *user_pol)
137 {
138         if (q_u == NULL) return;
139
140         DEBUG(5,("samr_make_samr_q_unknown_2c\n"));
141
142         memcpy(&q_u->user_pol, user_pol, sizeof(q_u->user_pol));
143 }
144
145
146 /*******************************************************************
147 reads or writes a structure.
148 ********************************************************************/
149 void samr_io_q_unknown_2c(char *desc,  SAMR_Q_UNKNOWN_2C *q_u, prs_struct *ps, int depth)
150 {
151         if (q_u == NULL) return;
152
153         prs_debug(ps, depth, desc, "samr_io_q_unknown_2c");
154         depth++;
155
156         prs_align(ps);
157
158         smb_io_pol_hnd("user_pol", &(q_u->user_pol), ps, depth); 
159         prs_align(ps);
160 }
161
162 /*******************************************************************
163 makes a structure.
164 ********************************************************************/
165 void make_samr_r_unknown_2c(SAMR_R_UNKNOWN_2C *q_u, uint32 status)
166 {
167         if (q_u == NULL) return;
168
169         DEBUG(5,("samr_make_r_unknown_2c\n"));
170
171         q_u->unknown_0 = 0x00160000;
172         q_u->unknown_1 = 0x00000000;
173         q_u->status    = status;
174 }
175
176
177 /*******************************************************************
178 reads or writes a structure.
179 ********************************************************************/
180 void samr_io_r_unknown_2c(char *desc,  SAMR_R_UNKNOWN_2C *r_u, prs_struct *ps, int depth)
181 {
182         if (r_u == NULL) return;
183
184         prs_debug(ps, depth, desc, "samr_io_r_unknown_2c");
185         depth++;
186
187         prs_align(ps);
188
189         prs_uint32("unknown_0", ps, depth, &(r_u->unknown_0));
190         prs_uint32("unknown_1", ps, depth, &(r_u->unknown_1));
191         prs_uint32("status   ", ps, depth, &(r_u->status   ));
192 }
193
194 /*******************************************************************
195 reads or writes a structure.
196 ********************************************************************/
197 void make_samr_q_unknown_3(SAMR_Q_UNKNOWN_3 *q_u,
198                                 POLICY_HND *user_pol, uint16 switch_value)
199 {
200         if (q_u == NULL) return;
201
202         DEBUG(5,("samr_make_samr_q_unknown_3\n"));
203
204         memcpy(&q_u->user_pol, user_pol, sizeof(q_u->user_pol));
205         q_u->switch_value = switch_value;
206 }
207
208
209 /*******************************************************************
210 reads or writes a structure.
211 ********************************************************************/
212 void samr_io_q_unknown_3(char *desc,  SAMR_Q_UNKNOWN_3 *q_u, prs_struct *ps, int depth)
213 {
214         if (q_u == NULL) return;
215
216         prs_debug(ps, depth, desc, "samr_io_q_unknown_3");
217         depth++;
218
219         prs_align(ps);
220
221         smb_io_pol_hnd("user_pol", &(q_u->user_pol), ps, depth); 
222         prs_align(ps);
223
224         prs_uint16("switch_value", ps, depth, &(q_u->switch_value));
225         prs_align(ps);
226 }
227
228 /*******************************************************************
229 reads or writes a structure.
230 ********************************************************************/
231 void make_samr_q_query_dom_info(SAMR_Q_QUERY_DOMAIN_INFO *q_u,
232                                 POLICY_HND *domain_pol, uint16 switch_value)
233 {
234         if (q_u == NULL) return;
235
236         DEBUG(5,("samr_make_samr_q_query_dom_info\n"));
237
238         memcpy(&q_u->domain_pol, domain_pol, sizeof(q_u->domain_pol));
239         q_u->switch_value = switch_value;
240 }
241
242 /*******************************************************************
243 reads or writes a structure.
244 ********************************************************************/
245 void samr_io_q_query_dom_info(char *desc,  SAMR_Q_QUERY_DOMAIN_INFO *q_u, prs_struct *ps, int depth)
246 {
247         if (q_u == NULL) return;
248
249         prs_debug(ps, depth, desc, "samr_io_q_query_dom_info");
250         depth++;
251
252         prs_align(ps);
253
254         smb_io_pol_hnd("domain_pol", &(q_u->domain_pol), ps, depth); 
255         prs_align(ps);
256
257         prs_uint16("switch_value", ps, depth, &(q_u->switch_value));
258         prs_align(ps);
259 }
260
261 /*******************************************************************
262 makes a structure.
263 ********************************************************************/
264 void make_unk_info2(SAM_UNK_INFO_2 *u_2, char *domain, char *server)
265 {
266         int len_domain = strlen(domain);
267         int len_server = strlen(server);
268
269         if (u_2 == NULL) return;
270
271         u_2->unknown_0 = 0x00000000;
272         u_2->unknown_1 = 0x80000000;
273         u_2->unknown_2 = 0x00000000;
274
275         u_2->ptr_0 = 1;
276         make_uni_hdr(&(u_2->hdr_domain), len_domain, len_domain, 1);
277         make_uni_hdr(&(u_2->hdr_server), len_server, len_server, 1);
278
279         u_2->seq_num = 0x10000000;
280         u_2->unknown_3 = 0x00000000;
281         
282         u_2->unknown_4  = 0x00000001;
283         u_2->unknown_5  = 0x00000003;
284         u_2->unknown_6  = 0x00000001;
285         u_2->num_domain_usrs  = 0x00000008;
286         u_2->num_domain_grps = 0x00000003;
287         u_2->num_local_grps = 0x00000003;
288
289         memset(u_2->padding, 0, sizeof(u_2->padding)); /* 12 bytes zeros */
290
291         make_unistr2(&u_2->uni_domain, domain, len_domain);
292         make_unistr2(&u_2->uni_server, server, len_server);
293 }
294
295 /*******************************************************************
296 reads or writes a structure.
297 ********************************************************************/
298 void sam_io_unk_info2(char *desc, SAM_UNK_INFO_2 *u_2, prs_struct *ps, int depth)
299 {
300         if (u_2 == NULL) return;
301
302         prs_debug(ps, depth, desc, "sam_io_unk_info2");
303         depth++;
304
305         prs_uint32("unknown_0", ps, depth, &u_2->unknown_0); /* 0x0000 0000 */
306         prs_uint32("unknown_1", ps, depth, &u_2->unknown_1); /* 0x8000 0000 */
307         prs_uint32("unknown_2", ps, depth, &u_2->unknown_2); /* 0x0000 0000 */
308
309         prs_uint32("ptr_0", ps, depth, &u_2->ptr_0);     /* pointer to unknown structure */
310         smb_io_unihdr("hdr_domain", &u_2->hdr_domain, ps, depth); /* domain name unicode header */
311         smb_io_unihdr("hdr_server", &u_2->hdr_server, ps, depth); /* server name unicode header */
312
313         /* put all the data in here, at the moment, including what the above
314            pointer is referring to
315          */
316
317         prs_uint32("seq_num ", ps, depth, &u_2->seq_num ); /* 0x0000 0099 or 0x1000 0000 */
318         prs_uint32("unknown_3 ", ps, depth, &u_2->unknown_3 ); /* 0x0000 0000 */
319         
320         prs_uint32("unknown_4 ", ps, depth, &u_2->unknown_4 ); /* 0x0000 0001 */
321         prs_uint32("unknown_5 ", ps, depth, &u_2->unknown_5 ); /* 0x0000 0003 */
322         prs_uint32("unknown_6 ", ps, depth, &u_2->unknown_6 ); /* 0x0000 0001 */
323         prs_uint32("num_domain_usrs ", ps, depth, &u_2->num_domain_usrs ); /* 0x0000 0008 */
324         prs_uint32("num_domain_grps", ps, depth, &u_2->num_domain_grps); /* 0x0000 0003 */
325         prs_uint32("num_local_grps", ps, depth, &u_2->num_local_grps); /* 0x0000 0003 */
326
327         prs_uint8s(False, "padding", ps, depth, u_2->padding, sizeof(u_2->padding)); /* 12 bytes zeros */
328
329         smb_io_unistr2( "uni_domain", &u_2->uni_domain, u_2->hdr_domain.buffer, ps, depth); /* domain name unicode string */
330         smb_io_unistr2( "uni_server", &u_2->uni_server, u_2->hdr_server.buffer, ps, depth); /* server name unicode string */
331
332         prs_align(ps);
333
334 }
335
336 /*******************************************************************
337 makes a SAMR_R_QUERY_DOMAIN_INFO structure.
338 ********************************************************************/
339 void make_samr_r_query_dom_info(SAMR_R_QUERY_DOMAIN_INFO *r_u, 
340                                 uint16 switch_value, SAM_UNK_CTR *ctr,
341                                 uint32 status)
342 {
343         if (r_u == NULL || ctr == NULL) return;
344
345         DEBUG(5,("make_samr_r_query_dom_info\n"));
346
347         r_u->ptr_0 = 0;
348         r_u->switch_value = 0;
349         r_u->status = status; /* return status */
350
351         if (status == 0)
352         {
353                 r_u->switch_value = switch_value;
354                 r_u->ptr_0 = 1;
355                 r_u->ctr = ctr;
356         }
357 }
358
359 /*******************************************************************
360 reads or writes a structure.
361 ********************************************************************/
362 void samr_io_r_query_dom_info(char *desc, SAMR_R_QUERY_DOMAIN_INFO *r_u, prs_struct *ps, int depth)
363 {
364         if (r_u == NULL) return;
365
366         prs_debug(ps, depth, desc, "samr_io_r_query_dom_info");
367         depth++;
368
369         prs_align(ps);
370
371         prs_uint32("ptr_0       ", ps, depth, &(r_u->ptr_0));
372         prs_uint16("switch_value", ps, depth, &(r_u->switch_value));
373         prs_align(ps);
374
375         if (r_u->ptr_0 != 0 && r_u->ctr != NULL)
376         {
377                 switch (r_u->switch_value)
378                 {
379                         case 0x02:
380                         {
381                                 sam_io_unk_info2("unk_inf2", &r_u->ctr->info.inf2, ps, depth);
382                                 break;
383                         }
384                         default:
385                         {
386                                 DEBUG(3,("samr_io_r_query_dom_info: unknown switch level 0x%x\n",
387                                           r_u->switch_value));
388                                 return;
389                         }
390                 }
391         }
392 }
393
394
395 /*******************************************************************
396  makes a DOM_SID3 structure.
397
398  calculate length by adding up the size of the components.
399  ********************************************************************/
400 void make_dom_sid3(DOM_SID3 *sid3, uint16 unk_0, uint16 unk_1, DOM_SID *sid)
401 {
402         if (sid3 == NULL) return;
403
404     sid3->sid = *sid;
405         sid3->len = 2 + 8 + sid3->sid.num_auths * 4;
406 }
407
408 /*******************************************************************
409 reads or writes a SAM_SID3 structure.
410
411 this one's odd, because the length (in bytes) is specified at the beginning.
412 the length _includes_ the length of the length, too :-)
413
414 ********************************************************************/
415 static void sam_io_dom_sid3(char *desc,  DOM_SID3 *sid3, prs_struct *ps, int depth)
416 {
417         if (sid3 == NULL) return;
418
419         prs_debug(ps, depth, desc, "sam_io_dom_sid3");
420         depth++;
421
422         prs_uint16("len", ps, depth, &(sid3->len));
423         prs_align(ps);
424         smb_io_dom_sid("", &(sid3->sid), ps, depth); 
425 }
426
427 /*******************************************************************
428 makes a SAMR_R_UNKNOWN3 structure.
429
430 unknown_2   : 0x0001
431 unknown_3   : 0x8004
432
433 unknown_4,5 : 0x0000 0014
434
435 unknown_6   : 0x0002
436 unknown_7   : 0x5800 or 0x0070
437
438 ********************************************************************/
439 static void make_sam_sid_stuff(SAM_SID_STUFF *stf,
440                                 uint16 unknown_2, uint16 unknown_3,
441                                 uint32 unknown_4, uint16 unknown_6, uint16 unknown_7,
442                                 int num_sid3s, DOM_SID3 sid3[MAX_SAM_SIDS])
443 {
444         stf->unknown_2 = unknown_2;
445         stf->unknown_3 = unknown_3;
446
447         bzero(stf->padding1, sizeof(stf->padding1));
448
449         stf->unknown_4 = unknown_4;
450         stf->unknown_5 = unknown_4;
451
452         stf->unknown_6 = unknown_6;
453         stf->unknown_7 = unknown_7;
454
455         stf->num_sids  = num_sid3s;
456
457         stf->padding2  = 0x0000;
458
459         memcpy(stf->sid, sid3, sizeof(DOM_SID3) * num_sid3s);
460 }
461
462 /*******************************************************************
463 reads or writes a SAM_SID_STUFF structure.
464 ********************************************************************/
465 static void sam_io_sid_stuff(char *desc,  SAM_SID_STUFF *stf, prs_struct *ps, int depth)
466 {
467         int i;
468
469         if (stf == NULL) return;
470
471         DEBUG(5,("make_sam_sid_stuff\n"));
472
473         prs_uint16("unknown_2", ps, depth, &(stf->unknown_2));
474         prs_uint16("unknown_3", ps, depth, &(stf->unknown_3));
475
476         prs_uint8s(False, "padding1", ps, depth, stf->padding1, sizeof(stf->padding1)); 
477         
478         prs_uint32("unknown_4", ps, depth, &(stf->unknown_4));
479         prs_uint32("unknown_5", ps, depth, &(stf->unknown_5));
480         prs_uint16("unknown_6", ps, depth, &(stf->unknown_6));
481         prs_uint16("unknown_7", ps, depth, &(stf->unknown_7));
482
483         prs_uint32("num_sids ", ps, depth, &(stf->num_sids ));
484         prs_uint16("padding2 ", ps, depth, &(stf->padding2 ));
485
486         SMB_ASSERT_ARRAY(stf->sid, stf->num_sids);
487
488         for (i = 0; i < stf->num_sids; i++)
489         {
490                 sam_io_dom_sid3("", &(stf->sid[i]), ps, depth); 
491         }
492 }
493
494 /*******************************************************************
495 reads or writes a SAMR_R_UNKNOWN3 structure.
496 ********************************************************************/
497 void make_samr_r_unknown_3(SAMR_R_UNKNOWN_3 *r_u,
498                                 uint16 unknown_2, uint16 unknown_3,
499                                 uint32 unknown_4, uint16 unknown_6, uint16 unknown_7,
500                                 int num_sid3s, DOM_SID3 sid3[MAX_SAM_SIDS],
501                                 uint32 status)
502 {
503         if (r_u == NULL) return;
504
505         DEBUG(5,("samr_make_r_unknown_3\n"));
506
507         r_u->ptr_0 = 0;
508         r_u->ptr_1 = 0;
509
510         if (status == 0x0)
511         {
512                 r_u->ptr_0 = 1;
513                 r_u->ptr_1 = 1;
514                 make_sam_sid_stuff(&(r_u->sid_stuff), unknown_2, unknown_3,
515                        unknown_4, unknown_6, unknown_7,
516                        num_sid3s, sid3);
517         }
518
519         r_u->status = status;
520 }
521
522
523 /*******************************************************************
524 reads or writes a SAMR_R_UNKNOWN_3 structure.
525
526 this one's odd, because the daft buggers use a different mechanism
527 for writing out the array of sids. they put the number of sids in
528 only one place: they've calculated the length of each sid and jumped
529 by that amount.  then, retrospectively, the length of the whole buffer
530 is put at the beginning of the data stream.
531
532 wierd.  
533
534 ********************************************************************/
535 void samr_io_r_unknown_3(char *desc,  SAMR_R_UNKNOWN_3 *r_u, prs_struct *ps, int depth)
536 {
537         int ptr_len0=0;
538         int ptr_len1=0;
539         int ptr_sid_stuff = 0;
540
541         if (r_u == NULL) return;
542
543         prs_debug(ps, depth, desc, "samr_io_r_unknown_3");
544         depth++;
545
546         prs_align(ps);
547
548         prs_uint32("ptr_0         ", ps, depth, &(r_u->ptr_0         ));
549
550         if (ps->io) 
551         {
552                 /* reading.  do the length later */
553                 prs_uint32("sid_stuff_len0", ps, depth, &(r_u->sid_stuff_len0));
554         }
555         else
556         {
557                 /* storing */
558                 ptr_len0 = ps->offset; ps->offset += 4;
559         }
560
561         if (r_u->ptr_0 != 0)
562         {
563                 prs_uint32("ptr_1         ", ps, depth, &(r_u->ptr_1         ));
564                 if (ps->io)
565                 {
566                         /* reading.  do the length later */
567                         prs_uint32("sid_stuff_len1", ps, depth, &(r_u->sid_stuff_len1));
568                 }
569                 else
570                 {
571                         /* storing */
572                         ptr_len1 = ps->offset; ps->offset += 4;
573                 }
574
575                 if (r_u->ptr_1 != 0)
576                 {
577                         ptr_sid_stuff = ps->offset;
578                         sam_io_sid_stuff("", &(r_u->sid_stuff), ps, depth); 
579                 }
580         }
581
582         if (!(ps->io)) /* storing not reading.  do the length, now. */
583         {
584                 if (ptr_sid_stuff != 0)
585                 {
586                         uint32 sid_stuff_len = ps->offset - ptr_sid_stuff;
587                         int old_len = ps->offset;
588
589                         ps->offset = ptr_len0;
590                         prs_uint32("sid_stuff_len0", ps, depth, &sid_stuff_len); 
591
592                         ps->offset = ptr_len1;
593                         prs_uint32("sid_stuff_len1", ps, depth, &sid_stuff_len);
594
595                         ps->offset = old_len;
596                 }
597         }
598
599         prs_uint32("status", ps, depth, &(r_u->status));
600 }
601
602 /*******************************************************************
603 reads or writes a SAM_STR1 structure.
604 ********************************************************************/
605 static void sam_io_sam_str1(char *desc,  SAM_STR1 *sam, uint32 acct_buf, uint32 name_buf, uint32 desc_buf, prs_struct *ps, int depth)
606 {
607         if (sam == NULL) return;
608
609         prs_debug(ps, depth, desc, "sam_io_sam_str1");
610         depth++;
611
612         prs_align(ps);
613
614         smb_io_unistr2("unistr2", &(sam->uni_acct_name), acct_buf, ps, depth); /* account name unicode string */
615         smb_io_unistr2("unistr2", &(sam->uni_full_name), name_buf, ps, depth); /* full name unicode string */
616         smb_io_unistr2("unistr2", &(sam->uni_acct_desc), desc_buf, ps, depth); /* account description unicode string */
617 }
618
619 /*******************************************************************
620 makes a SAM_ENTRY1 structure.
621 ********************************************************************/
622 static void make_sam_entry1(SAM_ENTRY1 *sam, uint32 user_idx, 
623                                 uint32 len_sam_name, uint32 len_sam_full, uint32 len_sam_desc,
624                                 uint32 rid_user, uint16 acb_info)
625 {
626         if (sam == NULL) return;
627
628         DEBUG(5,("make_sam_entry1\n"));
629
630         sam->user_idx = user_idx;
631         sam->rid_user = rid_user;
632         sam->acb_info = acb_info;
633         sam->pad      = 0;
634
635         make_uni_hdr(&(sam->hdr_acct_name), len_sam_name, len_sam_name, len_sam_name != 0);
636         make_uni_hdr(&(sam->hdr_user_name), len_sam_full, len_sam_full, len_sam_full != 0);
637         make_uni_hdr(&(sam->hdr_user_desc), len_sam_desc, len_sam_desc, len_sam_desc != 0);
638 }
639
640 /*******************************************************************
641 reads or writes a SAM_ENTRY1 structure.
642 ********************************************************************/
643 static void sam_io_sam_entry1(char *desc,  SAM_ENTRY1 *sam, prs_struct *ps, int depth)
644 {
645         if (sam == NULL) return;
646
647         prs_debug(ps, depth, desc, "sam_io_sam_entry1");
648         depth++;
649
650         prs_align(ps);
651
652         prs_uint32("user_idx ", ps, depth, &(sam->user_idx ));
653
654         prs_uint32("rid_user ", ps, depth, &(sam->rid_user ));
655         prs_uint16("acb_info ", ps, depth, &(sam->acb_info ));
656         prs_uint16("pad      ", ps, depth, &(sam->pad      ));
657
658         smb_io_unihdr("unihdr", &(sam->hdr_acct_name), ps, depth); /* account name unicode string header */
659         smb_io_unihdr("unihdr", &(sam->hdr_user_name), ps, depth); /* account name unicode string header */
660         smb_io_unihdr("unihdr", &(sam->hdr_user_desc), ps, depth); /* account name unicode string header */
661 }
662
663 /*******************************************************************
664 reads or writes a SAM_STR2 structure.
665 ********************************************************************/
666 static void sam_io_sam_str2(char *desc,  SAM_STR2 *sam, uint32 acct_buf, uint32 desc_buf, prs_struct *ps, int depth)
667 {
668         if (sam == NULL) return;
669
670         prs_debug(ps, depth, desc, "sam_io_sam_str2");
671         depth++;
672
673         prs_align(ps);
674
675         smb_io_unistr2("unistr2", &(sam->uni_srv_name), acct_buf, ps, depth); /* account name unicode string */
676         smb_io_unistr2("unistr2", &(sam->uni_srv_desc), desc_buf, ps, depth); /* account description unicode string */
677 }
678
679 /*******************************************************************
680 makes a SAM_ENTRY2 structure.
681 ********************************************************************/
682 static void make_sam_entry2(SAM_ENTRY2 *sam, uint32 user_idx, 
683                                 uint32 len_sam_name, uint32 len_sam_desc,
684                                 uint32 rid_user, uint16 acb_info)
685 {
686         if (sam == NULL) return;
687
688         DEBUG(5,("make_sam_entry2\n"));
689
690         sam->user_idx = user_idx;
691         sam->rid_user = rid_user;
692         sam->acb_info = acb_info;
693         sam->pad      = 0;
694
695         make_uni_hdr(&(sam->hdr_srv_name), len_sam_name, len_sam_name, len_sam_name != 0);
696         make_uni_hdr(&(sam->hdr_srv_desc), len_sam_desc, len_sam_desc, len_sam_desc != 0);
697 }
698
699 /*******************************************************************
700 reads or writes a SAM_ENTRY2 structure.
701 ********************************************************************/
702 static void sam_io_sam_entry2(char *desc,  SAM_ENTRY2 *sam, prs_struct *ps, int depth)
703 {
704         if (sam == NULL) return;
705
706         prs_debug(ps, depth, desc, "sam_io_sam_entry2");
707         depth++;
708
709         prs_align(ps);
710
711         prs_uint32("user_idx ", ps, depth, &(sam->user_idx ));
712
713         prs_uint32("rid_user ", ps, depth, &(sam->rid_user ));
714         prs_uint16("acb_info ", ps, depth, &(sam->acb_info ));
715         prs_uint16("pad      ", ps, depth, &(sam->pad      ));
716
717         smb_io_unihdr("unihdr", &(sam->hdr_srv_name), ps, depth); /* account name unicode string header */
718         smb_io_unihdr("unihdr", &(sam->hdr_srv_desc), ps, depth); /* account name unicode string header */
719 }
720
721 /*******************************************************************
722 reads or writes a SAM_STR3 structure.
723 ********************************************************************/
724 static void sam_io_sam_str3(char *desc,  SAM_STR3 *sam, uint32 acct_buf, uint32 desc_buf, prs_struct *ps, int depth)
725 {
726         if (sam == NULL) return;
727
728         prs_debug(ps, depth, desc, "sam_io_sam_str3");
729         depth++;
730
731         prs_align(ps);
732
733         smb_io_unistr2("unistr2", &(sam->uni_grp_name), acct_buf, ps, depth); /* account name unicode string */
734         smb_io_unistr2("unistr2", &(sam->uni_grp_desc), desc_buf, ps, depth); /* account description unicode string */
735 }
736
737 /*******************************************************************
738 makes a SAM_ENTRY3 structure.
739 ********************************************************************/
740 static void make_sam_entry3(SAM_ENTRY3 *sam, uint32 grp_idx, 
741                                 uint32 len_grp_name, uint32 len_grp_desc, uint32 rid_grp)
742 {
743         if (sam == NULL) return;
744
745         DEBUG(5,("make_sam_entry3\n"));
746
747         sam->grp_idx = grp_idx;
748         sam->rid_grp = rid_grp;
749         sam->attr    = 0x07; /* group rid attributes - gets ignored by nt 4.0 */
750
751         make_uni_hdr(&(sam->hdr_grp_name), len_grp_name, len_grp_name, len_grp_name != 0);
752         make_uni_hdr(&(sam->hdr_grp_desc), len_grp_desc, len_grp_desc, len_grp_desc != 0);
753 }
754
755 /*******************************************************************
756 reads or writes a SAM_ENTRY3 structure.
757 ********************************************************************/
758 static void sam_io_sam_entry3(char *desc,  SAM_ENTRY3 *sam, prs_struct *ps, int depth)
759 {
760         if (sam == NULL) return;
761
762         prs_debug(ps, depth, desc, "sam_io_sam_entry3");
763         depth++;
764
765         prs_align(ps);
766
767         prs_uint32("grp_idx", ps, depth, &(sam->grp_idx));
768
769         prs_uint32("rid_grp", ps, depth, &(sam->rid_grp));
770         prs_uint32("attr   ", ps, depth, &(sam->attr   ));
771
772         smb_io_unihdr("unihdr", &(sam->hdr_grp_name), ps, depth); /* account name unicode string header */
773         smb_io_unihdr("unihdr", &(sam->hdr_grp_desc), ps, depth); /* account name unicode string header */
774 }
775
776 /*******************************************************************
777 makes a SAM_ENTRY structure.
778 ********************************************************************/
779 static void make_sam_entry(SAM_ENTRY *sam, uint32 len_sam_name, uint32 rid)
780 {
781         if (sam == NULL) return;
782
783         DEBUG(5,("make_sam_entry\n"));
784
785         sam->rid = rid;
786         make_uni_hdr(&(sam->hdr_name), len_sam_name, len_sam_name, len_sam_name != 0);
787 }
788
789 /*******************************************************************
790 reads or writes a SAM_ENTRY structure.
791 ********************************************************************/
792 static void sam_io_sam_entry(char *desc,  SAM_ENTRY *sam, prs_struct *ps, int depth)
793 {
794         if (sam == NULL) return;
795
796         prs_debug(ps, depth, desc, "sam_io_sam_entry");
797         depth++;
798
799         prs_align(ps);
800         prs_uint32("rid", ps, depth, &(sam->rid ));
801         smb_io_unihdr("unihdr", &(sam->hdr_name), ps, depth); /* account name unicode string header */
802 }
803
804
805 /*******************************************************************
806 makes a SAMR_Q_ENUM_DOM_USERS structure.
807 ********************************************************************/
808 void make_samr_q_enum_dom_users(SAMR_Q_ENUM_DOM_USERS *q_e, POLICY_HND *pol,
809                                 uint16 req_num_entries, uint16 unk_0,
810                                 uint16 acb_mask, uint16 unk_1, uint32 size)
811 {
812         if (q_e == NULL || pol == NULL) return;
813
814         DEBUG(5,("make_samr_q_enum_dom_users\n"));
815
816         memcpy(&(q_e->pol), pol, sizeof(*pol));
817
818         q_e->req_num_entries = req_num_entries; /* zero indicates lots */
819         q_e->unknown_0 = unk_0; /* this gets returned in the response */
820         q_e->acb_mask  = acb_mask;
821         q_e->unknown_1 = unk_1;
822         q_e->max_size = size;
823 }
824
825 /*******************************************************************
826 reads or writes a structure.
827 ********************************************************************/
828 void samr_io_q_enum_dom_users(char *desc,  SAMR_Q_ENUM_DOM_USERS *q_e, prs_struct *ps, int depth)
829 {
830         if (q_e == NULL) return;
831
832         prs_debug(ps, depth, desc, "samr_io_q_enum_dom_users");
833         depth++;
834
835         prs_align(ps);
836
837         smb_io_pol_hnd("pol", &(q_e->pol), ps, depth); 
838         prs_align(ps);
839
840         prs_uint16("req_num_entries", ps, depth, &(q_e->req_num_entries));
841         prs_uint16("unknown_0      ", ps, depth, &(q_e->unknown_0      ));
842
843         prs_uint16("acb_mask       ", ps, depth, &(q_e->acb_mask       ));
844         prs_uint16("unknown_1      ", ps, depth, &(q_e->unknown_1      ));
845
846         prs_uint32("max_size       ", ps, depth, &(q_e->max_size       ));
847
848         prs_align(ps);
849 }
850
851
852 /*******************************************************************
853 makes a SAMR_R_ENUM_DOM_USERS structure.
854 ********************************************************************/
855 void make_samr_r_enum_dom_users(SAMR_R_ENUM_DOM_USERS *r_u,
856                 uint16 total_num_entries, uint16 unk_0,
857                 uint32 num_sam_entries, SAM_USER_INFO_21 pass[MAX_SAM_ENTRIES], uint32 status)
858 {
859         int i;
860
861         if (r_u == NULL) return;
862
863         DEBUG(5,("make_samr_r_enum_dom_users\n"));
864
865         if (num_sam_entries >= MAX_SAM_ENTRIES)
866         {
867                 num_sam_entries = MAX_SAM_ENTRIES;
868                 DEBUG(5,("limiting number of entries to %d\n",
869                          num_sam_entries));
870         }
871
872         r_u->total_num_entries = total_num_entries;
873         r_u->unknown_0         = unk_0;
874
875         if (total_num_entries > 0)
876         {
877                 r_u->ptr_entries1 = 1;
878                 r_u->ptr_entries2 = 1;
879                 r_u->num_entries2 = num_sam_entries;
880                 r_u->num_entries3 = num_sam_entries;
881
882                 SMB_ASSERT_ARRAY(r_u->sam, num_sam_entries);
883                 SMB_ASSERT_ARRAY(r_u->uni_acct_name, num_sam_entries);
884
885                 for (i = 0; i < num_sam_entries; i++)
886                 {
887                         make_sam_entry(&(r_u->sam[i]),
888                                        pass[i].uni_user_name.uni_str_len,
889                                        pass[i].user_rid);
890
891                         copy_unistr2(&(r_u->uni_acct_name[i]), &(pass[i].uni_user_name));
892                 }
893
894                 r_u->num_entries4 = num_sam_entries;
895         }
896         else
897         {
898                 r_u->ptr_entries1 = 0;
899                 r_u->num_entries2 = num_sam_entries;
900                 r_u->ptr_entries2 = 1;
901         }
902
903         r_u->status = status;
904 }
905
906 /*******************************************************************
907 reads or writes a structure.
908 ********************************************************************/
909 void samr_io_r_enum_dom_users(char *desc,  SAMR_R_ENUM_DOM_USERS *r_u, prs_struct *ps, int depth)
910 {
911         int i;
912
913         if (r_u == NULL) return;
914
915         prs_debug(ps, depth, desc, "samr_io_r_enum_dom_users");
916         depth++;
917
918         prs_align(ps);
919
920         prs_uint16("total_num_entries", ps, depth, &(r_u->total_num_entries));
921         prs_uint16("unknown_0        ", ps, depth, &(r_u->unknown_0        ));
922         prs_uint32("ptr_entries1", ps, depth, &(r_u->ptr_entries1));
923
924         if (r_u->total_num_entries != 0 && r_u->ptr_entries1 != 0)
925         {
926                 prs_uint32("num_entries2", ps, depth, &(r_u->num_entries2));
927                 prs_uint32("ptr_entries2", ps, depth, &(r_u->ptr_entries2));
928                 prs_uint32("num_entries3", ps, depth, &(r_u->num_entries3));
929
930                 SMB_ASSERT_ARRAY(r_u->sam, r_u->num_entries2);
931
932                 for (i = 0; i < r_u->num_entries2; i++)
933                 {
934                         prs_grow(ps);
935                         sam_io_sam_entry("", &(r_u->sam[i]), ps, depth);
936                 }
937
938                 SMB_ASSERT_ARRAY(r_u->uni_acct_name, r_u->num_entries2);
939
940                 for (i = 0; i < r_u->num_entries2; i++)
941                 {
942                         prs_grow(ps);
943                         smb_io_unistr2("", &(r_u->uni_acct_name[i]), r_u->sam[i].hdr_name.buffer, ps, depth);
944                 }
945
946                 prs_align(ps);
947
948                 prs_uint32("num_entries4", ps, depth, &(r_u->num_entries4));
949         }
950
951         prs_uint32("status", ps, depth, &(r_u->status));
952 }
953
954 /*******************************************************************
955 makes a SAMR_Q_QUERY_DISPINFO structure.
956 ********************************************************************/
957 void make_samr_q_query_dispinfo(SAMR_Q_QUERY_DISPINFO *q_e, POLICY_HND *pol,
958                                 uint16 switch_level, uint32 start_idx, uint32 size)
959 {
960         if (q_e == NULL || pol == NULL) return;
961
962         DEBUG(5,("make_samr_q_query_dispinfo\n"));
963
964         memcpy(&(q_e->pol), pol, sizeof(*pol));
965
966         q_e->switch_level = switch_level;
967
968         q_e->unknown_0 = 0;
969         q_e->start_idx = start_idx;
970         q_e->unknown_1 = 0x000007d0;
971         q_e->max_size  = size;
972 }
973
974 /*******************************************************************
975 reads or writes a structure.
976 ********************************************************************/
977 void samr_io_q_query_dispinfo(char *desc,  SAMR_Q_QUERY_DISPINFO *q_e, prs_struct *ps, int depth)
978 {
979         if (q_e == NULL) return;
980
981         prs_debug(ps, depth, desc, "samr_io_q_query_dispinfo");
982         depth++;
983
984         prs_align(ps);
985
986         smb_io_pol_hnd("pol", &(q_e->pol), ps, depth); 
987         prs_align(ps);
988
989         prs_uint16("switch_level", ps, depth, &(q_e->switch_level));
990         prs_uint16("unknown_0   ", ps, depth, &(q_e->unknown_0   ));
991         prs_uint32("start_idx   ", ps, depth, &(q_e->start_idx   ));
992         prs_uint32("unknown_1   ", ps, depth, &(q_e->unknown_1   ));
993         prs_uint32("max_size    ", ps, depth, &(q_e->max_size    ));
994
995         prs_align(ps);
996 }
997
998
999 /*******************************************************************
1000 makes a SAM_INFO_2 structure.
1001 ********************************************************************/
1002 void make_sam_info_2(SAM_INFO_2 *sam, uint32 acb_mask,
1003                 uint32 start_idx, uint32 num_sam_entries,
1004                 SAM_USER_INFO_21 pass[MAX_SAM_ENTRIES])
1005 {
1006         int i;
1007         int entries_added;
1008
1009         if (sam == NULL) return;
1010
1011         DEBUG(5,("make_sam_info_2\n"));
1012
1013         if (num_sam_entries >= MAX_SAM_ENTRIES)
1014         {
1015                 num_sam_entries = MAX_SAM_ENTRIES;
1016                 DEBUG(5,("limiting number of entries to %d\n", 
1017                          num_sam_entries));
1018         }
1019
1020         for (i = start_idx, entries_added = 0; i < num_sam_entries; i++)
1021         {
1022                 if (IS_BITS_SET_ALL(pass[i].acb_info, acb_mask))
1023                 {
1024                         make_sam_entry2(&(sam->sam[entries_added]),
1025                                         start_idx + entries_added + 1,
1026                                         pass[i].uni_user_name.uni_str_len,
1027                                         pass[i].uni_acct_desc.uni_str_len,
1028                                         pass[i].user_rid,
1029                                         pass[i].acb_info);
1030
1031                         copy_unistr2(&(sam->str[entries_added].uni_srv_name), &(pass[i].uni_user_name));
1032                         copy_unistr2(&(sam->str[entries_added].uni_srv_desc), &(pass[i].uni_acct_desc));
1033
1034                         entries_added++;
1035                 }
1036
1037                 sam->num_entries   = entries_added;
1038                 sam->ptr_entries   = 1;
1039                 sam->num_entries2  = entries_added;
1040         }
1041 }
1042
1043 /*******************************************************************
1044 reads or writes a structure.
1045 ********************************************************************/
1046 static void sam_io_sam_info_2(char *desc,  SAM_INFO_2 *sam, prs_struct *ps, int depth)
1047 {
1048         int i;
1049
1050         if (sam == NULL) return;
1051
1052         prs_debug(ps, depth, desc, "sam_io_sam_info_2");
1053         depth++;
1054
1055         prs_align(ps);
1056
1057         prs_uint32("num_entries  ", ps, depth, &(sam->num_entries  ));
1058         prs_uint32("ptr_entries  ", ps, depth, &(sam->ptr_entries  ));
1059
1060         prs_uint32("num_entries2 ", ps, depth, &(sam->num_entries2 ));
1061
1062         SMB_ASSERT_ARRAY(sam->sam, sam->num_entries);
1063
1064         for (i = 0; i < sam->num_entries; i++)
1065         {
1066                 prs_grow(ps);
1067                 sam_io_sam_entry2("", &(sam->sam[i]), ps, depth);
1068         }
1069
1070         for (i = 0; i < sam->num_entries; i++)
1071         {
1072                 prs_grow(ps);
1073                 sam_io_sam_str2 ("", &(sam->str[i]),
1074                                                          sam->sam[i].hdr_srv_name.buffer,
1075                                                          sam->sam[i].hdr_srv_desc.buffer,
1076                                                          ps, depth);
1077         }
1078 }
1079
1080
1081 /*******************************************************************
1082 makes a SAM_INFO_1 structure.
1083 ********************************************************************/
1084 void make_sam_info_1(SAM_INFO_1 *sam, uint32 acb_mask,
1085                 uint32 start_idx, uint32 num_sam_entries,
1086                 SAM_USER_INFO_21 pass[MAX_SAM_ENTRIES])
1087 {
1088         int i;
1089         int entries_added;
1090
1091         if (sam == NULL) return;
1092
1093         DEBUG(5,("make_sam_info_1\n"));
1094
1095         if (num_sam_entries >= MAX_SAM_ENTRIES)
1096         {
1097                 num_sam_entries = MAX_SAM_ENTRIES;
1098                 DEBUG(5,("limiting number of entries to %d\n", 
1099                          num_sam_entries));
1100         }
1101
1102         for (i = start_idx, entries_added = 0; i < num_sam_entries; i++)
1103         {
1104                 if (IS_BITS_SET_ALL(pass[i].acb_info, acb_mask))
1105                 {
1106                         make_sam_entry1(&(sam->sam[entries_added]),
1107                                                 start_idx + entries_added + 1,
1108                                                 pass[i].uni_user_name.uni_str_len,
1109                                                 pass[i].uni_full_name.uni_str_len, 
1110                                                 pass[i].uni_acct_desc.uni_str_len,
1111                                                 pass[i].user_rid,
1112                                                 pass[i].acb_info);
1113
1114                         copy_unistr2(&(sam->str[entries_added].uni_acct_name), &(pass[i].uni_user_name));
1115                         copy_unistr2(&(sam->str[entries_added].uni_full_name), &(pass[i].uni_full_name));
1116                         copy_unistr2(&(sam->str[entries_added].uni_acct_desc), &(pass[i].uni_acct_desc));
1117
1118                         entries_added++;
1119                 }
1120         }
1121
1122         sam->num_entries   = entries_added;
1123         sam->ptr_entries   = 1;
1124         sam->num_entries2  = entries_added;
1125 }
1126
1127
1128 /*******************************************************************
1129 reads or writes a structure.
1130 ********************************************************************/
1131 static void sam_io_sam_info_1(char *desc,  SAM_INFO_1 *sam, prs_struct *ps, int depth)
1132 {
1133         int i;
1134
1135         if (sam == NULL) return;
1136
1137         prs_debug(ps, depth, desc, "sam_io_sam_info_1");
1138         depth++;
1139
1140         prs_align(ps);
1141
1142         prs_uint32("num_entries  ", ps, depth, &(sam->num_entries  ));
1143         prs_uint32("ptr_entries  ", ps, depth, &(sam->ptr_entries  ));
1144
1145         prs_uint32("num_entries2 ", ps, depth, &(sam->num_entries2 ));
1146
1147         SMB_ASSERT_ARRAY(sam->sam, sam->num_entries);
1148
1149         for (i = 0; i < sam->num_entries; i++)
1150         {
1151                 prs_grow(ps);
1152                 sam_io_sam_entry1("", &(sam->sam[i]), ps, depth);
1153         }
1154
1155         for (i = 0; i < sam->num_entries; i++)
1156         {
1157                 prs_grow(ps);
1158                 sam_io_sam_str1 ("", &(sam->str[i]),
1159                                                          sam->sam[i].hdr_acct_name.buffer,
1160                                                          sam->sam[i].hdr_user_name.buffer,
1161                                                          sam->sam[i].hdr_user_desc.buffer,
1162                                                          ps, depth);
1163         }
1164 }
1165
1166
1167 /*******************************************************************
1168 makes a SAMR_R_QUERY_DISPINFO structure.
1169 ********************************************************************/
1170 void make_samr_r_query_dispinfo(SAMR_R_QUERY_DISPINFO *r_u,
1171                 uint16 switch_level, SAM_INFO_CTR *ctr, uint32 status)
1172 {
1173         if (r_u == NULL) return;
1174
1175         DEBUG(5,("make_samr_r_query_dispinfo\n"));
1176
1177         if (status == 0x0)
1178         {
1179                 r_u->unknown_0 = 0x0000001;
1180                 r_u->unknown_1 = 0x0000001;
1181         }
1182         else
1183         {
1184                 r_u->unknown_0 = 0x0;
1185                 r_u->unknown_1 = 0x0;
1186         }
1187
1188         r_u->switch_level = switch_level;
1189         r_u->ctr = ctr;
1190         r_u->status = status;
1191 }
1192
1193
1194 /*******************************************************************
1195 reads or writes a structure.
1196 ********************************************************************/
1197 void samr_io_r_query_dispinfo(char *desc,  SAMR_R_QUERY_DISPINFO *r_u, prs_struct *ps, int depth)
1198 {
1199         if (r_u == NULL) return;
1200
1201         prs_debug(ps, depth, desc, "samr_io_r_query_dispinfo");
1202         depth++;
1203
1204         prs_align(ps);
1205
1206         prs_uint32("unknown_0    ", ps, depth, &(r_u->unknown_0    ));
1207         prs_uint32("unknown_1    ", ps, depth, &(r_u->unknown_1    ));
1208         prs_uint16("switch_level ", ps, depth, &(r_u->switch_level ));
1209
1210         prs_align(ps);
1211
1212         switch (r_u->switch_level)
1213         {
1214                 case 0x1:
1215                 {
1216                         sam_io_sam_info_1("users", r_u->ctr->sam.info1, ps, depth);
1217                         break;
1218                 }
1219                 case 0x2:
1220                 {
1221                         sam_io_sam_info_2("servers", r_u->ctr->sam.info2, ps, depth);
1222                         break;
1223                 }
1224                 default:
1225                 {
1226                         DEBUG(5,("samr_io_r_query_dispinfo: unknown switch value\n"));
1227                         break;
1228                 }
1229         }
1230
1231         prs_uint32("status", ps, depth, &(r_u->status));
1232 }
1233
1234
1235 /*******************************************************************
1236 makes a SAMR_Q_OPEN_GROUP structure.
1237 ********************************************************************/
1238 void make_samr_q_open_group(SAMR_Q_OPEN_GROUP *q_c,
1239                                 POLICY_HND *hnd, uint32 unk, uint32 rid)
1240 {
1241         if (q_c == NULL || hnd == NULL) return;
1242
1243         DEBUG(5,("make_samr_q_open_group\n"));
1244
1245         memcpy(&(q_c->domain_pol), hnd, sizeof(q_c->domain_pol));
1246         q_c->unknown = unk;
1247         q_c->rid_group = rid;
1248 }
1249
1250
1251 #if 0
1252 /* SAMR_Q_CREATE_DOM_GROUP - SAM create group */
1253 typedef struct q_samr_create_dom_group_info
1254 {
1255         POLICY_HND pol;        /* policy handle */
1256
1257         UNIHDR hdr_acct_desc;
1258         UNISTR2 uni_acct_desc;
1259
1260         uint16 unknown_1;    /* 0x0002 */
1261         uint16 unknown_2;    /* 0x0001 */
1262
1263 } SAMR_Q_CREATE_DOM_GROUP;
1264
1265 /* SAMR_R_CREATE_DOM_GROUP - SAM create group */
1266 typedef struct r_samr_create_dom_group_info
1267 {
1268         POLICY_HND pol;        /* policy handle */
1269
1270         uint32 rid;    
1271         uint32 status;    
1272
1273 } SAMR_R_CREATE_DOM_GROUP;
1274
1275 /* SAMR_Q_QUERY_GROUPINFO - SAM Group Info */
1276 typedef struct q_samr_query_group_info
1277 {
1278         POLICY_HND pol;        /* policy handle */
1279
1280         uint16 switch_level;    /* 0x0001 seen */
1281
1282 } SAMR_Q_QUERY_GROUPINFO;
1283
1284 typedef struct samr_group_info1
1285 {
1286         UNIHDR hdr_acct_name;
1287         UNIHDR hdr_acct_desc;
1288
1289         uint32 unknown_1; /* 0x0000 0003 - number of group members? */
1290         uint32 unknown_2; /* 0x0000 0001 - number of group members? */
1291
1292         UNISTR2 uni_acct_name;
1293         UNISTR2 uni_acct_desc;
1294
1295 } GROUP_INFO1;
1296
1297 typedef struct samr_group_info4
1298 {
1299         UNIHDR hdr_acct_desc;
1300         UNISTR2 uni_acct_desc;
1301
1302 } GROUP_INFO4;
1303
1304 /* SAMR_R_QUERY_GROUPINFO - SAM Group Info */
1305 typedef struct r_samr_query_groupinfo_info
1306 {
1307         uint32 ptr;        
1308         uint16 switch_value;     /* 0x0001 seen */
1309         /* uint8[2] padding */
1310
1311         union
1312         {
1313                 GROUP_INFO1 info1;
1314
1315         } group;
1316
1317         uint32 status;
1318
1319 } SAMR_R_QUERY_GROUPINFO;
1320
1321
1322 /* SAMR_Q_SET_GROUPINFO - SAM Group Info */
1323 typedef struct q_samr_set_group_info
1324 {
1325         POLICY_HND pol;        /* policy handle */
1326         uint16 switch_value1;     /* 0x0004 seen */
1327         uint16 switch_value2;     /* 0x0004 seen */
1328
1329         union
1330         {
1331                 GROUP_INFO4 info4;
1332
1333         } group;
1334
1335 } SAMR_Q_SET_GROUPINFO;
1336
1337 /* SAMR_R_SET_GROUPINFO - SAM Group Info */
1338 typedef struct r_samr_set_group_info
1339 {
1340         uint32 status;
1341
1342 } SAMR_R_SET_GROUPINFO;
1343
1344
1345 /* SAMR_Q_ADD_GROUPMEM - probably an add group member */
1346 typedef struct q_samr_add_group_mem_info
1347 {
1348         POLICY_HND pol;       /* policy handle */
1349
1350         uint32 rid;         /* rid */
1351         uint32 unknown;     /* 0x0000 0005 */
1352
1353 } SAMR_Q_ADD_GROUPMEM;
1354
1355
1356 /* SAMR_R_ADD_GROUPMEM - probably an add group member */
1357 typedef struct r_samr_add_group_mem_info
1358 {
1359         uint32 status;         /* return status */
1360
1361 } SAMR_R_ADD_GROUPMEM;
1362
1363
1364 /* SAMR_Q_OPEN_GROUP - probably an open */
1365 typedef struct q_samr_open_group_info
1366 {
1367         POLICY_HND domain_pol;
1368         uint32 unknown;         /* 0x0000 0001, 0x0000 0003, 0x0000 001f */
1369         uint32 rid_group;        /* rid */
1370
1371 } SAMR_Q_OPEN_GROUP;
1372
1373
1374 /* SAMR_R_OPEN_GROUP - probably an open */
1375 typedef struct r_samr_open_group_info
1376 {
1377         POLICY_HND pol;       /* policy handle */
1378         uint32 status;         /* return status */
1379
1380 } SAMR_R_OPEN_GROUP;
1381 #endif
1382
1383
1384
1385 /*******************************************************************
1386 makes a SAMR_Q_ENUM_DOM_GROUPS structure.
1387 ********************************************************************/
1388 void make_samr_q_enum_dom_groups(SAMR_Q_ENUM_DOM_GROUPS *q_e, POLICY_HND *pol,
1389                                 uint16 switch_level, uint32 start_idx, uint32 size)
1390 {
1391         if (q_e == NULL || pol == NULL) return;
1392
1393         DEBUG(5,("make_samr_q_enum_dom_groups\n"));
1394
1395         memcpy(&(q_e->pol), pol, sizeof(*pol));
1396
1397         q_e->switch_level = switch_level;
1398
1399         q_e->unknown_0 = 0;
1400         q_e->start_idx = start_idx;
1401         q_e->unknown_1 = 0x000007d0;
1402         q_e->max_size  = size;
1403 }
1404
1405
1406 /*******************************************************************
1407 reads or writes a structure.
1408 ********************************************************************/
1409 void samr_io_q_enum_dom_groups(char *desc,  SAMR_Q_ENUM_DOM_GROUPS *q_e, prs_struct *ps, int depth)
1410 {
1411         if (q_e == NULL) return;
1412
1413         prs_debug(ps, depth, desc, "samr_io_q_enum_dom_groups");
1414         depth++;
1415
1416         prs_align(ps);
1417
1418         smb_io_pol_hnd("pol", &(q_e->pol), ps, depth); 
1419         prs_align(ps);
1420
1421         prs_uint16("switch_level", ps, depth, &(q_e->switch_level));
1422         prs_uint16("unknown_0   ", ps, depth, &(q_e->unknown_0   ));
1423         prs_uint32("start_idx   ", ps, depth, &(q_e->start_idx   ));
1424         prs_uint32("unknown_1   ", ps, depth, &(q_e->unknown_1   ));
1425         prs_uint32("max_size    ", ps, depth, &(q_e->max_size    ));
1426
1427         prs_align(ps);
1428 }
1429
1430
1431 /*******************************************************************
1432 makes a SAMR_R_ENUM_DOM_GROUPS structure.
1433 ********************************************************************/
1434 void make_samr_r_enum_dom_groups(SAMR_R_ENUM_DOM_GROUPS *r_u,
1435                 uint32 start_idx, uint32 num_sam_entries,
1436                 DOMAIN_GRP *grp,
1437                 uint32 status)
1438 {
1439         int i;
1440         int entries_added;
1441
1442         if (r_u == NULL) return;
1443
1444         DEBUG(5,("make_samr_r_enum_dom_groups\n"));
1445
1446         if (num_sam_entries >= MAX_SAM_ENTRIES)
1447         {
1448                 num_sam_entries = MAX_SAM_ENTRIES;
1449                 DEBUG(5,("limiting number of entries to %d\n", 
1450                          num_sam_entries));
1451         }
1452
1453         if (status == 0x0)
1454         {
1455                 for (i = start_idx, entries_added = 0; i < num_sam_entries; i++)
1456                 {
1457                         int acct_name_len = strlen(grp[i].name);
1458                         int acct_desc_len = strlen(grp[i].comment);
1459
1460                         make_sam_entry3(&(r_u->sam[entries_added]),
1461                                         start_idx + entries_added + 1,
1462                                         acct_name_len,
1463                                         acct_desc_len,
1464                                         grp[i].rid);
1465
1466                         make_unistr2(&(r_u->str[entries_added].uni_grp_name), grp[i].name   , acct_name_len);
1467                         make_unistr2(&(r_u->str[entries_added].uni_grp_desc), grp[i].comment, acct_desc_len);
1468
1469                         entries_added++;
1470                 }
1471
1472                 if (entries_added > 0)
1473                 {
1474                         r_u->unknown_0 = 0x0000492;
1475                         r_u->unknown_1 = 0x000049a;
1476                 }
1477                 else
1478                 {
1479                         r_u->unknown_0 = 0x0;
1480                         r_u->unknown_1 = 0x0;
1481                 }
1482                 r_u->switch_level  = 3;
1483                 r_u->num_entries   = entries_added;
1484                 r_u->ptr_entries   = 1;
1485                 r_u->num_entries2  = entries_added;
1486         }
1487         else
1488         {
1489                 r_u->switch_level = 0;
1490         }
1491
1492         r_u->status = status;
1493 }
1494
1495 /*******************************************************************
1496 reads or writes a structure.
1497 ********************************************************************/
1498 void samr_io_r_enum_dom_groups(char *desc,  SAMR_R_ENUM_DOM_GROUPS *r_u, prs_struct *ps, int depth)
1499 {
1500         int i;
1501
1502         if (r_u == NULL) return;
1503
1504         prs_debug(ps, depth, desc, "samr_io_r_enum_dom_groups");
1505         depth++;
1506
1507         prs_align(ps);
1508
1509         prs_uint32("unknown_0    ", ps, depth, &(r_u->unknown_0    ));
1510         prs_uint32("unknown_1    ", ps, depth, &(r_u->unknown_1    ));
1511         prs_uint32("switch_level ", ps, depth, &(r_u->switch_level ));
1512
1513         if (r_u->switch_level != 0)
1514         {
1515                 prs_uint32("num_entries  ", ps, depth, &(r_u->num_entries  ));
1516                 prs_uint32("ptr_entries  ", ps, depth, &(r_u->ptr_entries  ));
1517
1518                 prs_uint32("num_entries2 ", ps, depth, &(r_u->num_entries2 ));
1519
1520                 SMB_ASSERT_ARRAY(r_u->sam, r_u->num_entries);
1521
1522                 for (i = 0; i < r_u->num_entries; i++)
1523                 {
1524                         prs_grow(ps);
1525                         sam_io_sam_entry3("", &(r_u->sam[i]), ps, depth);
1526                 }
1527
1528                 for (i = 0; i < r_u->num_entries; i++)
1529                 {
1530                         prs_grow(ps);
1531                         sam_io_sam_str3 ("", &(r_u->str[i]),
1532                                              r_u->sam[i].hdr_grp_name.buffer,
1533                                              r_u->sam[i].hdr_grp_desc.buffer,
1534                                              ps, depth);
1535                 }
1536         }
1537
1538         prs_uint32("status", ps, depth, &(r_u->status));
1539 }
1540
1541 /*******************************************************************
1542 makes a SAMR_Q_QUERY_USERGROUPS structure.
1543 ********************************************************************/
1544 void make_samr_q_query_usergroups(SAMR_Q_QUERY_USERGROUPS *q_u,
1545                                 POLICY_HND *hnd)
1546 {
1547         if (q_u == NULL || hnd == NULL) return;
1548
1549         DEBUG(5,("make_samr_q_query_usergroups\n"));
1550
1551         memcpy(&(q_u->pol), hnd, sizeof(q_u->pol));
1552 }
1553
1554
1555 /*******************************************************************
1556 reads or writes a structure.
1557 ********************************************************************/
1558 void samr_io_q_query_usergroups(char *desc,  SAMR_Q_QUERY_USERGROUPS *q_u, prs_struct *ps, int depth)
1559 {
1560         if (q_u == NULL) return;
1561
1562         prs_debug(ps, depth, desc, "samr_io_q_query_usergroups");
1563         depth++;
1564
1565         prs_align(ps);
1566
1567         smb_io_pol_hnd("pol", &(q_u->pol), ps, depth); 
1568         prs_align(ps);
1569 }
1570
1571 /*******************************************************************
1572 makes a SAMR_R_QUERY_USERGROUPS structure.
1573 ********************************************************************/
1574 void make_samr_r_query_usergroups(SAMR_R_QUERY_USERGROUPS *r_u,
1575                 uint32 num_gids, DOM_GID *gid, uint32 status)
1576 {
1577         if (r_u == NULL) return;
1578
1579         DEBUG(5,("make_samr_r_query_usergroups\n"));
1580
1581         if (status == 0x0)
1582         {
1583                 r_u->ptr_0        = 1;
1584                 r_u->num_entries  = num_gids;
1585                 r_u->ptr_1        = (num_gids != 0) ? 1 : 0;
1586                 r_u->num_entries2 = num_gids;
1587
1588                 r_u->gid = gid;
1589         }
1590         else
1591         {
1592                 r_u->ptr_0       = 0;
1593                 r_u->num_entries = 0;
1594                 r_u->ptr_1       = 0;
1595         }
1596
1597         r_u->status = status;
1598 }
1599
1600 /*******************************************************************
1601 reads or writes a structure.
1602 ********************************************************************/
1603 void samr_io_r_query_usergroups(char *desc,  SAMR_R_QUERY_USERGROUPS *r_u, prs_struct *ps, int depth)
1604 {
1605         int i;
1606         if (r_u == NULL) return;
1607
1608         prs_debug(ps, depth, desc, "samr_io_r_query_usergroups");
1609         depth++;
1610
1611         prs_align(ps);
1612
1613         prs_uint32("ptr_0       ", ps, depth, &(r_u->ptr_0      ));
1614
1615         if (r_u->ptr_0 != 0)
1616         {
1617                 prs_uint32("num_entries ", ps, depth, &(r_u->num_entries));
1618                 prs_uint32("ptr_1       ", ps, depth, &(r_u->ptr_1      ));
1619
1620                 if (r_u->num_entries != 0)
1621                 {
1622                         prs_uint32("num_entries2", ps, depth, &(r_u->num_entries2));
1623
1624                         for (i = 0; i < r_u->num_entries2; i++)
1625                         {
1626                                 prs_grow(ps);
1627                                 smb_io_gid("", &(r_u->gid[i]), ps, depth);
1628                         }
1629                 }
1630         }
1631         prs_uint32("status", ps, depth, &(r_u->status));
1632 }
1633
1634
1635 /*******************************************************************
1636 makes a SAMR_Q_ENUM_DOM_ALIASES structure.
1637 ********************************************************************/
1638 void make_samr_q_enum_dom_aliases(SAMR_Q_ENUM_DOM_ALIASES *q_e, POLICY_HND *pol, uint32 size)
1639 {
1640         if (q_e == NULL || pol == NULL) return;
1641
1642         DEBUG(5,("make_samr_q_enum_dom_aliases\n"));
1643
1644         memcpy(&(q_e->pol), pol, sizeof(*pol));
1645
1646         q_e->unknown_0 = 0;
1647         q_e->max_size = size;
1648 }
1649
1650
1651 /*******************************************************************
1652 reads or writes a structure.
1653 ********************************************************************/
1654 void samr_io_q_enum_dom_aliases(char *desc,  SAMR_Q_ENUM_DOM_ALIASES *q_e, prs_struct *ps, int depth)
1655 {
1656         if (q_e == NULL) return;
1657
1658         prs_debug(ps, depth, desc, "samr_io_q_enum_dom_aliases");
1659         depth++;
1660
1661         prs_align(ps);
1662
1663         smb_io_pol_hnd("pol", &(q_e->pol), ps, depth); 
1664         prs_align(ps);
1665
1666         prs_uint32("unknown_0", ps, depth, &(q_e->unknown_0));
1667         prs_uint32("max_size ", ps, depth, &(q_e->max_size ));
1668
1669         prs_align(ps);
1670 }
1671
1672
1673 /*******************************************************************
1674 makes a SAMR_R_ENUM_DOM_ALIASES structure.
1675 ********************************************************************/
1676 void make_samr_r_enum_dom_aliases(SAMR_R_ENUM_DOM_ALIASES *r_u,
1677                 uint32 num_sam_entries, LOCAL_GRP *alss,
1678                 uint32 status)
1679 {
1680         int i;
1681
1682         if (r_u == NULL) return;
1683
1684         DEBUG(5,("make_samr_r_enum_dom_aliases\n"));
1685
1686         if (num_sam_entries >= MAX_SAM_ENTRIES)
1687         {
1688                 num_sam_entries = MAX_SAM_ENTRIES;
1689                 DEBUG(5,("limiting number of entries to %d\n", 
1690                          num_sam_entries));
1691         }
1692
1693         r_u->num_entries  = num_sam_entries;
1694
1695         if (num_sam_entries > 0)
1696         {
1697                 r_u->ptr_entries  = 1;
1698                 r_u->num_entries2 = num_sam_entries;
1699                 r_u->ptr_entries2 = 1;
1700                 r_u->num_entries3 = num_sam_entries;
1701
1702                 SMB_ASSERT_ARRAY(r_u->sam, num_sam_entries);
1703
1704                 for (i = 0; i < num_sam_entries; i++)
1705                 {
1706                         int acct_name_len = strlen(alss[i].name);
1707
1708                         make_sam_entry(&(r_u->sam[i]),
1709                                         acct_name_len,
1710                                         alss[i].rid);
1711
1712                         make_unistr2(&(r_u->uni_grp_name[i]), alss[i].name   , acct_name_len);
1713                 }
1714
1715                 r_u->num_entries4 = num_sam_entries;
1716         }
1717         else
1718         {
1719                 r_u->ptr_entries = 0;
1720         }
1721
1722         r_u->status = status;
1723 }
1724
1725 /*******************************************************************
1726 reads or writes a structure.
1727 ********************************************************************/
1728 void samr_io_r_enum_dom_aliases(char *desc,  SAMR_R_ENUM_DOM_ALIASES *r_u, prs_struct *ps, int depth)
1729 {
1730         int i;
1731
1732         if (r_u == NULL) return;
1733
1734         prs_debug(ps, depth, desc, "samr_io_r_enum_dom_aliases");
1735         depth++;
1736
1737         prs_align(ps);
1738
1739         prs_uint32("num_entries", ps, depth, &(r_u->num_entries));
1740         prs_uint32("ptr_entries", ps, depth, &(r_u->ptr_entries));
1741         
1742         if (r_u->num_entries != 0 && r_u->ptr_entries != 0)
1743         {
1744                 prs_uint32("num_entries2", ps, depth, &(r_u->num_entries2));
1745                 prs_uint32("ptr_entries2", ps, depth, &(r_u->ptr_entries2));
1746                 prs_uint32("num_entries3", ps, depth, &(r_u->num_entries3));
1747
1748                 SMB_ASSERT_ARRAY(r_u->sam, r_u->num_entries);
1749
1750                 for (i = 0; i < r_u->num_entries; i++)
1751                 {
1752                         sam_io_sam_entry("", &(r_u->sam[i]), ps, depth);
1753                 }
1754
1755                 for (i = 0; i < r_u->num_entries; i++)
1756                 {
1757                         smb_io_unistr2("", &(r_u->uni_grp_name[i]), r_u->sam[i].hdr_name.buffer, ps, depth);
1758                 }
1759
1760                 prs_align(ps);
1761
1762                 prs_uint32("num_entries4", ps, depth, &(r_u->num_entries4));
1763         }
1764
1765         prs_uint32("status", ps, depth, &(r_u->status));
1766 }
1767
1768
1769 /*******************************************************************
1770 makes a ALIAS_INFO3 structure.
1771 ********************************************************************/
1772 void make_samr_alias_info3(ALIAS_INFO3 *al3, char *acct_desc)
1773                 {
1774         int acct_len = acct_desc != NULL ? strlen(acct_desc) : 0;
1775         if (al3 == NULL) return;
1776
1777         DEBUG(5,("make_samr_alias_info3\n"));
1778
1779         make_uni_hdr(&(al3->hdr_acct_desc), acct_len , acct_len, acct_desc ? 1 : 0);
1780         make_unistr2(&(al3->uni_acct_desc), acct_desc, acct_len);
1781 }
1782
1783
1784 /*******************************************************************
1785 reads or writes a structure.
1786 ********************************************************************/
1787 void samr_io_alias_info3(char *desc,  ALIAS_INFO3 *al3, prs_struct *ps, int depth)
1788 {
1789         if (al3 == NULL) return;
1790
1791         prs_debug(ps, depth, desc, "samr_io_alias_info3");
1792         depth++;
1793
1794         prs_align(ps);
1795
1796         smb_io_unihdr ("hdr_acct_desc", &(al3->hdr_acct_desc) , ps, depth); 
1797         smb_io_unistr2("uni_acct_desc", &(al3->uni_acct_desc), al3->hdr_acct_desc.buffer, ps, depth);
1798 }
1799
1800 /*******************************************************************
1801 reads or writes a structure.
1802 ********************************************************************/
1803 void samr_alias_info_ctr(char *desc,  ALIAS_INFO_CTR *ctr, prs_struct *ps, int depth)
1804 {
1805         if (ctr == NULL) return;
1806
1807         prs_debug(ps, depth, desc, "samr_alias_info_ctr");
1808         depth++;
1809
1810         prs_uint16("switch_value", ps, depth, &(ctr->switch_value));
1811         prs_align(ps);
1812
1813         if (ctr->switch_value != 0)
1814         {
1815                 switch (ctr->switch_value)
1816                         {
1817                                 case 3:
1818                                 {
1819                                 samr_io_alias_info3("alias_info3", &(ctr->alias.info3), ps, depth);
1820                                         break;
1821                                 }
1822                                 default:
1823                                 {
1824                                 DEBUG(4,("samr_alias_info_ctr: unsupported switch level\n"));
1825                                         break;
1826                                 }
1827                         }
1828                 }
1829
1830         prs_align(ps);
1831 }
1832
1833
1834 /*******************************************************************
1835 makes a SAMR_Q_QUERY_ALIASINFO structure.
1836 ********************************************************************/
1837 void make_samr_q_query_aliasinfo(SAMR_Q_QUERY_ALIASINFO *q_e,
1838                                 POLICY_HND *pol,
1839                                 uint16 switch_level)
1840 {
1841         if (q_e == NULL || pol == NULL) return;
1842
1843         DEBUG(5,("make_samr_q_query_aliasinfo\n"));
1844
1845         memcpy(&(q_e->pol), pol, sizeof(*pol));
1846
1847         q_e->switch_level = switch_level;
1848 }
1849
1850
1851 /*******************************************************************
1852 reads or writes a structure.
1853 ********************************************************************/
1854 void samr_io_q_query_aliasinfo(char *desc,  SAMR_Q_QUERY_ALIASINFO *q_e, prs_struct *ps, int depth)
1855 {
1856         if (q_e == NULL) return;
1857
1858         prs_debug(ps, depth, desc, "samr_io_q_query_aliasinfo");
1859         depth++;
1860
1861         prs_align(ps);
1862
1863         smb_io_pol_hnd("pol", &(q_e->pol), ps, depth); 
1864         prs_align(ps);
1865
1866         prs_uint16("switch_level", ps, depth, &(q_e->switch_level));
1867 }
1868
1869
1870 /*******************************************************************
1871 makes a SAMR_R_QUERY_ALIASINFO structure.
1872 ********************************************************************/
1873 void make_samr_r_query_aliasinfo(SAMR_R_QUERY_ALIASINFO *r_u, ALIAS_INFO_CTR *ctr,
1874                 uint32 status)
1875 {
1876         if (r_u == NULL) return;
1877
1878         DEBUG(5,("make_samr_r_query_aliasinfo\n"));
1879
1880         r_u->ptr = (status == 0x0 && ctr != NULL) ? 1 : 0;
1881         r_u->ctr = ctr;
1882         r_u->status = status;
1883         }
1884
1885
1886 /*******************************************************************
1887 reads or writes a structure.
1888 ********************************************************************/
1889 void samr_io_r_query_aliasinfo(char *desc,  SAMR_R_QUERY_ALIASINFO *r_u, prs_struct *ps, int depth)
1890 {
1891         if (r_u == NULL) return;
1892
1893         prs_debug(ps, depth, desc, "samr_io_r_query_aliasinfo");
1894         depth++;
1895
1896         prs_align(ps);
1897
1898         prs_uint32("ptr", ps, depth, &(r_u->ptr));
1899         
1900         if (r_u->ptr != 0)
1901         {
1902                 samr_alias_info_ctr("ctr", r_u->ctr, ps, depth);
1903         }
1904
1905         prs_uint32("status", ps, depth, &(r_u->status));
1906 }
1907
1908
1909 /*******************************************************************
1910 makes a SAMR_Q_SET_ALIASINFO structure.
1911 ********************************************************************/
1912 void make_samr_q_set_aliasinfo(SAMR_Q_SET_ALIASINFO *q_u, POLICY_HND *hnd,
1913                                 ALIAS_INFO_CTR *ctr)
1914 {
1915         if (q_u == NULL) return;
1916
1917         DEBUG(5,("make_samr_q_set_aliasinfo\n"));
1918
1919         memcpy(&(q_u->alias_pol), hnd, sizeof(q_u->alias_pol));
1920         q_u->ctr = ctr;
1921 }
1922
1923
1924 /*******************************************************************
1925 reads or writes a structure.
1926 ********************************************************************/
1927 void samr_io_q_set_aliasinfo(char *desc,  SAMR_Q_SET_ALIASINFO *q_u, prs_struct *ps, int depth)
1928 {
1929         if (q_u == NULL) return;
1930
1931         prs_debug(ps, depth, desc, "samr_io_q_set_aliasinfo");
1932         depth++;
1933
1934         prs_align(ps);
1935
1936         smb_io_pol_hnd("alias_pol", &(q_u->alias_pol), ps, depth); 
1937         samr_alias_info_ctr("ctr", q_u->ctr, ps, depth);
1938 }
1939
1940 /*******************************************************************
1941 reads or writes a structure.
1942 ********************************************************************/
1943 void samr_io_r_set_aliasinfo(char *desc,  SAMR_R_SET_ALIASINFO *r_u, prs_struct *ps, int depth)
1944 {
1945         if (r_u == NULL) return;
1946
1947         prs_debug(ps, depth, desc, "samr_io_r_set_aliasinfo");
1948         depth++;
1949
1950         prs_align(ps);
1951         prs_uint32("status", ps, depth, &(r_u->status));
1952 }
1953
1954
1955
1956 /*******************************************************************
1957 makes a SAMR_Q_QUERY_USERALIASES structure.
1958 ********************************************************************/
1959 void make_samr_q_query_useraliases(SAMR_Q_QUERY_USERALIASES *q_u,
1960                                 POLICY_HND *hnd,
1961                                 DOM_SID *sid)
1962 {
1963         if (q_u == NULL || hnd == NULL) return;
1964
1965         DEBUG(5,("make_samr_q_query_useraliases\n"));
1966
1967         memcpy(&(q_u->pol), hnd, sizeof(q_u->pol));
1968
1969         q_u->num_sids1 = 1;
1970         q_u->ptr = 0;
1971         q_u->num_sids2 = 1;
1972
1973         {
1974                 q_u->ptr_sid[0] = 1;
1975                 make_dom_sid2(&q_u->sid[0], sid);
1976         }
1977 }
1978
1979 /*******************************************************************
1980 reads or writes a SAMR_Q_QUERY_USERALIASES structure.
1981 ********************************************************************/
1982 void samr_io_q_query_useraliases(char *desc,  SAMR_Q_QUERY_USERALIASES *q_u, prs_struct *ps, int depth)
1983 {
1984         fstring tmp;
1985         int i;
1986
1987         if (q_u == NULL) return;
1988
1989         prs_debug(ps, depth, desc, "samr_io_q_query_useraliases");
1990         depth++;
1991
1992         prs_align(ps);
1993
1994         smb_io_pol_hnd("pol", &(q_u->pol), ps, depth); 
1995         prs_align(ps);
1996
1997         prs_uint32("num_sids1", ps, depth, &(q_u->num_sids1));
1998         prs_uint32("ptr      ", ps, depth, &(q_u->ptr      ));
1999         prs_uint32("num_sids2", ps, depth, &(q_u->num_sids2));
2000
2001         SMB_ASSERT_ARRAY(q_u->ptr_sid, q_u->num_sids2);
2002
2003         for (i = 0; i < q_u->num_sids2; i++)
2004         {
2005                 slprintf(tmp, sizeof(tmp) - 1, "ptr[%02d]", i);
2006                 prs_uint32(tmp, ps, depth, &(q_u->ptr_sid[i]));
2007         }
2008
2009         for (i = 0; i < q_u->num_sids2; i++)
2010         {
2011                 if (q_u->ptr_sid[i] != 0)
2012                 {
2013                         prs_grow(ps);
2014                         slprintf(tmp, sizeof(tmp)-1, "sid[%02d]", i);
2015                         smb_io_dom_sid2(tmp, &(q_u->sid[i]), ps, depth); 
2016                 }
2017         }
2018
2019         prs_align(ps);
2020 }
2021
2022
2023 /*******************************************************************
2024 makes a SAMR_R_QUERY_USERALIASES structure.
2025 ********************************************************************/
2026 void make_samr_r_query_useraliases(SAMR_R_QUERY_USERALIASES *r_u,
2027                 uint32 num_rids, uint32 *rid, uint32 status)
2028 {
2029         if (r_u == NULL) return;
2030
2031         DEBUG(5,("make_samr_r_query_useraliases\n"));
2032
2033         if (status == 0x0)
2034         {
2035                 r_u->num_entries  = num_rids;
2036                 r_u->ptr = 1;
2037                 r_u->num_entries2 = num_rids;
2038
2039                 r_u->rid = rid;
2040         }
2041         else
2042         {
2043                 r_u->num_entries  = 0;
2044                 r_u->ptr = 0;
2045                 r_u->num_entries2 = 0;
2046         }
2047
2048         r_u->status = status;
2049 }
2050
2051 /*******************************************************************
2052 reads or writes a structure.
2053 ********************************************************************/
2054 void samr_io_r_query_useraliases(char *desc,  SAMR_R_QUERY_USERALIASES *r_u, prs_struct *ps, int depth)
2055 {
2056         fstring tmp;
2057         int i;
2058         if (r_u == NULL) return;
2059
2060         prs_debug(ps, depth, desc, "samr_io_r_query_useraliases");
2061         depth++;
2062
2063         prs_align(ps);
2064
2065         prs_uint32("num_entries", ps, depth, &(r_u->num_entries));
2066         prs_uint32("ptr        ", ps, depth, &(r_u->ptr        ));
2067         prs_uint32("num_entries2", ps, depth, &(r_u->num_entries2));
2068
2069         if (r_u->num_entries != 0)
2070         {
2071                 for (i = 0; i < r_u->num_entries2; i++)
2072                 {
2073                         slprintf(tmp, sizeof(tmp)-1, "rid[%02d]", i);
2074                         prs_uint32(tmp, ps, depth, &(r_u->rid[i]));
2075                 }
2076         }
2077
2078         prs_uint32("status", ps, depth, &(r_u->status));
2079 }
2080
2081 /*******************************************************************
2082 makes a SAMR_Q_OPEN_ALIAS structure.
2083 ********************************************************************/
2084 void make_samr_q_open_alias(SAMR_Q_OPEN_ALIAS *q_u,
2085                                 uint32 unknown_0, uint32 rid)
2086 {
2087         if (q_u == NULL) return;
2088
2089         DEBUG(5,("make_samr_q_open_alias\n"));
2090
2091         /* example values: 0x0000 0008 */
2092         q_u->unknown_0 = unknown_0; 
2093
2094         q_u->rid_alias = rid; 
2095 }
2096
2097 /*******************************************************************
2098 reads or writes a structure.
2099 ********************************************************************/
2100 void samr_io_q_open_alias(char *desc,  SAMR_Q_OPEN_ALIAS *q_u, prs_struct *ps, int depth)
2101 {
2102         if (q_u == NULL) return;
2103
2104         prs_debug(ps, depth, desc, "samr_io_q_open_alias");
2105         depth++;
2106
2107         prs_align(ps);
2108
2109         prs_uint32("unknown_0", ps, depth, &(q_u->unknown_0));
2110         prs_uint32("rid_alias", ps, depth, &(q_u->rid_alias));
2111 }
2112
2113 /*******************************************************************
2114 reads or writes a structure.
2115 ********************************************************************/
2116 void samr_io_r_open_alias(char *desc,  SAMR_R_OPEN_ALIAS *r_u, prs_struct *ps, int depth)
2117 {
2118         if (r_u == NULL) return;
2119
2120         prs_debug(ps, depth, desc, "samr_io_r_open_alias");
2121         depth++;
2122
2123         prs_align(ps);
2124
2125         smb_io_pol_hnd("pol", &(r_u->pol), ps, depth); 
2126         prs_align(ps);
2127
2128         prs_uint32("status", ps, depth, &(r_u->status));
2129 }
2130
2131 /*******************************************************************
2132 makes a SAMR_Q_UNKNOWN_12 structure.
2133 ********************************************************************/
2134 void make_samr_q_unknown_12(SAMR_Q_UNKNOWN_12 *q_u,
2135                 POLICY_HND *pol, uint32 rid,
2136                 uint32 num_gids, uint32 *gid)
2137 {
2138         int i;
2139         if (q_u == NULL) return;
2140
2141         DEBUG(5,("make_samr_r_unknwon_12\n"));
2142
2143         memcpy(&(q_u->pol), pol, sizeof(*pol));
2144
2145         q_u->num_gids1 = num_gids;
2146         q_u->rid       = rid;
2147         q_u->ptr       = 0;
2148         q_u->num_gids2 = num_gids;
2149
2150         for (i = 0; i < num_gids; i++)
2151         {
2152                 q_u->gid[i] = gid[i];
2153         }
2154 }
2155
2156 /*******************************************************************
2157 reads or writes a structure.
2158 ********************************************************************/
2159 void samr_io_q_unknown_12(char *desc,  SAMR_Q_UNKNOWN_12 *q_u, prs_struct *ps, int depth)
2160 {
2161         int i;
2162         fstring tmp;
2163
2164         if (q_u == NULL) return;
2165
2166         prs_debug(ps, depth, desc, "samr_io_q_unknown_12");
2167         depth++;
2168
2169         prs_align(ps);
2170
2171         smb_io_pol_hnd("pol", &(q_u->pol), ps, depth); 
2172         prs_align(ps);
2173
2174         prs_uint32("num_gids1", ps, depth, &(q_u->num_gids1));
2175         prs_uint32("rid      ", ps, depth, &(q_u->rid      ));
2176         prs_uint32("ptr      ", ps, depth, &(q_u->ptr      ));
2177         prs_uint32("num_gids2", ps, depth, &(q_u->num_gids2));
2178
2179         SMB_ASSERT_ARRAY(q_u->gid, q_u->num_gids2);
2180
2181         for (i = 0; i < q_u->num_gids2; i++)
2182         {
2183                 prs_grow(ps);
2184                 slprintf(tmp, sizeof(tmp) - 1, "gid[%02d]  ", i);
2185                 prs_uint32(tmp, ps, depth, &(q_u->gid[i]));
2186         }
2187
2188         prs_align(ps);
2189 }
2190
2191
2192 /*******************************************************************
2193 makes a SAMR_R_UNKNOWN_12 structure.
2194 ********************************************************************/
2195 void make_samr_r_unknown_12(SAMR_R_UNKNOWN_12 *r_u,
2196                 uint32 num_aliases, fstring *als_name, uint8 *num_als_usrs,
2197                 uint32 status)
2198 {
2199         int i;
2200         if (r_u == NULL || als_name == NULL || num_als_usrs == NULL) return;
2201
2202         DEBUG(5,("make_samr_r_unknown_12\n"));
2203
2204         if (status == 0x0)
2205         {
2206                 r_u->num_aliases1 = num_aliases;
2207                 r_u->ptr_aliases  = 1;
2208                 r_u->num_aliases2 = num_aliases;
2209
2210                 r_u->num_als_usrs1 = num_aliases;
2211                 r_u->ptr_als_usrs  = 1;
2212                 r_u->num_als_usrs2 = num_aliases;
2213
2214                 SMB_ASSERT_ARRAY(r_u->hdr_als_name, num_aliases);
2215
2216                 for (i = 0; i < num_aliases; i++)
2217                 {
2218                         int als_len = als_name[i] != NULL ? strlen(als_name[i]) : 0;
2219                         make_uni_hdr(&(r_u->hdr_als_name[i]), als_len    , als_len, als_name[i] ? 1 : 0);
2220                         make_unistr2(&(r_u->uni_als_name[i]), als_name[i], als_len);
2221                         r_u->num_als_usrs[i] = num_als_usrs[i];
2222                 }
2223         }
2224         else
2225         {
2226                 r_u->num_aliases1 = num_aliases;
2227                 r_u->ptr_aliases  = 0;
2228                 r_u->num_aliases2 = num_aliases;
2229
2230                 r_u->num_als_usrs1 = num_aliases;
2231                 r_u->ptr_als_usrs  = 0;
2232                 r_u->num_als_usrs2 = num_aliases;
2233         }
2234
2235         r_u->status = status;
2236 }
2237
2238 /*******************************************************************
2239 reads or writes a structure.
2240 ********************************************************************/
2241 void samr_io_r_unknown_12(char *desc,  SAMR_R_UNKNOWN_12 *r_u, prs_struct *ps, int depth)
2242 {
2243         int i;
2244         fstring tmp;
2245         if (r_u == NULL) return;
2246
2247         prs_debug(ps, depth, desc, "samr_io_r_unknown_12");
2248         depth++;
2249
2250         prs_align(ps);
2251
2252         prs_uint32("num_aliases1", ps, depth, &(r_u->num_aliases1));
2253         prs_uint32("ptr_aliases ", ps, depth, &(r_u->ptr_aliases ));
2254         prs_uint32("num_aliases2", ps, depth, &(r_u->num_aliases2));
2255
2256         if (r_u->ptr_aliases != 0 && r_u->num_aliases1 != 0)
2257         {
2258                 SMB_ASSERT_ARRAY(r_u->hdr_als_name, r_u->num_aliases2);
2259
2260                 for (i = 0; i < r_u->num_aliases2; i++)
2261                 {
2262                         prs_grow(ps);
2263                         slprintf(tmp, sizeof(tmp) - 1, "als_hdr[%02d]  ", i);
2264                         smb_io_unihdr ("", &(r_u->hdr_als_name[i]), ps, depth); 
2265                 }
2266                 for (i = 0; i < r_u->num_aliases2; i++)
2267                 {
2268                         prs_grow(ps);
2269                         slprintf(tmp, sizeof(tmp) - 1, "als_str[%02d]  ", i);
2270                         smb_io_unistr2("", &(r_u->uni_als_name[i]), r_u->hdr_als_name[i].buffer, ps, depth); 
2271                 }
2272         }
2273
2274         prs_align(ps);
2275
2276         prs_uint32("num_als_usrs1", ps, depth, &(r_u->num_als_usrs1));
2277         prs_uint32("ptr_als_usrs ", ps, depth, &(r_u->ptr_als_usrs ));
2278         prs_uint32("num_als_usrs2", ps, depth, &(r_u->num_als_usrs2));
2279
2280         if (r_u->ptr_als_usrs != 0 && r_u->num_als_usrs1 != 0)
2281         {
2282                 SMB_ASSERT_ARRAY(r_u->num_als_usrs, r_u->num_als_usrs2);
2283
2284                 for (i = 0; i < r_u->num_als_usrs2; i++)
2285                 {
2286                         prs_grow(ps);
2287                         slprintf(tmp, sizeof(tmp) - 1, "als_usrs[%02d]  ", i);
2288                         prs_uint32(tmp, ps, depth, &(r_u->num_als_usrs[i]));
2289                 }
2290         }
2291
2292         prs_uint32("status", ps, depth, &(r_u->status));
2293 }
2294
2295 /*******************************************************************
2296 makes a SAMR_Q_OPEN_ALIAS structure.
2297 ********************************************************************/
2298 void make_samr_q_delete_alias(SAMR_Q_DELETE_DOM_ALIAS *q_u, POLICY_HND *hnd)
2299 {
2300         if (q_u == NULL) return;
2301
2302         DEBUG(5,("make_samr_q_delete_alias\n"));
2303
2304         memcpy(&(q_u->alias_pol), hnd, sizeof(q_u->alias_pol));
2305 }
2306
2307
2308 /*******************************************************************
2309 reads or writes a structure.
2310 ********************************************************************/
2311 void samr_io_q_delete_alias(char *desc,  SAMR_Q_DELETE_DOM_ALIAS *q_u, prs_struct *ps, int depth)
2312 {
2313         if (q_u == NULL) return;
2314
2315         prs_debug(ps, depth, desc, "samr_io_q_delete_alias");
2316         depth++;
2317
2318         prs_align(ps);
2319
2320         smb_io_pol_hnd("alias_pol", &(q_u->alias_pol), ps, depth); 
2321 }
2322
2323 /*******************************************************************
2324 reads or writes a structure.
2325 ********************************************************************/
2326 void samr_io_r_delete_alias(char *desc,  SAMR_R_DELETE_DOM_ALIAS *r_u, prs_struct *ps, int depth)
2327 {
2328         if (r_u == NULL) return;
2329
2330         prs_debug(ps, depth, desc, "samr_io_r_delete_alias");
2331         depth++;
2332
2333         prs_align(ps);
2334
2335         smb_io_pol_hnd("pol", &(r_u->pol), ps, depth); 
2336         prs_uint32("status", ps, depth, &(r_u->status));
2337 }
2338
2339
2340 /*******************************************************************
2341 makes a SAMR_Q_CREATE_DOM_ALIAS structure.
2342 ********************************************************************/
2343 void make_samr_q_create_dom_alias(SAMR_Q_CREATE_DOM_ALIAS *q_u, POLICY_HND *hnd,
2344                                 char *acct_desc)
2345 {
2346         int acct_len = acct_desc != NULL ? strlen(acct_desc) : 0;
2347         if (q_u == NULL) return;
2348
2349         DEBUG(5,("make_samr_q_create_dom_alias\n"));
2350
2351         memcpy(&(q_u->dom_pol), hnd, sizeof(q_u->dom_pol));
2352
2353         make_uni_hdr(&(q_u->hdr_acct_desc), acct_len , acct_len, acct_desc ? 1 : 0);
2354         make_unistr2(&(q_u->uni_acct_desc), acct_desc, acct_len);
2355
2356         q_u->unknown_1 = 0x001f;
2357         q_u->unknown_2 = 0x000f;
2358 }
2359
2360
2361 /*******************************************************************
2362 reads or writes a structure.
2363 ********************************************************************/
2364 void samr_io_q_create_dom_alias(char *desc,  SAMR_Q_CREATE_DOM_ALIAS *q_u, prs_struct *ps, int depth)
2365 {
2366         if (q_u == NULL) return;
2367
2368         prs_debug(ps, depth, desc, "samr_io_q_create_dom_alias");
2369         depth++;
2370
2371         prs_align(ps);
2372
2373         smb_io_pol_hnd("dom_pol", &(q_u->dom_pol), ps, depth); 
2374
2375         smb_io_unihdr ("hdr_acct_desc", &(q_u->hdr_acct_desc) , ps, depth); 
2376         smb_io_unistr2("uni_acct_desc", &(q_u->uni_acct_desc), q_u->hdr_acct_desc.buffer, ps, depth);
2377
2378         prs_uint16("unknown_1", ps, depth, &(q_u->unknown_1));
2379         prs_uint16("unknown_2", ps, depth, &(q_u->unknown_2));
2380 }
2381
2382 /*******************************************************************
2383 reads or writes a structure.
2384 ********************************************************************/
2385 void samr_io_r_create_dom_alias(char *desc,  SAMR_R_CREATE_DOM_ALIAS *r_u, prs_struct *ps, int depth)
2386 {
2387         if (r_u == NULL) return;
2388
2389         prs_debug(ps, depth, desc, "samr_io_r_create_dom_alias");
2390         depth++;
2391
2392         prs_align(ps);
2393
2394         smb_io_pol_hnd("alias_pol", &(r_u->alias_pol), ps, depth); 
2395         prs_uint32("rid", ps, depth, &(r_u->rid));
2396
2397         prs_uint32("status", ps, depth, &(r_u->status));
2398         }
2399
2400
2401
2402 /*******************************************************************
2403 makes a SAMR_Q_UNK_ALIASMEM structure.
2404 ********************************************************************/
2405 void make_samr_q_unk_aliasmem(SAMR_Q_UNK_ALIASMEM *q_u, POLICY_HND *hnd,
2406                                 DOM_SID *sid)
2407 {
2408         if (q_u == NULL) return;
2409
2410         DEBUG(5,("make_samr_q_unk_aliasmem\n"));
2411
2412         memcpy(&(q_u->alias_pol), hnd, sizeof(q_u->alias_pol));
2413         sid_copy(&q_u->sid, sid);
2414 }
2415
2416
2417 /*******************************************************************
2418 reads or writes a structure.
2419 ********************************************************************/
2420 void samr_io_q_unk_aliasmem(char *desc,  SAMR_Q_UNK_ALIASMEM *q_u, prs_struct *ps, int depth)
2421 {
2422         if (q_u == NULL) return;
2423
2424         prs_debug(ps, depth, desc, "samr_io_q_unk_aliasmem");
2425         depth++;
2426
2427         prs_align(ps);
2428
2429         smb_io_pol_hnd("alias_pol", &(q_u->alias_pol), ps, depth); 
2430         smb_io_dom_sid("sid      ", &(q_u->sid      ), ps, depth); 
2431 }
2432
2433 /*******************************************************************
2434 reads or writes a structure.
2435 ********************************************************************/
2436 void samr_io_r_unk_aliasmem(char *desc,  SAMR_R_UNK_ALIASMEM *r_u, prs_struct *ps, int depth)
2437 {
2438         if (r_u == NULL) return;
2439
2440         prs_debug(ps, depth, desc, "samr_io_r_unk_aliasmem");
2441         depth++;
2442
2443         prs_align(ps);
2444
2445         prs_uint32("status", ps, depth, &(r_u->status));
2446 }
2447
2448
2449 /*******************************************************************
2450 makes a SAMR_Q_ADD_ALIASMEM structure.
2451 ********************************************************************/
2452 void make_samr_q_add_aliasmem(SAMR_Q_ADD_ALIASMEM *q_u, POLICY_HND *hnd,
2453                                 DOM_SID *sid)
2454 {
2455         if (q_u == NULL) return;
2456
2457         DEBUG(5,("make_samr_q_add_aliasmem\n"));
2458
2459         memcpy(&(q_u->alias_pol), hnd, sizeof(q_u->alias_pol));
2460         sid_copy(&q_u->sid, sid);
2461 }
2462
2463
2464 /*******************************************************************
2465 reads or writes a structure.
2466 ********************************************************************/
2467 void samr_io_q_add_aliasmem(char *desc,  SAMR_Q_ADD_ALIASMEM *q_u, prs_struct *ps, int depth)
2468 {
2469         if (q_u == NULL) return;
2470
2471         prs_debug(ps, depth, desc, "samr_io_q_add_aliasmem");
2472         depth++;
2473
2474         prs_align(ps);
2475
2476         smb_io_pol_hnd("alias_pol", &(q_u->alias_pol), ps, depth); 
2477         smb_io_dom_sid("sid      ", &(q_u->sid      ), ps, depth); 
2478 }
2479
2480 /*******************************************************************
2481 reads or writes a structure.
2482 ********************************************************************/
2483 void samr_io_r_add_aliasmem(char *desc,  SAMR_R_ADD_ALIASMEM *r_u, prs_struct *ps, int depth)
2484 {
2485         if (r_u == NULL) return;
2486
2487         prs_debug(ps, depth, desc, "samr_io_r_add_aliasmem");
2488         depth++;
2489
2490         prs_align(ps);
2491
2492         prs_uint32("status", ps, depth, &(r_u->status));
2493 }
2494
2495 /*******************************************************************
2496 makes a SAMR_Q_QUERY_ALIASMEM structure.
2497 ********************************************************************/
2498 void make_samr_q_query_aliasmem(SAMR_Q_QUERY_ALIASMEM *q_c, POLICY_HND *hnd)
2499 {
2500         if (q_c == NULL || hnd == NULL) return;
2501
2502         DEBUG(5,("make_samr_q_query_aliasmem\n"));
2503
2504         memcpy(&(q_c->alias_pol), hnd, sizeof(q_c->alias_pol));
2505 }
2506
2507 /*******************************************************************
2508 reads or writes a structure.
2509 ********************************************************************/
2510 void samr_io_q_query_aliasmem(char *desc,  SAMR_Q_QUERY_ALIASMEM *q_u, prs_struct *ps, int depth)
2511 {
2512         if (q_u == NULL) return;
2513
2514         prs_debug(ps, depth, desc, "samr_io_q_query_aliasmem");
2515         depth++;
2516
2517         prs_align(ps);
2518
2519         smb_io_pol_hnd("alias_pol", &(q_u->alias_pol), ps, depth); 
2520 }
2521
2522 /*******************************************************************
2523 makes a SAMR_R_QUERY_ALIASMEM structure.
2524 ********************************************************************/
2525 void make_samr_r_query_aliasmem(SAMR_R_QUERY_ALIASMEM *r_u,
2526                 uint32 num_sids, DOM_SID *sid, uint32 status)
2527 {
2528         if (r_u == NULL) return;
2529
2530         DEBUG(5,("make_samr_r_query_aliasmem\n"));
2531
2532         if (status == 0x0)
2533         {
2534                 r_u->num_sids = num_sids;
2535                 r_u->ptr      = (num_sids != 0) ? 1 : 0;
2536                 r_u->num_sids = num_sids;
2537
2538                 r_u->sid = sid;
2539         }
2540         else
2541         {
2542                 r_u->ptr      = 0;
2543                 r_u->num_sids = 0;
2544         }
2545
2546         r_u->status = status;
2547 }
2548
2549 /*******************************************************************
2550 reads or writes a structure.
2551 ********************************************************************/
2552 void samr_io_r_query_aliasmem(char *desc,  SAMR_R_QUERY_ALIASMEM *r_u, prs_struct *ps, int depth)
2553 {
2554         int i;
2555         uint32 ptr_sid[MAX_LOOKUP_SIDS];
2556
2557         if (r_u == NULL) return;
2558
2559         prs_debug(ps, depth, desc, "samr_io_r_query_aliasmem");
2560         depth++;
2561
2562         prs_align(ps);
2563
2564         prs_uint32("ptr", ps, depth, &(r_u->ptr));
2565
2566         if (r_u->ptr != 0)
2567         {
2568                 prs_uint32("num_sids ", ps, depth, &(r_u->num_sids));
2569
2570                 SMB_ASSERT_ARRAY(ptr_sid, r_u->num_sids);
2571
2572                 if (r_u->num_sids != 0)
2573                 {
2574                         prs_uint32("num_sids1", ps, depth, &(r_u->num_sids1));
2575
2576                         for (i = 0; i < r_u->num_sids1; i++)
2577                         {
2578                                 prs_grow(ps);
2579                                 ptr_sid[i] = 1;
2580                                 prs_uint32("", ps, depth, &(ptr_sid[i]));
2581                         }
2582                         for (i = 0; i < r_u->num_sids1; i++)
2583                         {
2584                                 prs_grow(ps);
2585                                 if (ptr_sid[i] != 0)
2586                                 {
2587                                         smb_io_dom_sid("", &(r_u->sid[i]), ps, depth);
2588                                 }
2589                         }
2590                 }
2591         }
2592         prs_uint32("status", ps, depth, &(r_u->status));
2593 }
2594
2595
2596 /*******************************************************************
2597 reads or writes a structure.
2598 ********************************************************************/
2599 void samr_io_q_lookup_names(char *desc,  SAMR_Q_LOOKUP_NAMES *q_u, prs_struct *ps, int depth)
2600 {
2601         int i;
2602
2603         if (q_u == NULL) return;
2604
2605         prs_debug(ps, depth, desc, "samr_io_q_lookup_names");
2606         depth++;
2607
2608         prs_align(ps);
2609
2610         smb_io_pol_hnd("pol", &(q_u->pol), ps, depth); 
2611         prs_align(ps);
2612
2613         prs_uint32("num_rids1", ps, depth, &(q_u->num_rids1));
2614         prs_uint32("rid      ", ps, depth, &(q_u->rid      ));
2615         prs_uint32("ptr      ", ps, depth, &(q_u->ptr      ));
2616         prs_uint32("num_rids2", ps, depth, &(q_u->num_rids2));
2617
2618         SMB_ASSERT_ARRAY(q_u->hdr_user_name, q_u->num_rids2);
2619
2620         for (i = 0; i < q_u->num_rids2; i++)
2621         {
2622                 prs_grow(ps);
2623                 smb_io_unihdr ("", &(q_u->hdr_user_name[i]), ps, depth); 
2624         }
2625         for (i = 0; i < q_u->num_rids2; i++)
2626         {
2627                 prs_grow(ps);
2628                 smb_io_unistr2("", &(q_u->uni_user_name[i]), q_u->hdr_user_name[i].buffer, ps, depth); 
2629         }
2630
2631         prs_align(ps);
2632 }
2633
2634
2635 /*******************************************************************
2636 makes a SAMR_R_LOOKUP_NAMES structure.
2637 ********************************************************************/
2638 void make_samr_r_lookup_names(SAMR_R_LOOKUP_NAMES *r_u,
2639                 uint32 num_rids, uint32 *rid, uint8 *type, uint32 status)
2640 {
2641         int i;
2642         if (r_u == NULL) return;
2643
2644         DEBUG(5,("make_samr_r_lookup_names\n"));
2645
2646         if (status == 0x0)
2647         {
2648                 r_u->num_entries  = num_rids;
2649                 r_u->undoc_buffer = 1;
2650                 r_u->num_entries2 = num_rids;
2651
2652                 SMB_ASSERT_ARRAY(r_u->dom_rid, num_rids);
2653
2654                 for (i = 0; i < num_rids; i++)
2655                 {
2656                         make_dom_rid3(&(r_u->dom_rid[i]), rid[i], type[i]);
2657                 }
2658
2659                 r_u->num_entries3 = num_rids;
2660         }
2661         else
2662         {
2663                 r_u->num_entries  = 0;
2664                 r_u->undoc_buffer = 0;
2665                 r_u->num_entries2 = 0;
2666                 r_u->num_entries3 = 0;
2667         }
2668
2669         r_u->status = status;
2670 }
2671
2672 /*******************************************************************
2673 reads or writes a structure.
2674 ********************************************************************/
2675 void samr_io_r_lookup_names(char *desc,  SAMR_R_LOOKUP_NAMES *r_u, prs_struct *ps, int depth)
2676 {
2677         int i;
2678         if (r_u == NULL) return;
2679
2680         prs_debug(ps, depth, desc, "samr_io_r_lookup_names");
2681         depth++;
2682
2683         prs_align(ps);
2684
2685         prs_uint32("num_entries ", ps, depth, &(r_u->num_entries ));
2686         prs_uint32("undoc_buffer", ps, depth, &(r_u->undoc_buffer));
2687         prs_uint32("num_entries2", ps, depth, &(r_u->num_entries2));
2688
2689         if (r_u->num_entries != 0)
2690         {
2691                 SMB_ASSERT_ARRAY(r_u->dom_rid, r_u->num_entries2);
2692
2693                 for (i = 0; i < r_u->num_entries2; i++)
2694                 {
2695                         prs_grow(ps);
2696                         smb_io_dom_rid3("", &(r_u->dom_rid[i]), ps, depth);
2697         }
2698
2699         }
2700
2701         prs_uint32("num_entries3", ps, depth, &(r_u->num_entries3));
2702
2703         prs_uint32("status", ps, depth, &(r_u->status));
2704 }
2705
2706
2707 /*******************************************************************
2708 reads or writes a structure.
2709 ********************************************************************/
2710 void make_samr_q_open_user(SAMR_Q_OPEN_USER *q_u,
2711                                 POLICY_HND *pol,
2712                                 uint32 unk_0, uint32 rid)
2713 {
2714         if (q_u == NULL) return;
2715
2716         DEBUG(5,("samr_make_samr_q_open_user\n"));
2717
2718         memcpy(&q_u->domain_pol, pol, sizeof(q_u->domain_pol));
2719         
2720         q_u->unknown_0 = unk_0;
2721         q_u->user_rid  = rid;
2722 }
2723
2724 /*******************************************************************
2725 reads or writes a structure.
2726 ********************************************************************/
2727 void samr_io_q_open_user(char *desc,  SAMR_Q_OPEN_USER *q_u, prs_struct *ps, int depth)
2728 {
2729         if (q_u == NULL) return;
2730
2731         prs_debug(ps, depth, desc, "samr_io_q_open_user");
2732         depth++;
2733
2734         prs_align(ps);
2735
2736         smb_io_pol_hnd("domain_pol", &(q_u->domain_pol), ps, depth); 
2737         prs_align(ps);
2738
2739         prs_uint32("unknown_0", ps, depth, &(q_u->unknown_0));
2740         prs_uint32("user_rid ", ps, depth, &(q_u->user_rid ));
2741
2742         prs_align(ps);
2743 }
2744
2745 /*******************************************************************
2746 reads or writes a structure.
2747 ********************************************************************/
2748 void samr_io_r_open_user(char *desc,  SAMR_R_OPEN_USER *r_u, prs_struct *ps, int depth)
2749 {
2750         if (r_u == NULL) return;
2751
2752         prs_debug(ps, depth, desc, "samr_io_r_open_user");
2753         depth++;
2754
2755         prs_align(ps);
2756
2757         smb_io_pol_hnd("user_pol", &(r_u->user_pol), ps, depth); 
2758         prs_align(ps);
2759
2760         prs_uint32("status", ps, depth, &(r_u->status));
2761 }
2762
2763 /*******************************************************************
2764 makes a SAMR_Q_QUERY_USERINFO structure.
2765 ********************************************************************/
2766 void make_samr_q_query_userinfo(SAMR_Q_QUERY_USERINFO *q_u,
2767                                 POLICY_HND *hnd, uint16 switch_value)
2768 {
2769         if (q_u == NULL || hnd == NULL) return;
2770
2771         DEBUG(5,("make_samr_q_query_userinfo\n"));
2772
2773         memcpy(&(q_u->pol), hnd, sizeof(q_u->pol));
2774         q_u->switch_value = switch_value;
2775 }
2776
2777
2778 /*******************************************************************
2779 reads or writes a structure.
2780 ********************************************************************/
2781 void samr_io_q_query_userinfo(char *desc,  SAMR_Q_QUERY_USERINFO *q_u, prs_struct *ps, int depth)
2782 {
2783         if (q_u == NULL) return;
2784
2785         prs_debug(ps, depth, desc, "samr_io_q_query_userinfo");
2786         depth++;
2787
2788         prs_align(ps);
2789
2790         smb_io_pol_hnd("pol", &(q_u->pol), ps, depth); 
2791         prs_align(ps);
2792
2793         prs_uint16("switch_value", ps, depth, &(q_u->switch_value)); /* 0x0015 or 0x0011 */
2794
2795         prs_align(ps);
2796 }
2797
2798 /*******************************************************************
2799 reads or writes a LOGON_HRS structure.
2800 ********************************************************************/
2801 static void sam_io_logon_hrs(char *desc,  LOGON_HRS *hrs, prs_struct *ps, int depth)
2802 {
2803         if (hrs == NULL) return;
2804
2805         prs_debug(ps, depth, desc, "sam_io_logon_hrs");
2806         depth++;
2807
2808         prs_align(ps);
2809         
2810         prs_uint32 (       "len  ", ps, depth, &(hrs->len ));
2811
2812         if (hrs->len > 64)
2813         {
2814                 DEBUG(5,("sam_io_logon_hrs: truncating length\n"));
2815                 hrs->len = 64;
2816         }
2817
2818         prs_uint8s (False, "hours", ps, depth, hrs->hours, hrs->len);
2819 }
2820
2821 /*******************************************************************
2822 makes a SAM_USER_INFO_10 structure.
2823 ********************************************************************/
2824 void make_sam_user_info10(SAM_USER_INFO_10 *usr,
2825                                 uint32 acb_info)
2826 {
2827         if (usr == NULL) return;
2828
2829         DEBUG(5,("make_sam_user_info10\n"));
2830
2831         usr->acb_info = acb_info;
2832 }
2833
2834 /*******************************************************************
2835 reads or writes a structure.
2836 ********************************************************************/
2837 void sam_io_user_info10(char *desc,  SAM_USER_INFO_10 *usr, prs_struct *ps, int depth)
2838 {
2839         if (usr == NULL) return;
2840
2841         prs_debug(ps, depth, desc, "samr_io_r_user_info10");
2842         depth++;
2843
2844         prs_align(ps);
2845
2846         prs_uint32("acb_info", ps, depth, &(usr->acb_info));
2847 }
2848
2849 /*******************************************************************
2850 makes a SAM_USER_INFO_11 structure.
2851 ********************************************************************/
2852 void make_sam_user_info11(SAM_USER_INFO_11 *usr,
2853                                 NTTIME *expiry,
2854                                 char *mach_acct,
2855                                 uint32 rid_user,
2856                                 uint32 rid_group,
2857                                 uint16 acct_ctrl)
2858                                 
2859 {
2860         int len_mach_acct;
2861         if (usr == NULL || expiry == NULL || mach_acct == NULL) return;
2862
2863         DEBUG(5,("make_sam_user_info11\n"));
2864
2865         len_mach_acct = strlen(mach_acct);
2866
2867         memcpy(&(usr->expiry),expiry, sizeof(usr->expiry)); /* expiry time or something? */
2868         bzero(usr->padding_1, sizeof(usr->padding_1)); /* 0 - padding 24 bytes */
2869
2870         make_uni_hdr(&(usr->hdr_mach_acct), len_mach_acct, len_mach_acct, 4);  /* unicode header for machine account */
2871         usr->padding_2 = 0;               /* 0 - padding 4 bytes */
2872
2873         usr->ptr_1        = 1;            /* pointer */
2874         bzero(usr->padding_3, sizeof(usr->padding_3)); /* 0 - padding 32 bytes */
2875         usr->padding_4    = 0;            /* 0 - padding 4 bytes */
2876
2877         usr->ptr_2        = 1;            /* pointer */
2878         usr->padding_5    = 0;            /* 0 - padding 4 bytes */
2879
2880         usr->ptr_3        = 1;          /* pointer */
2881         bzero(usr->padding_6, sizeof(usr->padding_6)); /* 0 - padding 32 bytes */
2882
2883         usr->rid_user     = rid_user; 
2884         usr->rid_group    = rid_group;
2885
2886         usr->acct_ctrl    = acct_ctrl;
2887         usr->unknown_3    = 0x0000;
2888
2889         usr->unknown_4    = 0x003f;       /* 0x003f      - 16 bit unknown */
2890         usr->unknown_5    = 0x003c;       /* 0x003c      - 16 bit unknown */
2891
2892         bzero(usr->padding_7, sizeof(usr->padding_7)); /* 0 - padding 16 bytes */
2893         usr->padding_8    = 0;            /* 0 - padding 4 bytes */
2894         
2895         make_unistr2(&(usr->uni_mach_acct), mach_acct, len_mach_acct);  /* unicode string for machine account */
2896
2897         bzero(usr->padding_9, sizeof(usr->padding_9)); /* 0 - padding 48 bytes */
2898 }
2899
2900 /*******************************************************************
2901 reads or writes a structure.
2902 ********************************************************************/
2903 void sam_io_user_info11(char *desc,  SAM_USER_INFO_11 *usr, prs_struct *ps, int depth)
2904 {
2905         if (usr == NULL) return;
2906
2907         prs_debug(ps, depth, desc, "samr_io_r_unknown_24");
2908         depth++;
2909
2910         prs_align(ps);
2911
2912         prs_uint8s (False, "padding_0", ps, depth, usr->padding_0, sizeof(usr->padding_0)); 
2913
2914         smb_io_time("time", &(usr->expiry), ps, depth); 
2915
2916         prs_uint8s (False, "padding_1", ps, depth, usr->padding_1, sizeof(usr->padding_1));
2917
2918         smb_io_unihdr ("unihdr", &(usr->hdr_mach_acct), ps, depth); 
2919         prs_uint32(        "padding_2", ps, depth, &(usr->padding_2));
2920
2921         prs_uint32(        "ptr_1    ", ps, depth, &(usr->ptr_1    ));
2922         prs_uint8s (False, "padding_3", ps, depth, usr->padding_3, sizeof(usr->padding_3));
2923         prs_uint32(        "padding_4", ps, depth, &(usr->padding_4));
2924
2925         prs_uint32(        "ptr_2    ", ps, depth, &(usr->ptr_2    ));
2926         prs_uint32(        "padding_5", ps, depth, &(usr->padding_5));
2927
2928         prs_uint32(        "ptr_3    ", ps, depth, &(usr->ptr_3    ));
2929         prs_uint8s (False, "padding_6", ps, depth, usr->padding_6, sizeof(usr->padding_6));
2930
2931         prs_uint32(        "rid_user ", ps, depth, &(usr->rid_user ));
2932         prs_uint32(        "rid_group", ps, depth, &(usr->rid_group));
2933         prs_uint16(        "acct_ctrl", ps, depth, &(usr->acct_ctrl));
2934         prs_uint16(        "unknown_3", ps, depth, &(usr->unknown_3));
2935         prs_uint16(        "unknown_4", ps, depth, &(usr->unknown_4));
2936         prs_uint16(        "unknown_5", ps, depth, &(usr->unknown_5));
2937
2938         prs_uint8s (False, "padding_7", ps, depth, usr->padding_7, sizeof(usr->padding_7));
2939         prs_uint32(        "padding_8", ps, depth, &(usr->padding_8));
2940         
2941         smb_io_unistr2("unistr2", &(usr->uni_mach_acct), True, ps, depth); 
2942         prs_align(ps);
2943
2944         prs_uint8s (False, "padding_9", ps, depth, usr->padding_9, sizeof(usr->padding_9));
2945 }
2946 /*************************************************************************
2947  make_sam_user_info21
2948
2949  unknown_3 = 0x00ff ffff
2950  unknown_5 = 0x0002 0000
2951  unknown_6 = 0x0000 04ec 
2952
2953  *************************************************************************/
2954 void make_sam_user_info21(SAM_USER_INFO_21 *usr,
2955
2956         NTTIME *logon_time,
2957         NTTIME *logoff_time,
2958         NTTIME *kickoff_time,
2959         NTTIME *pass_last_set_time,
2960         NTTIME *pass_can_change_time,
2961         NTTIME *pass_must_change_time,
2962
2963         char *user_name,
2964         char *full_name,
2965         char *home_dir,
2966         char *dir_drive,
2967         char *logon_script,
2968         char *profile_path,
2969         char *description,
2970         char *workstations,
2971         char *unknown_str,
2972         char *munged_dial,
2973
2974         uint32 user_rid,
2975         uint32 group_rid,
2976         uint16 acb_info, 
2977
2978         uint32 unknown_3,
2979         uint16 logon_divs,
2980         LOGON_HRS *hrs,
2981         uint32 unknown_5,
2982         uint32 unknown_6)
2983 {
2984         int len_user_name    = user_name    != NULL ? strlen(user_name   ) : 0;
2985         int len_full_name    = full_name    != NULL ? strlen(full_name   ) : 0;
2986         int len_home_dir     = home_dir     != NULL ? strlen(home_dir    ) : 0;
2987         int len_dir_drive    = dir_drive    != NULL ? strlen(dir_drive   ) : 0;
2988         int len_logon_script = logon_script != NULL ? strlen(logon_script) : 0;
2989         int len_profile_path = profile_path != NULL ? strlen(profile_path) : 0;
2990         int len_description  = description  != NULL ? strlen(description ) : 0;
2991         int len_workstations = workstations != NULL ? strlen(workstations) : 0;
2992         int len_unknown_str  = unknown_str  != NULL ? strlen(unknown_str ) : 0;
2993         int len_munged_dial  = munged_dial  != NULL ? strlen(munged_dial ) : 0;
2994
2995         usr->logon_time            = *logon_time;
2996         usr->logoff_time           = *logoff_time;
2997         usr->kickoff_time          = *kickoff_time;
2998         usr->pass_last_set_time    = *pass_last_set_time;
2999         usr->pass_can_change_time  = *pass_can_change_time;
3000         usr->pass_must_change_time = *pass_must_change_time;
3001
3002         make_uni_hdr(&(usr->hdr_user_name   ), len_user_name   , len_user_name   , 1);
3003         make_uni_hdr(&(usr->hdr_full_name   ), len_full_name   , len_full_name   , 1);
3004         make_uni_hdr(&(usr->hdr_home_dir    ), len_home_dir    , len_home_dir    , 1);
3005         make_uni_hdr(&(usr->hdr_dir_drive   ), len_dir_drive   , len_dir_drive   , 1);
3006         make_uni_hdr(&(usr->hdr_logon_script), len_logon_script, len_logon_script, 1);
3007         make_uni_hdr(&(usr->hdr_profile_path), len_profile_path, len_profile_path, 1);
3008         make_uni_hdr(&(usr->hdr_acct_desc   ), len_description , len_description , 1);
3009         make_uni_hdr(&(usr->hdr_workstations), len_workstations, len_workstations, 1);
3010         make_uni_hdr(&(usr->hdr_unknown_str ), len_unknown_str , len_unknown_str , 1);
3011         make_uni_hdr(&(usr->hdr_munged_dial ), len_munged_dial , len_munged_dial , 1);
3012
3013         bzero(usr->nt_pwd, sizeof(usr->nt_pwd));
3014         bzero(usr->lm_pwd, sizeof(usr->lm_pwd));
3015
3016         usr->user_rid  = user_rid;
3017         usr->group_rid = group_rid;
3018         usr->acb_info = acb_info;
3019         usr->unknown_3 = unknown_3; /* 0x00ff ffff */
3020
3021         usr->logon_divs = logon_divs; /* should be 168 (hours/week) */
3022         usr->ptr_logon_hrs = hrs ? 1 : 0;
3023         usr->unknown_5 = unknown_5; /* 0x0002 0000 */
3024
3025         bzero(usr->padding1, sizeof(usr->padding1));
3026
3027         make_unistr2(&(usr->uni_user_name   ), user_name   , len_user_name   );
3028         make_unistr2(&(usr->uni_full_name   ), full_name   , len_full_name   );
3029         make_unistr2(&(usr->uni_home_dir    ), home_dir    , len_home_dir    );
3030         make_unistr2(&(usr->uni_dir_drive   ), dir_drive   , len_dir_drive   );
3031         make_unistr2(&(usr->uni_logon_script), logon_script, len_logon_script);
3032         make_unistr2(&(usr->uni_profile_path), profile_path, len_profile_path);
3033         make_unistr2(&(usr->uni_acct_desc ), description , len_description );
3034         make_unistr2(&(usr->uni_workstations), workstations, len_workstations);
3035         make_unistr2(&(usr->uni_unknown_str ), unknown_str , len_unknown_str );
3036         make_unistr2(&(usr->uni_munged_dial ), munged_dial , len_munged_dial );
3037
3038         usr->unknown_6 = unknown_6; /* 0x0000 04ec */
3039         usr->padding4 = 0;
3040
3041         if (hrs)
3042         {
3043                 memcpy(&(usr->logon_hrs), hrs, sizeof(usr->logon_hrs));
3044         }
3045         else
3046         {
3047                 memset(&(usr->logon_hrs), 0xff, sizeof(usr->logon_hrs));
3048         }
3049 }
3050
3051
3052 /*******************************************************************
3053 reads or writes a structure.
3054 ********************************************************************/
3055 static void sam_io_user_info21(char *desc,  SAM_USER_INFO_21 *usr, prs_struct *ps, int depth)
3056 {
3057         if (usr == NULL) return;
3058
3059         prs_debug(ps, depth, desc, "lsa_io_user_info");
3060         depth++;
3061
3062         prs_align(ps);
3063         
3064         smb_io_time("logon_time           ", &(usr->logon_time)           , ps, depth);
3065         smb_io_time("logoff_time          ", &(usr->logoff_time)          , ps, depth); 
3066         smb_io_time("kickoff_time         ", &(usr->kickoff_time)         , ps, depth); 
3067         smb_io_time("pass_last_set_time   ", &(usr->pass_last_set_time)   , ps, depth); 
3068         smb_io_time("pass_can_change_time ", &(usr->pass_can_change_time) , ps, depth); 
3069         smb_io_time("pass_must_change_time", &(usr->pass_must_change_time), ps, depth); 
3070
3071         smb_io_unihdr("hdr_user_name   ", &(usr->hdr_user_name)   , ps, depth); /* username unicode string header */
3072         smb_io_unihdr("hdr_full_name   ", &(usr->hdr_full_name)   , ps, depth); /* user's full name unicode string header */
3073         smb_io_unihdr("hdr_home_dir    ", &(usr->hdr_home_dir)    , ps, depth); /* home directory unicode string header */
3074         smb_io_unihdr("hdr_dir_drive   ", &(usr->hdr_dir_drive)   , ps, depth); /* home directory drive */
3075         smb_io_unihdr("hdr_logon_script", &(usr->hdr_logon_script), ps, depth); /* logon script unicode string header */
3076         smb_io_unihdr("hdr_profile_path", &(usr->hdr_profile_path), ps, depth); /* profile path unicode string header */
3077         smb_io_unihdr("hdr_acct_desc   ", &(usr->hdr_acct_desc  ) , ps, depth); /* account description */
3078         smb_io_unihdr("hdr_workstations", &(usr->hdr_workstations), ps, depth); /* workstations user can log on from */
3079         smb_io_unihdr("hdr_unknown_str ", &(usr->hdr_unknown_str ), ps, depth); /* unknown string */
3080         smb_io_unihdr("hdr_munged_dial ", &(usr->hdr_munged_dial ), ps, depth); /* workstations user can log on from */
3081
3082         prs_uint8s (False, "lm_pwd        ", ps, depth, usr->lm_pwd   , sizeof(usr->lm_pwd   ));
3083         prs_uint8s (False, "nt_pwd        ", ps, depth, usr->nt_pwd   , sizeof(usr->nt_pwd   ));
3084
3085         prs_uint32("user_rid      ", ps, depth, &(usr->user_rid     ));       /* User ID */
3086         prs_uint32("group_rid     ", ps, depth, &(usr->group_rid    ));      /* Group ID */
3087         prs_uint16("acb_info      ", ps, depth, &(usr->acb_info     ));      /* Group ID */
3088         prs_align(ps);
3089
3090         prs_uint32("unknown_3     ", ps, depth, &(usr->unknown_3    ));
3091         prs_uint16("logon_divs    ", ps, depth, &(usr->logon_divs   ));     /* logon divisions per week */
3092         prs_align(ps);
3093         prs_uint32("ptr_logon_hrs ", ps, depth, &(usr->ptr_logon_hrs));
3094         prs_uint32("unknown_5     ", ps, depth, &(usr->unknown_5    ));
3095
3096         prs_uint8s (False, "padding1      ", ps, depth, usr->padding1, sizeof(usr->padding1));
3097
3098         /* here begins pointed-to data */
3099
3100         smb_io_unistr2("uni_user_name   ", &(usr->uni_user_name)   , usr->hdr_user_name   .buffer, ps, depth); /* username unicode string */
3101         smb_io_unistr2("uni_full_name   ", &(usr->uni_full_name)   , usr->hdr_full_name   .buffer, ps, depth); /* user's full name unicode string */
3102         smb_io_unistr2("uni_home_dir    ", &(usr->uni_home_dir)    , usr->hdr_home_dir    .buffer, ps, depth); /* home directory unicode string */
3103         smb_io_unistr2("uni_dir_drive   ", &(usr->uni_dir_drive)   , usr->hdr_dir_drive   .buffer, ps, depth); /* home directory drive unicode string */
3104         smb_io_unistr2("uni_logon_script", &(usr->uni_logon_script), usr->hdr_logon_script.buffer, ps, depth); /* logon script unicode string */
3105         smb_io_unistr2("uni_profile_path", &(usr->uni_profile_path), usr->hdr_profile_path.buffer, ps, depth); /* profile path unicode string */
3106         smb_io_unistr2("uni_acct_desc   ", &(usr->uni_acct_desc   ), usr->hdr_acct_desc   .buffer, ps, depth); /* user description unicode string */
3107         smb_io_unistr2("uni_workstations", &(usr->uni_workstations), usr->hdr_workstations.buffer, ps, depth); /* worksations user can log on from */
3108         smb_io_unistr2("uni_unknown_str ", &(usr->uni_unknown_str ), usr->hdr_unknown_str .buffer, ps, depth); /* unknown string */
3109         smb_io_unistr2("uni_munged_dial ", &(usr->uni_munged_dial ), usr->hdr_munged_dial .buffer, ps, depth); /* worksations user can log on from */
3110
3111         prs_uint32("unknown_6     ", ps, depth, &(usr->unknown_6  ));
3112         prs_uint32("padding4      ", ps, depth, &(usr->padding4   ));
3113
3114         if (usr->ptr_logon_hrs)
3115         {
3116                 sam_io_logon_hrs("logon_hrs", &(usr->logon_hrs)   , ps, depth);
3117                 prs_align(ps);
3118         }
3119 }
3120
3121
3122 /*******************************************************************
3123 makes a SAMR_R_QUERY_USERINFO structure.
3124 ********************************************************************/
3125 void make_samr_r_query_userinfo(SAMR_R_QUERY_USERINFO *r_u,
3126                                 uint16 switch_value, void *info, uint32 status)
3127                                 
3128 {
3129         if (r_u == NULL || info == NULL) return;
3130
3131         DEBUG(5,("make_samr_r_query_userinfo\n"));
3132
3133         r_u->ptr = 0;
3134         r_u->switch_value = 0;
3135
3136         if (status == 0)
3137         {
3138                 r_u->switch_value = switch_value;
3139
3140                 switch (switch_value)
3141                 {
3142                         case 0x10:
3143                         {
3144                                 r_u->ptr = 1;
3145                                 r_u->info.id10 = (SAM_USER_INFO_10*)info;
3146
3147                                 break;
3148                         }
3149
3150                         case 0x11:
3151                         {
3152                                 r_u->ptr = 1;
3153                                 r_u->info.id11 = (SAM_USER_INFO_11*)info;
3154
3155                                 break;
3156                         }
3157
3158                         case 21:
3159                         {
3160                                 r_u->ptr = 1;
3161                                 r_u->info.id21 = (SAM_USER_INFO_21*)info;
3162
3163                                 break;
3164                         }
3165
3166                         default:
3167                         {
3168                                 DEBUG(4,("make_samr_r_query_userinfo: unsupported switch level\n"));
3169                                 break;
3170                         }
3171                 }
3172         }
3173
3174         r_u->status = status;         /* return status */
3175 }
3176
3177 /*******************************************************************
3178 reads or writes a structure.
3179 ********************************************************************/
3180 void samr_io_r_query_userinfo(char *desc,  SAMR_R_QUERY_USERINFO *r_u, prs_struct *ps, int depth)
3181 {
3182         if (r_u == NULL) return;
3183
3184         prs_debug(ps, depth, desc, "samr_io_r_query_userinfo");
3185         depth++;
3186
3187         prs_align(ps);
3188
3189         prs_uint32("ptr         ", ps, depth, &(r_u->ptr         ));
3190         prs_uint16("switch_value", ps, depth, &(r_u->switch_value));
3191         prs_align(ps);
3192
3193         if (r_u->ptr != 0 && r_u->switch_value != 0)
3194         {
3195                 switch (r_u->switch_value)
3196                 {
3197                         case 0x10:
3198                         {
3199                                 if (r_u->info.id10 != NULL)
3200                                 {
3201                                         sam_io_user_info10("", r_u->info.id10, ps, depth);
3202                                 }
3203                                 else
3204                                 {
3205                                         DEBUG(2,("samr_io_r_query_userinfo: info pointer not initialised\n"));
3206                                         return;
3207                                 }
3208                                 break;
3209                         }
3210 /*
3211                         case 0x11:
3212                         {
3213                                 if (r_u->info.id11 != NULL)
3214                                 {
3215                                         sam_io_user_info11("", r_u->info.id11, ps, depth);
3216                                 }
3217                                 else
3218                                 {
3219                                         DEBUG(2,("samr_io_r_query_userinfo: info pointer not initialised\n"));
3220                                         return;
3221                                 }
3222                                 break;
3223                         }
3224 */
3225                         case 21:
3226                         {
3227                                 if (r_u->info.id21 != NULL)
3228                                 {
3229                                         sam_io_user_info21("", r_u->info.id21, ps, depth);
3230                                 }
3231                                 else
3232                                 {
3233                                         DEBUG(2,("samr_io_r_query_userinfo: info pointer not initialised\n"));
3234                                         return;
3235                                 }
3236                                 break;
3237                         }
3238                         default:
3239                         {
3240                                 DEBUG(2,("samr_io_r_query_userinfo: unknown switch level\n"));
3241                                 break;
3242                         }
3243                                 
3244                 }
3245         }
3246
3247         prs_uint32("status", ps, depth, &(r_u->status));
3248 }
3249
3250 /*******************************************************************
3251 reads or writes a structure.
3252 ********************************************************************/
3253 void samr_io_q_unknown_32(char *desc,  SAMR_Q_UNKNOWN_32 *q_u, prs_struct *ps, int depth)
3254 {
3255         if (q_u == NULL) return;
3256
3257         prs_debug(ps, depth, desc, "samr_io_q_unknown_32");
3258         depth++;
3259
3260         prs_align(ps);
3261
3262         smb_io_pol_hnd("pol", &(q_u->pol), ps, depth); 
3263         prs_align(ps);
3264
3265         smb_io_unihdr ("", &(q_u->hdr_mach_acct), ps, depth); 
3266         smb_io_unistr2("", &(q_u->uni_mach_acct), q_u->hdr_mach_acct.buffer, ps, depth); 
3267
3268         prs_align(ps);
3269
3270         prs_uint32("acct_ctrl", ps, depth, &(q_u->acct_ctrl));
3271         prs_uint16("unknown_1", ps, depth, &(q_u->unknown_1));
3272         prs_uint16("unknown_2", ps, depth, &(q_u->unknown_2));
3273 }
3274
3275 /*******************************************************************
3276 reads or writes a structure.
3277 ********************************************************************/
3278 void samr_io_r_unknown_32(char *desc,  SAMR_R_UNKNOWN_32 *r_u, prs_struct *ps, int depth)
3279 {
3280         if (r_u == NULL) return;
3281
3282         prs_debug(ps, depth, desc, "samr_io_r_unknown_32");
3283         depth++;
3284
3285         prs_align(ps);
3286
3287         smb_io_pol_hnd("pol", &(r_u->pol), ps, depth); 
3288         prs_align(ps);
3289
3290         prs_uint32("status", ps, depth, &(r_u->status));
3291 }
3292
3293
3294 /*******************************************************************
3295 makes a SAMR_Q_CONNECT structure.
3296 ********************************************************************/
3297 void make_samr_q_connect(SAMR_Q_CONNECT *q_u,
3298                                 char *srv_name, uint32 unknown_0)
3299 {
3300         int len_srv_name = strlen(srv_name);
3301
3302         if (q_u == NULL) return;
3303
3304         DEBUG(5,("make_samr_q_connect\n"));
3305
3306         /* make PDC server name \\server */
3307         q_u->ptr_srv_name = len_srv_name > 0 ? 1 : 0; 
3308         make_unistr2(&(q_u->uni_srv_name), srv_name, len_srv_name+1);  
3309
3310         /* example values: 0x0000 0002 */
3311         q_u->unknown_0 = unknown_0; 
3312 }
3313
3314
3315 /*******************************************************************
3316 reads or writes a structure.
3317 ********************************************************************/
3318 void samr_io_q_connect(char *desc,  SAMR_Q_CONNECT *q_u, prs_struct *ps, int depth)
3319 {
3320         if (q_u == NULL) return;
3321
3322         prs_debug(ps, depth, desc, "samr_io_q_connect");
3323         depth++;
3324
3325         prs_align(ps);
3326
3327         prs_uint32("ptr_srv_name", ps, depth, &(q_u->ptr_srv_name));
3328         smb_io_unistr2("", &(q_u->uni_srv_name), q_u->ptr_srv_name, ps, depth); 
3329
3330         prs_align(ps);
3331
3332         prs_uint32("unknown_0   ", ps, depth, &(q_u->unknown_0   ));
3333 }
3334
3335 /*******************************************************************
3336 reads or writes a structure.
3337 ********************************************************************/
3338 void samr_io_r_connect(char *desc,  SAMR_R_CONNECT *r_u, prs_struct *ps, int depth)
3339 {
3340         if (r_u == NULL) return;
3341
3342         prs_debug(ps, depth, desc, "samr_io_r_connect");
3343         depth++;
3344
3345         prs_align(ps);
3346
3347         smb_io_pol_hnd("connect_pol", &(r_u->connect_pol), ps, depth); 
3348         prs_align(ps);
3349
3350         prs_uint32("status", ps, depth, &(r_u->status));
3351 }
3352
3353 /*******************************************************************
3354 makes a SAMR_Q_CONNECT_ANON structure.
3355 ********************************************************************/
3356 void make_samr_q_connect_anon(SAMR_Q_CONNECT_ANON *q_u)
3357 {
3358         if (q_u == NULL) return;
3359
3360         DEBUG(5,("make_samr_q_connect_anon\n"));
3361
3362         q_u->ptr       = 1;
3363         q_u->unknown_0 = 0x5c; /* server name (?!!) */
3364         q_u->unknown_1 = 0x01;
3365         q_u->unknown_2 = 0x20;
3366 }
3367
3368
3369 /*******************************************************************
3370 reads or writes a structure.
3371 ********************************************************************/
3372 void samr_io_q_connect_anon(char *desc,  SAMR_Q_CONNECT_ANON *q_u, prs_struct *ps, int depth)
3373 {
3374         if (q_u == NULL) return;
3375
3376         prs_debug(ps, depth, desc, "samr_io_q_connect_anon");
3377         depth++;
3378
3379         prs_align(ps);
3380
3381         prs_uint32("ptr      ", ps, depth, &(q_u->ptr      ));
3382         prs_uint16("unknown_0", ps, depth, &(q_u->unknown_0));
3383         prs_uint16("unknown_1", ps, depth, &(q_u->unknown_1));
3384         prs_uint32("unknown_2", ps, depth, &(q_u->unknown_2));
3385 }
3386
3387 /*******************************************************************
3388 reads or writes a structure.
3389 ********************************************************************/
3390 void samr_io_r_connect_anon(char *desc,  SAMR_R_CONNECT_ANON *r_u, prs_struct *ps, int depth)
3391 {
3392         if (r_u == NULL) return;
3393
3394         prs_debug(ps, depth, desc, "samr_io_r_connect_anon");
3395         depth++;
3396
3397         prs_align(ps);
3398
3399         smb_io_pol_hnd("connect_pol", &(r_u->connect_pol), ps, depth); 
3400         prs_align(ps);
3401
3402         prs_uint32("status", ps, depth, &(r_u->status));
3403 }
3404
3405 /*******************************************************************
3406 makes a SAMR_Q_UNKNOWN_38 structure.
3407 ********************************************************************/
3408 void make_samr_q_unknown_38(SAMR_Q_UNKNOWN_38 *q_u, char *srv_name)
3409 {
3410         int len_srv_name = strlen(srv_name);
3411
3412         if (q_u == NULL) return;
3413
3414         DEBUG(5,("make_samr_q_unknown_38\n"));
3415
3416         q_u->ptr = 1;
3417         make_uni_hdr(&(q_u->hdr_srv_name), len_srv_name, len_srv_name, len_srv_name != 0);
3418         make_unistr2(&(q_u->uni_srv_name), srv_name, len_srv_name);  
3419
3420 }
3421
3422 /*******************************************************************
3423 reads or writes a structure.
3424 ********************************************************************/
3425 void samr_io_q_unknown_38(char *desc,  SAMR_Q_UNKNOWN_38 *q_u, prs_struct *ps, int depth)
3426 {
3427         if (q_u == NULL) return;
3428
3429         prs_debug(ps, depth, desc, "samr_io_q_unknown_38");
3430         depth++;
3431
3432         prs_align(ps);
3433
3434         prs_uint32("ptr", ps, depth, &(q_u->ptr));
3435         if (q_u->ptr != 0)
3436         {
3437                 smb_io_unihdr ("", &(q_u->hdr_srv_name), ps, depth); 
3438                 smb_io_unistr2("", &(q_u->uni_srv_name), q_u->hdr_srv_name.buffer, ps, depth); 
3439         }
3440 }
3441
3442 /*******************************************************************
3443 makes a SAMR_R_UNKNOWN_38 structure.
3444 ********************************************************************/
3445 void make_samr_r_unknown_38(SAMR_R_UNKNOWN_38 *r_u)
3446 {
3447         if (r_u == NULL) return;
3448
3449         DEBUG(5,("make_r_unknown_38\n"));
3450
3451         r_u->unk_0 = 0;
3452         r_u->unk_1 = 0;
3453         r_u->unk_2 = 0;
3454         r_u->unk_3 = 0;
3455 }
3456
3457 /*******************************************************************
3458 reads or writes a structure.
3459 ********************************************************************/
3460 void samr_io_r_unknown_38(char *desc,  SAMR_R_UNKNOWN_38 *r_u, prs_struct *ps, int depth)
3461 {
3462         if (r_u == NULL) return;
3463
3464         prs_debug(ps, depth, desc, "samr_io_r_unknown_38");
3465         depth++;
3466
3467         prs_align(ps);
3468
3469         prs_uint16("unk_0", ps, depth, &(r_u->unk_0));
3470         prs_align(ps);
3471         prs_uint16("unk_1", ps, depth, &(r_u->unk_1));
3472         prs_align(ps);
3473         prs_uint16("unk_2", ps, depth, &(r_u->unk_2));
3474         prs_align(ps);
3475         prs_uint16("unk_3", ps, depth, &(r_u->unk_3));
3476         prs_align(ps);
3477 }
3478
3479 /*******************************************************************
3480 make a SAMR_ENC_PASSWD structure.
3481 ********************************************************************/
3482 void make_enc_passwd(SAMR_ENC_PASSWD *pwd, char pass[512])
3483 {
3484         if (pwd == NULL) return;
3485
3486         pwd->ptr = 1;
3487         memcpy(pwd->pass, pass, sizeof(pwd->pass)); 
3488 }
3489
3490 /*******************************************************************
3491 reads or writes a SAMR_ENC_PASSWD structure.
3492 ********************************************************************/
3493 void samr_io_enc_passwd(char *desc, SAMR_ENC_PASSWD *pwd, prs_struct *ps, int depth)
3494 {
3495         if (pwd == NULL) return;
3496
3497         prs_debug(ps, depth, desc, "samr_io_enc_passwd");
3498         depth++;
3499
3500         prs_align(ps);
3501
3502         prs_uint32("ptr", ps, depth, &(pwd->ptr));
3503         prs_uint8s(False, "pwd", ps, depth, pwd->pass, sizeof(pwd->pass)); 
3504 }
3505
3506 /*******************************************************************
3507 makes a SAMR_ENC_HASH structure.
3508 ********************************************************************/
3509 void make_enc_hash(SAMR_ENC_HASH *hsh, uchar hash[16])
3510 {
3511         if (hsh == NULL) return;
3512
3513         hsh->ptr = 1;
3514         memcpy(hsh->hash, hash, sizeof(hsh->hash));
3515 }
3516
3517 /*******************************************************************
3518 reads or writes a SAMR_ENC_HASH structure.
3519 ********************************************************************/
3520 void samr_io_enc_hash(char *desc, SAMR_ENC_HASH *hsh, prs_struct *ps, int depth)
3521 {
3522         if (hsh == NULL) return;
3523
3524         prs_debug(ps, depth, desc, "samr_io_enc_hash");
3525         depth++;
3526
3527         prs_align(ps);
3528
3529         prs_uint32("ptr ", ps, depth, &(hsh->ptr));
3530         prs_uint8s(False, "hash", ps, depth, hsh->hash, sizeof(hsh->hash)); 
3531 }
3532
3533 /*******************************************************************
3534 makes a SAMR_R_UNKNOWN_38 structure.
3535 ********************************************************************/
3536 void make_samr_q_chgpasswd_user(SAMR_Q_CHGPASSWD_USER *q_u,
3537                                 char *dest_host, char *user_name,
3538                                 char nt_newpass[516], uchar nt_oldhash[16],
3539                                 char lm_newpass[516], uchar lm_oldhash[16])
3540 {
3541         int len_dest_host = strlen(dest_host);
3542         int len_user_name = strlen(user_name);
3543
3544         if (q_u == NULL) return;
3545
3546         DEBUG(5,("make_samr_q_chgpasswd_user\n"));
3547
3548         q_u->ptr_0 = 1;
3549         make_uni_hdr(&(q_u->hdr_dest_host), len_dest_host, len_dest_host, len_dest_host != 0);
3550         make_unistr2(&(q_u->uni_dest_host), dest_host, len_dest_host);  
3551         make_uni_hdr(&(q_u->hdr_user_name), len_user_name, len_user_name, len_user_name != 0);
3552         make_unistr2(&(q_u->uni_user_name), user_name, len_user_name);  
3553
3554         make_enc_passwd(&(q_u->nt_newpass), nt_newpass);
3555         make_enc_hash  (&(q_u->nt_oldhash), nt_oldhash);
3556
3557         q_u->unknown = 0x01;
3558
3559         make_enc_passwd(&(q_u->lm_newpass), lm_newpass);
3560         make_enc_hash  (&(q_u->lm_oldhash), lm_oldhash);
3561 }
3562
3563 /*******************************************************************
3564 reads or writes a structure.
3565 ********************************************************************/
3566 void samr_io_q_chgpasswd_user(char *desc, SAMR_Q_CHGPASSWD_USER *q_u, prs_struct *ps, int depth)
3567 {
3568         if (q_u == NULL) return;
3569
3570         prs_debug(ps, depth, desc, "samr_io_q_chgpasswd_user");
3571         depth++;
3572
3573         prs_align(ps);
3574
3575         prs_uint32("ptr_0", ps, depth, &(q_u->ptr_0));
3576
3577         smb_io_unihdr ("", &(q_u->hdr_dest_host), ps, depth); 
3578         smb_io_unistr2("", &(q_u->uni_dest_host), q_u->hdr_dest_host.buffer, ps, depth); 
3579         smb_io_unihdr ("", &(q_u->hdr_user_name), ps, depth); 
3580         smb_io_unistr2("", &(q_u->uni_user_name), q_u->hdr_user_name.buffer, ps, depth); 
3581
3582         samr_io_enc_passwd("nt_newpass", &(q_u->nt_newpass), ps, depth); 
3583         prs_grow(ps);
3584         samr_io_enc_hash  ("nt_oldhash", &(q_u->nt_oldhash), ps, depth); 
3585
3586         prs_uint32("unknown", ps, depth, &(q_u->unknown));
3587
3588         samr_io_enc_passwd("lm_newpass", &(q_u->lm_newpass), ps, depth); 
3589         prs_grow(ps);
3590         samr_io_enc_hash  ("lm_oldhash", &(q_u->lm_oldhash), ps, depth); 
3591 }
3592
3593 /*******************************************************************
3594 makes a SAMR_R_CHGPASSWD_USER structure.
3595 ********************************************************************/
3596 void make_samr_r_chgpasswd_user(SAMR_R_CHGPASSWD_USER *r_u, uint32 status)
3597 {
3598         if (r_u == NULL) return;
3599
3600         DEBUG(5,("make_r_chgpasswd_user\n"));
3601
3602         r_u->status = status;
3603 }
3604
3605 /*******************************************************************
3606 reads or writes a structure.
3607 ********************************************************************/
3608 void samr_io_r_chgpasswd_user(char *desc, SAMR_R_CHGPASSWD_USER *r_u, prs_struct *ps, int depth)
3609 {
3610         if (r_u == NULL) return;
3611
3612         prs_debug(ps, depth, desc, "samr_io_r_chgpasswd_user");
3613         depth++;
3614
3615         prs_align(ps);
3616
3617         prs_uint32("status", ps, depth, &(r_u->status));
3618 }
3619
3620