r8507: BUG 2557: don't give and rpc fault when you get an unsupported SetPrinter...
[vlendec/samba-autobuild/.git] / source3 / rpc_parse / parse_spoolss.c
1 /* 
2  *  Unix SMB/CIFS implementation.
3  *  RPC Pipe client / server routines
4  *  Copyright (C) Andrew Tridgell              1992-2000,
5  *  Copyright (C) Luke Kenneth Casson Leighton 1996-2000,
6  *  Copyright (C) Jean François Micouleau      1998-2000,
7  *  Copyright (C) Gerald Carter                2000-2002,
8  *  Copyright (C) Tim Potter                   2001-2002.
9  *
10  *  This program is free software; you can redistribute it and/or modify
11  *  it under the terms of the GNU General Public License as published by
12  *  the Free Software Foundation; either version 2 of the License, or
13  *  (at your option) any later version.
14  *  
15  *  This program is distributed in the hope that it will be useful,
16  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
17  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  *  GNU General Public License for more details.
19  *  
20  *  You should have received a copy of the GNU General Public License
21  *  along with this program; if not, write to the Free Software
22  *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23  */
24
25 #include "includes.h"
26
27 #undef DBGC_CLASS
28 #define DBGC_CLASS DBGC_RPC_PARSE
29
30
31 /*******************************************************************
32 This should be moved in a more generic lib.
33 ********************************************************************/  
34
35 BOOL spoolss_io_system_time(const char *desc, prs_struct *ps, int depth, SYSTEMTIME *systime)
36 {
37         if(!prs_uint16("year", ps, depth, &systime->year))
38                 return False;
39         if(!prs_uint16("month", ps, depth, &systime->month))
40                 return False;
41         if(!prs_uint16("dayofweek", ps, depth, &systime->dayofweek))
42                 return False;
43         if(!prs_uint16("day", ps, depth, &systime->day))
44                 return False;
45         if(!prs_uint16("hour", ps, depth, &systime->hour))
46                 return False;
47         if(!prs_uint16("minute", ps, depth, &systime->minute))
48                 return False;
49         if(!prs_uint16("second", ps, depth, &systime->second))
50                 return False;
51         if(!prs_uint16("milliseconds", ps, depth, &systime->milliseconds))
52                 return False;
53
54         return True;
55 }
56
57 /*******************************************************************
58 ********************************************************************/  
59
60 BOOL make_systemtime(SYSTEMTIME *systime, struct tm *unixtime)
61 {
62         systime->year=unixtime->tm_year+1900;
63         systime->month=unixtime->tm_mon+1;
64         systime->dayofweek=unixtime->tm_wday;
65         systime->day=unixtime->tm_mday;
66         systime->hour=unixtime->tm_hour;
67         systime->minute=unixtime->tm_min;
68         systime->second=unixtime->tm_sec;
69         systime->milliseconds=0;
70
71         return True;
72 }
73
74 /*******************************************************************
75 reads or writes an DOC_INFO structure.
76 ********************************************************************/  
77
78 static BOOL smb_io_doc_info_1(const char *desc, DOC_INFO_1 *info_1, prs_struct *ps, int depth)
79 {
80         if (info_1 == NULL) return False;
81
82         prs_debug(ps, depth, desc, "smb_io_doc_info_1");
83         depth++;
84  
85         if(!prs_align(ps))
86                 return False;
87         
88         if(!prs_uint32("p_docname",    ps, depth, &info_1->p_docname))
89                 return False;
90         if(!prs_uint32("p_outputfile", ps, depth, &info_1->p_outputfile))
91                 return False;
92         if(!prs_uint32("p_datatype",   ps, depth, &info_1->p_datatype))
93                 return False;
94
95         if(!smb_io_unistr2("", &info_1->docname,    info_1->p_docname,    ps, depth))
96                 return False;
97         if(!smb_io_unistr2("", &info_1->outputfile, info_1->p_outputfile, ps, depth))
98                 return False;
99         if(!smb_io_unistr2("", &info_1->datatype,   info_1->p_datatype,   ps, depth))
100                 return False;
101
102         return True;
103 }
104
105 /*******************************************************************
106 reads or writes an DOC_INFO structure.
107 ********************************************************************/  
108
109 static BOOL smb_io_doc_info(const char *desc, DOC_INFO *info, prs_struct *ps, int depth)
110 {
111         uint32 useless_ptr=0;
112         
113         if (info == NULL) return False;
114
115         prs_debug(ps, depth, desc, "smb_io_doc_info");
116         depth++;
117  
118         if(!prs_align(ps))
119                 return False;
120         
121         if(!prs_uint32("switch_value", ps, depth, &info->switch_value))
122                 return False;
123         
124         if(!prs_uint32("doc_info_X ptr", ps, depth, &useless_ptr))
125                 return False;
126
127         switch (info->switch_value)
128         {
129                 case 1: 
130                         if(!smb_io_doc_info_1("",&info->doc_info_1, ps, depth))
131                                 return False;
132                         break;
133                 case 2:
134                         /*
135                           this is just a placeholder
136                           
137                           MSDN July 1998 says doc_info_2 is only on
138                           Windows 95, and as Win95 doesn't do RPC to print
139                           this case is nearly impossible
140                           
141                           Maybe one day with Windows for dishwasher 2037 ...
142                           
143                         */
144                         /* smb_io_doc_info_2("",&info->doc_info_2, ps, depth); */
145                         break;
146                 default:
147                         DEBUG(0,("Something is obviously wrong somewhere !\n"));
148                         break;
149         }
150
151         return True;
152 }
153
154 /*******************************************************************
155 reads or writes an DOC_INFO_CONTAINER structure.
156 ********************************************************************/  
157
158 static BOOL smb_io_doc_info_container(const char *desc, DOC_INFO_CONTAINER *cont, prs_struct *ps, int depth)
159 {
160         if (cont == NULL) return False;
161
162         prs_debug(ps, depth, desc, "smb_io_doc_info_container");
163         depth++;
164  
165         if(!prs_align(ps))
166                 return False;
167         
168         if(!prs_uint32("level", ps, depth, &cont->level))
169                 return False;
170         
171         if(!smb_io_doc_info("",&cont->docinfo, ps, depth))
172                 return False;
173
174         return True;
175 }
176
177 /*******************************************************************
178 reads or writes an NOTIFY OPTION TYPE structure.
179 ********************************************************************/  
180
181 /* NOTIFY_OPTION_TYPE and NOTIFY_OPTION_TYPE_DATA are really one
182    structure.  The _TYPE structure is really the deferred referrants (i.e
183    the notify fields array) of the _TYPE structure. -tpot */
184
185 static BOOL smb_io_notify_option_type(const char *desc, SPOOL_NOTIFY_OPTION_TYPE *type, prs_struct *ps, int depth)
186 {
187         prs_debug(ps, depth, desc, "smb_io_notify_option_type");
188         depth++;
189  
190         if (!prs_align(ps))
191                 return False;
192
193         if(!prs_uint16("type", ps, depth, &type->type))
194                 return False;
195         if(!prs_uint16("reserved0", ps, depth, &type->reserved0))
196                 return False;
197         if(!prs_uint32("reserved1", ps, depth, &type->reserved1))
198                 return False;
199         if(!prs_uint32("reserved2", ps, depth, &type->reserved2))
200                 return False;
201         if(!prs_uint32("count", ps, depth, &type->count))
202                 return False;
203         if(!prs_uint32("fields_ptr", ps, depth, &type->fields_ptr))
204                 return False;
205
206         return True;
207 }
208
209 /*******************************************************************
210 reads or writes an NOTIFY OPTION TYPE DATA.
211 ********************************************************************/  
212
213 static BOOL smb_io_notify_option_type_data(const char *desc, SPOOL_NOTIFY_OPTION_TYPE *type, prs_struct *ps, int depth)
214 {
215         int i;
216
217         prs_debug(ps, depth, desc, "smb_io_notify_option_type_data");
218         depth++;
219  
220         /* if there are no fields just return */
221         if (type->fields_ptr==0)
222                 return True;
223
224         if(!prs_align(ps))
225                 return False;
226
227         if(!prs_uint32("count2", ps, depth, &type->count2))
228                 return False;
229         
230         if (type->count2 != type->count)
231                 DEBUG(4,("What a mess, count was %x now is %x !\n", type->count, type->count2));
232
233         /* parse the option type data */
234         for(i=0;i<type->count2;i++)
235                 if(!prs_uint16("fields",ps,depth,&type->fields[i]))
236                         return False;
237         return True;
238 }
239
240 /*******************************************************************
241 reads or writes an NOTIFY OPTION structure.
242 ********************************************************************/  
243
244 static BOOL smb_io_notify_option_type_ctr(const char *desc, SPOOL_NOTIFY_OPTION_TYPE_CTR *ctr , prs_struct *ps, int depth)
245 {               
246         int i;
247         
248         prs_debug(ps, depth, desc, "smb_io_notify_option_type_ctr");
249         depth++;
250  
251         if(!prs_uint32("count", ps, depth, &ctr->count))
252                 return False;
253
254         /* reading */
255         if (UNMARSHALLING(ps))
256                 if((ctr->type=PRS_ALLOC_MEM(ps,SPOOL_NOTIFY_OPTION_TYPE,ctr->count)) == NULL)
257                         return False;
258                 
259         /* the option type struct */
260         for(i=0;i<ctr->count;i++)
261                 if(!smb_io_notify_option_type("", &ctr->type[i] , ps, depth))
262                         return False;
263
264         /* the type associated with the option type struct */
265         for(i=0;i<ctr->count;i++)
266                 if(!smb_io_notify_option_type_data("", &ctr->type[i] , ps, depth))
267                         return False;
268         
269         return True;
270 }
271
272 /*******************************************************************
273 reads or writes an NOTIFY OPTION structure.
274 ********************************************************************/  
275
276 static BOOL smb_io_notify_option(const char *desc, SPOOL_NOTIFY_OPTION *option, prs_struct *ps, int depth)
277 {
278         prs_debug(ps, depth, desc, "smb_io_notify_option");
279         depth++;
280         
281         if(!prs_uint32("version", ps, depth, &option->version))
282                 return False;
283         if(!prs_uint32("flags", ps, depth, &option->flags))
284                 return False;
285         if(!prs_uint32("count", ps, depth, &option->count))
286                 return False;
287         if(!prs_uint32("option_type_ptr", ps, depth, &option->option_type_ptr))
288                 return False;
289         
290         /* marshalling or unmarshalling, that would work */     
291         if (option->option_type_ptr!=0) {
292                 if(!smb_io_notify_option_type_ctr("", &option->ctr ,ps, depth))
293                         return False;
294         }
295         else {
296                 option->ctr.type=NULL;
297                 option->ctr.count=0;
298         }
299         
300         return True;
301 }
302
303 /*******************************************************************
304 reads or writes an NOTIFY INFO DATA structure.
305 ********************************************************************/  
306
307 static BOOL smb_io_notify_info_data(const char *desc,SPOOL_NOTIFY_INFO_DATA *data, prs_struct *ps, int depth)
308 {
309         uint32 useless_ptr=0x0FF0ADDE;
310
311         prs_debug(ps, depth, desc, "smb_io_notify_info_data");
312         depth++;
313
314         if(!prs_align(ps))
315                 return False;
316         if(!prs_uint16("type",           ps, depth, &data->type))
317                 return False;
318         if(!prs_uint16("field",          ps, depth, &data->field))
319                 return False;
320
321         if(!prs_uint32("how many words", ps, depth, &data->size))
322                 return False;
323         if(!prs_uint32("id",             ps, depth, &data->id))
324                 return False;
325         if(!prs_uint32("how many words", ps, depth, &data->size))
326                 return False;
327
328         switch (data->enc_type) {
329
330                 /* One and two value data has two uint32 values */
331
332         case NOTIFY_ONE_VALUE:
333         case NOTIFY_TWO_VALUE:
334
335                 if(!prs_uint32("value[0]", ps, depth, &data->notify_data.value[0]))
336                         return False;
337                 if(!prs_uint32("value[1]", ps, depth, &data->notify_data.value[1]))
338                         return False;
339                 break;
340
341                 /* Pointers and strings have a string length and a
342                    pointer.  For a string the length is expressed as
343                    the number of uint16 characters plus a trailing
344                    \0\0. */
345
346         case NOTIFY_POINTER:
347
348                 if(!prs_uint32("string length", ps, depth, &data->notify_data.data.length ))
349                         return False;
350                 if(!prs_uint32("pointer", ps, depth, &useless_ptr))
351                         return False;
352
353                 break;
354
355         case NOTIFY_STRING:
356
357                 if(!prs_uint32("string length", ps, depth, &data->notify_data.data.length))
358                         return False;
359
360                 if(!prs_uint32("pointer", ps, depth, &useless_ptr))
361                         return False;
362
363                 break;
364
365         case NOTIFY_SECDESC:
366                 if( !prs_uint32( "sd size", ps, depth, &data->notify_data.sd.size ) )
367                         return False;
368                 if( !prs_uint32( "pointer", ps, depth, &useless_ptr ) )
369                         return False;
370                 
371                 break;
372
373         default:
374                 DEBUG(3, ("invalid enc_type %d for smb_io_notify_info_data\n",
375                           data->enc_type));
376                 break;
377         }
378
379         return True;
380 }
381
382 /*******************************************************************
383 reads or writes an NOTIFY INFO DATA structure.
384 ********************************************************************/  
385
386 BOOL smb_io_notify_info_data_strings(const char *desc,SPOOL_NOTIFY_INFO_DATA *data,
387                                      prs_struct *ps, int depth)
388 {
389         prs_debug(ps, depth, desc, "smb_io_notify_info_data_strings");
390         depth++;
391         
392         if(!prs_align(ps))
393                 return False;
394
395         switch(data->enc_type) {
396
397                 /* No data for values */
398
399         case NOTIFY_ONE_VALUE:
400         case NOTIFY_TWO_VALUE:
401
402                 break;
403
404                 /* Strings start with a length in uint16s */
405
406         case NOTIFY_STRING:
407
408                 if (MARSHALLING(ps))
409                         data->notify_data.data.length /= 2;
410
411                 if(!prs_uint32("string length", ps, depth, &data->notify_data.data.length))
412                         return False;
413
414                 if (UNMARSHALLING(ps)) {
415                         data->notify_data.data.string = PRS_ALLOC_MEM(ps, uint16,
416                                                                 data->notify_data.data.length);
417
418                         if (!data->notify_data.data.string) 
419                                 return False;
420                 }
421
422                 if (!prs_uint16uni(True, "string", ps, depth, data->notify_data.data.string,
423                                    data->notify_data.data.length))
424                         return False;
425
426                 if (MARSHALLING(ps))
427                         data->notify_data.data.length *= 2;
428
429                 break;
430
431         case NOTIFY_POINTER:
432
433                 if (UNMARSHALLING(ps)) {
434                         data->notify_data.data.string = PRS_ALLOC_MEM(ps, uint16,
435                                                                 data->notify_data.data.length);
436
437                         if (!data->notify_data.data.string) 
438                                 return False;
439                 }
440
441                 if(!prs_uint8s(True,"buffer",ps,depth,(uint8*)data->notify_data.data.string,data->notify_data.data.length))
442                         return False;
443
444                 break;
445
446         case NOTIFY_SECDESC:    
447                 if( !prs_uint32("secdesc size ", ps, depth, &data->notify_data.sd.size ) )
448                         return False;
449                 if ( !sec_io_desc( "sec_desc", &data->notify_data.sd.desc, ps, depth ) )
450                         return False;
451                 break;
452
453         default:
454                 DEBUG(3, ("invalid enc_type %d for smb_io_notify_info_data_strings\n",
455                           data->enc_type));
456                 break;
457         }
458
459 #if 0
460         if (isvalue==False) {
461
462                 /* length of string in unicode include \0 */
463                 x=data->notify_data.data.length+1;
464
465                 if (data->field != 16)
466                 if(!prs_uint32("string length", ps, depth, &x ))
467                         return False;
468
469                 if (MARSHALLING(ps)) {
470                         /* These are already in little endian format. Don't byte swap. */
471                         if (x == 1) {
472
473                                 /* No memory allocated for this string
474                                    therefore following the data.string
475                                    pointer is a bad idea.  Use a pointer to
476                                    the uint32 length union member to
477                                    provide a source for a unicode NULL */
478
479                                 if(!prs_uint8s(True,"string",ps,depth, (uint8 *)&data->notify_data.data.length,x*2)) 
480                                         return False;
481                         } else {
482
483                                 if (data->field == 16)
484                                         x /= 2;
485
486                                 if(!prs_uint16uni(True,"string",ps,depth,data->notify_data.data.string,x))
487                                         return False;
488                         }
489                 } else {
490
491                         /* Tallocate memory for string */
492
493                         data->notify_data.data.string = PRS_ALLOC_MEM(ps, uint16, x * 2);
494                         if (!data->notify_data.data.string) 
495                                 return False;
496
497                         if(!prs_uint16uni(True,"string",ps,depth,data->notify_data.data.string,x))
498                                 return False;
499                 }
500         }
501
502 #endif
503
504 #if 0   /* JERRY */
505         /* Win2k does not seem to put this parse align here */
506         if(!prs_align(ps))
507                 return False;
508 #endif
509
510         return True;
511 }
512
513 /*******************************************************************
514 reads or writes an NOTIFY INFO structure.
515 ********************************************************************/  
516
517 static BOOL smb_io_notify_info(const char *desc, SPOOL_NOTIFY_INFO *info, prs_struct *ps, int depth)
518 {
519         int i;
520
521         prs_debug(ps, depth, desc, "smb_io_notify_info");
522         depth++;
523  
524         if(!prs_align(ps))
525                 return False;
526
527         if(!prs_uint32("count", ps, depth, &info->count))
528                 return False;
529         if(!prs_uint32("version", ps, depth, &info->version))
530                 return False;
531         if(!prs_uint32("flags", ps, depth, &info->flags))
532                 return False;
533         if(!prs_uint32("count", ps, depth, &info->count))
534                 return False;
535
536         for (i=0;i<info->count;i++) {
537                 if(!smb_io_notify_info_data(desc, &info->data[i], ps, depth))
538                         return False;
539         }
540
541         /* now do the strings at the end of the stream */       
542         for (i=0;i<info->count;i++) {
543                 if(!smb_io_notify_info_data_strings(desc, &info->data[i], ps, depth))
544                         return False;
545         }
546
547         return True;
548 }
549
550 /*******************************************************************
551 ********************************************************************/  
552
553 BOOL spool_io_user_level_1( const char *desc, prs_struct *ps, int depth, SPOOL_USER_1 *q_u )
554 {
555         prs_debug(ps, depth, desc, "");
556         depth++;
557
558         if (!prs_align(ps))
559                 return False;
560
561         if (!prs_uint32("size", ps, depth, &q_u->size))
562                 return False;
563
564         if (!prs_io_unistr2_p("", ps, depth, &q_u->client_name))
565                 return False;
566         if (!prs_io_unistr2_p("", ps, depth, &q_u->user_name))
567                 return False;
568
569         if (!prs_uint32("build", ps, depth, &q_u->build))
570                 return False;
571         if (!prs_uint32("major", ps, depth, &q_u->major))
572                 return False;
573         if (!prs_uint32("minor", ps, depth, &q_u->minor))
574                 return False;
575         if (!prs_uint32("processor", ps, depth, &q_u->processor))
576                 return False;
577
578         if (!prs_io_unistr2("", ps, depth, q_u->client_name))
579                 return False;
580         if (!prs_align(ps))
581                 return False;
582
583         if (!prs_io_unistr2("", ps, depth, q_u->user_name))
584                 return False;
585
586         return True;
587 }
588
589 /*******************************************************************
590 ********************************************************************/  
591
592 static BOOL spool_io_user_level(const char *desc, SPOOL_USER_CTR *q_u, prs_struct *ps, int depth)
593 {
594         if (q_u==NULL)
595                 return False;
596
597         prs_debug(ps, depth, desc, "spool_io_user_level");
598         depth++;
599
600         if (!prs_align(ps))
601                 return False;
602
603         if (!prs_uint32("level", ps, depth, &q_u->level))
604                 return False;
605         
606         switch ( q_u->level ) 
607         {       
608                 case 1:
609                         if ( !prs_pointer( "" , ps, depth, (void**)&q_u->user.user1, 
610                                 sizeof(SPOOL_USER_1), (PRS_POINTER_CAST)spool_io_user_level_1 )) 
611                         {
612                                 return False;
613                         }
614                         break;
615                 default:
616                         return False;   
617         }       
618
619         return True;
620 }
621
622 /*******************************************************************
623  * read or write a DEVICEMODE struct.
624  * on reading allocate memory for the private member
625  ********************************************************************/
626
627 #define DM_NUM_OPTIONAL_FIELDS          8
628
629 BOOL spoolss_io_devmode(const char *desc, prs_struct *ps, int depth, DEVICEMODE *devmode)
630 {
631         int available_space;            /* size of the device mode left to parse */
632                                         /* only important on unmarshalling       */
633         int i = 0;
634                                         
635         struct optional_fields {
636                 fstring         name;
637                 uint32*         field;
638         } opt_fields[DM_NUM_OPTIONAL_FIELDS] = {
639                 { "icmmethod",          NULL },
640                 { "icmintent",          NULL },
641                 { "mediatype",          NULL },
642                 { "dithertype",         NULL },
643                 { "reserved1",          NULL },
644                 { "reserved2",          NULL },
645                 { "panningwidth",       NULL },
646                 { "panningheight",      NULL }
647         };
648
649         /* assign at run time to keep non-gcc compilers happy */
650
651         opt_fields[0].field = &devmode->icmmethod;
652         opt_fields[1].field = &devmode->icmintent;
653         opt_fields[2].field = &devmode->mediatype;
654         opt_fields[3].field = &devmode->dithertype;
655         opt_fields[4].field = &devmode->reserved1;
656         opt_fields[5].field = &devmode->reserved2;
657         opt_fields[6].field = &devmode->panningwidth;
658         opt_fields[7].field = &devmode->panningheight;
659                 
660         
661         prs_debug(ps, depth, desc, "spoolss_io_devmode");
662         depth++;
663
664         if (UNMARSHALLING(ps)) {
665                 devmode->devicename.buffer = PRS_ALLOC_MEM(ps, uint16, 32);
666                 if (devmode->devicename.buffer == NULL)
667                         return False;
668         }
669
670         if (!prs_uint16uni(True,"devicename", ps, depth, devmode->devicename.buffer, MAXDEVICENAME))
671                 return False;
672         
673         if (!prs_uint16("specversion",      ps, depth, &devmode->specversion))
674                 return False;
675                 
676         if (!prs_uint16("driverversion",    ps, depth, &devmode->driverversion))
677                 return False;
678         if (!prs_uint16("size",             ps, depth, &devmode->size))
679                 return False;
680         if (!prs_uint16("driverextra",      ps, depth, &devmode->driverextra))
681                 return False;
682         if (!prs_uint32("fields",           ps, depth, &devmode->fields))
683                 return False;
684         if (!prs_uint16("orientation",      ps, depth, &devmode->orientation))
685                 return False;
686         if (!prs_uint16("papersize",        ps, depth, &devmode->papersize))
687                 return False;
688         if (!prs_uint16("paperlength",      ps, depth, &devmode->paperlength))
689                 return False;
690         if (!prs_uint16("paperwidth",       ps, depth, &devmode->paperwidth))
691                 return False;
692         if (!prs_uint16("scale",            ps, depth, &devmode->scale))
693                 return False;
694         if (!prs_uint16("copies",           ps, depth, &devmode->copies))
695                 return False;
696         if (!prs_uint16("defaultsource",    ps, depth, &devmode->defaultsource))
697                 return False;
698         if (!prs_uint16("printquality",     ps, depth, &devmode->printquality))
699                 return False;
700         if (!prs_uint16("color",            ps, depth, &devmode->color))
701                 return False;
702         if (!prs_uint16("duplex",           ps, depth, &devmode->duplex))
703                 return False;
704         if (!prs_uint16("yresolution",      ps, depth, &devmode->yresolution))
705                 return False;
706         if (!prs_uint16("ttoption",         ps, depth, &devmode->ttoption))
707                 return False;
708         if (!prs_uint16("collate",          ps, depth, &devmode->collate))
709                 return False;
710
711         if (UNMARSHALLING(ps)) {
712                 devmode->formname.buffer = PRS_ALLOC_MEM(ps, uint16, 32);
713                 if (devmode->formname.buffer == NULL)
714                         return False;
715         }
716
717         if (!prs_uint16uni(True, "formname",  ps, depth, devmode->formname.buffer, 32))
718                 return False;
719         if (!prs_uint16("logpixels",        ps, depth, &devmode->logpixels))
720                 return False;
721         if (!prs_uint32("bitsperpel",       ps, depth, &devmode->bitsperpel))
722                 return False;
723         if (!prs_uint32("pelswidth",        ps, depth, &devmode->pelswidth))
724                 return False;
725         if (!prs_uint32("pelsheight",       ps, depth, &devmode->pelsheight))
726                 return False;
727         if (!prs_uint32("displayflags",     ps, depth, &devmode->displayflags))
728                 return False;
729         if (!prs_uint32("displayfrequency", ps, depth, &devmode->displayfrequency))
730                 return False;
731         /* 
732          * every device mode I've ever seen on the wire at least has up 
733          * to the displayfrequency field.   --jerry (05-09-2002)
734          */
735          
736         /* add uint32's + uint16's + two UNICODE strings */
737          
738         available_space = devmode->size - (sizeof(uint32)*6 + sizeof(uint16)*18 + sizeof(uint16)*64);
739         
740         /* Sanity check - we only have uint32's left tp parse */
741         
742         if ( available_space && ((available_space % sizeof(uint32)) != 0) ) {
743                 DEBUG(0,("spoolss_io_devmode: available_space [%d] no in multiple of 4 bytes (size = %d)!\n",
744                         available_space, devmode->size));
745                 DEBUG(0,("spoolss_io_devmode: please report to samba-technical@samba.org!\n"));
746                 return False;
747         }
748
749         /* 
750          * Conditional parsing.  Assume that the DeviceMode has been 
751          * zero'd by the caller. 
752          */
753         
754         while ((available_space > 0)  && (i < DM_NUM_OPTIONAL_FIELDS))
755         {
756                 DEBUG(11, ("spoolss_io_devmode: [%d] bytes left to parse in devmode\n", available_space));
757                 if (!prs_uint32(opt_fields[i].name, ps, depth, opt_fields[i].field))
758                         return False;
759                 available_space -= sizeof(uint32);
760                 i++;
761         }        
762         
763         /* Sanity Check - we should no available space at this point unless 
764            MS changes the device mode structure */
765                 
766         if (available_space) {
767                 DEBUG(0,("spoolss_io_devmode: I've parsed all I know and there is still stuff left|\n"));
768                 DEBUG(0,("spoolss_io_devmode: available_space = [%d], devmode_size = [%d]!\n",
769                         available_space, devmode->size));
770                 DEBUG(0,("spoolss_io_devmode: please report to samba-technical@samba.org!\n"));
771                 return False;
772         }
773
774
775         if (devmode->driverextra!=0) {
776                 if (UNMARSHALLING(ps)) {
777                         devmode->dev_private=PRS_ALLOC_MEM(ps, uint8, devmode->driverextra);
778                         if(devmode->dev_private == NULL)
779                                 return False;
780                         DEBUG(7,("spoolss_io_devmode: allocated memory [%d] for dev_private\n",devmode->driverextra)); 
781                 }
782                         
783                 DEBUG(7,("spoolss_io_devmode: parsing [%d] bytes of dev_private\n",devmode->driverextra));
784                 if (!prs_uint8s(False, "dev_private",  ps, depth,
785                                 devmode->dev_private, devmode->driverextra))
786                         return False;
787         }
788
789         return True;
790 }
791
792 /*******************************************************************
793  Read or write a DEVICEMODE container
794 ********************************************************************/  
795
796 static BOOL spoolss_io_devmode_cont(const char *desc, DEVMODE_CTR *dm_c, prs_struct *ps, int depth)
797 {
798         if (dm_c==NULL)
799                 return False;
800
801         prs_debug(ps, depth, desc, "spoolss_io_devmode_cont");
802         depth++;
803
804         if(!prs_align(ps))
805                 return False;
806         
807         if (!prs_uint32("size", ps, depth, &dm_c->size))
808                 return False;
809
810         if (!prs_uint32("devmode_ptr", ps, depth, &dm_c->devmode_ptr))
811                 return False;
812
813         if (dm_c->size==0 || dm_c->devmode_ptr==0) {
814                 if (UNMARSHALLING(ps))
815                         /* if while reading there is no DEVMODE ... */
816                         dm_c->devmode=NULL;
817                 return True;
818         }
819         
820         /* so we have a DEVICEMODE to follow */         
821         if (UNMARSHALLING(ps)) {
822                 DEBUG(9,("Allocating memory for spoolss_io_devmode\n"));
823                 dm_c->devmode=PRS_ALLOC_MEM(ps,DEVICEMODE,1);
824                 if(dm_c->devmode == NULL)
825                         return False;
826         }
827         
828         /* this is bad code, shouldn't be there */
829         if (!prs_uint32("size", ps, depth, &dm_c->size))
830                 return False;
831                 
832         if (!spoolss_io_devmode(desc, ps, depth, dm_c->devmode))
833                 return False;
834
835         return True;
836 }
837
838 /*******************************************************************
839 ********************************************************************/  
840
841 static BOOL spoolss_io_printer_default(const char *desc, PRINTER_DEFAULT *pd, prs_struct *ps, int depth)
842 {
843         if (pd==NULL)
844                 return False;
845
846         prs_debug(ps, depth, desc, "spoolss_io_printer_default");
847         depth++;
848
849         if (!prs_uint32("datatype_ptr", ps, depth, &pd->datatype_ptr))
850                 return False;
851
852         if (!smb_io_unistr2("datatype", &pd->datatype, pd->datatype_ptr, ps,depth))
853                 return False;
854         
855         if (!prs_align(ps))
856                 return False;
857
858         if (!spoolss_io_devmode_cont("", &pd->devmode_cont, ps, depth))
859                 return False;
860
861         if (!prs_align(ps))
862                 return False;
863
864         if (!prs_uint32("access_required", ps, depth, &pd->access_required))
865                 return False;
866
867         return True;
868 }
869
870 /*******************************************************************
871  * init a structure.
872  ********************************************************************/
873
874 BOOL make_spoolss_q_open_printer_ex(SPOOL_Q_OPEN_PRINTER_EX *q_u,
875                 const fstring printername, 
876                 const fstring datatype, 
877                 uint32 access_required,
878                 const fstring clientname,
879                 const fstring user_name)
880 {
881         DEBUG(5,("make_spoolss_q_open_printer_ex\n"));
882
883         q_u->printername = TALLOC_P( get_talloc_ctx(), UNISTR2 );
884         init_unistr2(q_u->printername, printername, UNI_STR_TERMINATE);
885
886         q_u->printer_default.datatype_ptr = 0;
887
888         q_u->printer_default.devmode_cont.size=0;
889         q_u->printer_default.devmode_cont.devmode_ptr=0;
890         q_u->printer_default.devmode_cont.devmode=NULL;
891         q_u->printer_default.access_required=access_required;
892
893         q_u->user_switch = 1;
894         
895         q_u->user_ctr.level                 = 1;
896         q_u->user_ctr.user.user1            = TALLOC_P( get_talloc_ctx(), SPOOL_USER_1 );
897         q_u->user_ctr.user.user1->size      = strlen(clientname) + strlen(user_name) + 10;
898         q_u->user_ctr.user.user1->build     = 1381;
899         q_u->user_ctr.user.user1->major     = 2;
900         q_u->user_ctr.user.user1->minor     = 0;
901         q_u->user_ctr.user.user1->processor = 0;
902
903         q_u->user_ctr.user.user1->client_name = TALLOC_P( get_talloc_ctx(), UNISTR2 );
904         q_u->user_ctr.user.user1->user_name   = TALLOC_P( get_talloc_ctx(), UNISTR2 );
905
906         init_unistr2(q_u->user_ctr.user.user1->client_name, clientname, UNI_STR_TERMINATE);
907         init_unistr2(q_u->user_ctr.user.user1->user_name, user_name, UNI_STR_TERMINATE);
908         
909         return True;
910 }
911
912 /*******************************************************************
913  * init a structure.
914  ********************************************************************/
915
916 BOOL make_spoolss_q_addprinterex( TALLOC_CTX *mem_ctx, SPOOL_Q_ADDPRINTEREX *q_u, 
917         const char *srv_name, const char* clientname, const char* user_name,
918         uint32 level, PRINTER_INFO_CTR *ctr)
919 {
920         DEBUG(5,("make_spoolss_q_addprinterex\n"));
921         
922         if (!ctr) 
923                 return False;
924
925         ZERO_STRUCTP(q_u);
926
927         q_u->server_name = TALLOC_P( mem_ctx, UNISTR2 );
928         init_unistr2(q_u->server_name, srv_name, UNI_FLAGS_NONE);
929
930         q_u->level = level;
931         
932         q_u->info.level = level;
933         q_u->info.info_ptr = (ctr->printers_2!=NULL)?1:0;
934         switch (level) {
935                 case 2:
936                         /* init q_u->info.info2 from *info */
937                         if (!make_spoolss_printer_info_2(mem_ctx, &q_u->info.info_2, ctr->printers_2)) {
938                                 DEBUG(0,("make_spoolss_q_addprinterex: Unable to fill SPOOL_Q_ADDPRINTEREX struct!\n"));
939                                 return False;
940                         }
941                         break;
942                 default :
943                         break;
944         }
945
946         q_u->user_switch=1;
947
948         q_u->user_ctr.level                 = 1;
949         q_u->user_ctr.user.user1            = TALLOC_P( get_talloc_ctx(), SPOOL_USER_1 );
950         q_u->user_ctr.user.user1->build     = 1381;
951         q_u->user_ctr.user.user1->major     = 2; 
952         q_u->user_ctr.user.user1->minor     = 0;
953         q_u->user_ctr.user.user1->processor = 0;
954
955         q_u->user_ctr.user.user1->client_name = TALLOC_P( mem_ctx, UNISTR2 );
956         q_u->user_ctr.user.user1->user_name   = TALLOC_P( mem_ctx, UNISTR2 );
957
958         init_unistr2(q_u->user_ctr.user.user1->client_name, clientname, UNI_STR_TERMINATE);
959         init_unistr2(q_u->user_ctr.user.user1->user_name, user_name, UNI_STR_TERMINATE);
960
961         q_u->user_ctr.user.user1->size = q_u->user_ctr.user.user1->user_name->uni_str_len +
962                                    q_u->user_ctr.user.user1->client_name->uni_str_len + 2;
963         
964         return True;
965 }
966         
967 /*******************************************************************
968 create a SPOOL_PRINTER_INFO_2 stuct from a PRINTER_INFO_2 struct
969 *******************************************************************/
970
971 BOOL make_spoolss_printer_info_2(TALLOC_CTX *mem_ctx, SPOOL_PRINTER_INFO_LEVEL_2 **spool_info2, 
972                                 PRINTER_INFO_2 *info)
973 {
974
975         SPOOL_PRINTER_INFO_LEVEL_2 *inf;
976
977         /* allocate the necessary memory */
978         if (!(inf=TALLOC_P(mem_ctx, SPOOL_PRINTER_INFO_LEVEL_2))) {
979                 DEBUG(0,("make_spoolss_printer_info_2: Unable to allocate SPOOL_PRINTER_INFO_LEVEL_2 sruct!\n"));
980                 return False;
981         }
982         
983         inf->servername_ptr     = (info->servername.buffer!=NULL)?1:0;
984         inf->printername_ptr    = (info->printername.buffer!=NULL)?1:0;
985         inf->sharename_ptr      = (info->sharename.buffer!=NULL)?1:0;
986         inf->portname_ptr       = (info->portname.buffer!=NULL)?1:0;
987         inf->drivername_ptr     = (info->drivername.buffer!=NULL)?1:0;
988         inf->comment_ptr        = (info->comment.buffer!=NULL)?1:0;
989         inf->location_ptr       = (info->location.buffer!=NULL)?1:0;
990         inf->devmode_ptr        = (info->devmode!=NULL)?1:0;
991         inf->sepfile_ptr        = (info->sepfile.buffer!=NULL)?1:0;
992         inf->printprocessor_ptr = (info->printprocessor.buffer!=NULL)?1:0;
993         inf->datatype_ptr       = (info->datatype.buffer!=NULL)?1:0;
994         inf->parameters_ptr     = (info->parameters.buffer!=NULL)?1:0;
995         inf->secdesc_ptr        = (info->secdesc!=NULL)?1:0;
996         inf->attributes         = info->attributes;
997         inf->priority           = info->priority;
998         inf->default_priority   = info->defaultpriority;
999         inf->starttime          = info->starttime;
1000         inf->untiltime          = info->untiltime;
1001         inf->cjobs              = info->cjobs;
1002         inf->averageppm = info->averageppm;
1003         init_unistr2_from_unistr(&inf->servername,      &info->servername);
1004         init_unistr2_from_unistr(&inf->printername,     &info->printername);
1005         init_unistr2_from_unistr(&inf->sharename,       &info->sharename);
1006         init_unistr2_from_unistr(&inf->portname,        &info->portname);
1007         init_unistr2_from_unistr(&inf->drivername,      &info->drivername);
1008         init_unistr2_from_unistr(&inf->comment,         &info->comment);
1009         init_unistr2_from_unistr(&inf->location,        &info->location);
1010         init_unistr2_from_unistr(&inf->sepfile,         &info->sepfile);
1011         init_unistr2_from_unistr(&inf->printprocessor,  &info->printprocessor);
1012         init_unistr2_from_unistr(&inf->datatype,        &info->datatype);
1013         init_unistr2_from_unistr(&inf->parameters,      &info->parameters);
1014         init_unistr2_from_unistr(&inf->datatype,        &info->datatype);
1015
1016         *spool_info2 = inf;
1017
1018         return True;
1019 }
1020
1021 /*******************************************************************
1022 create a SPOOL_PRINTER_INFO_3 struct from a PRINTER_INFO_3 struct
1023 *******************************************************************/
1024
1025 BOOL make_spoolss_printer_info_3(TALLOC_CTX *mem_ctx, SPOOL_PRINTER_INFO_LEVEL_3 **spool_info3, 
1026                                 PRINTER_INFO_3 *info)
1027 {
1028
1029         SPOOL_PRINTER_INFO_LEVEL_3 *inf;
1030
1031         /* allocate the necessary memory */
1032         if (!(inf=TALLOC_P(mem_ctx, SPOOL_PRINTER_INFO_LEVEL_3))) {
1033                 DEBUG(0,("make_spoolss_printer_info_3: Unable to allocate SPOOL_PRINTER_INFO_LEVEL_3 sruct!\n"));
1034                 return False;
1035         }
1036         
1037         inf->secdesc_ptr        = (info->secdesc!=NULL)?1:0;
1038
1039         *spool_info3 = inf;
1040
1041         return True;
1042 }
1043
1044 /*******************************************************************
1045 create a SPOOL_PRINTER_INFO_7 struct from a PRINTER_INFO_7 struct
1046 *******************************************************************/
1047
1048 BOOL make_spoolss_printer_info_7(TALLOC_CTX *mem_ctx, SPOOL_PRINTER_INFO_LEVEL_7 **spool_info7, 
1049                                 PRINTER_INFO_7 *info)
1050 {
1051
1052         SPOOL_PRINTER_INFO_LEVEL_7 *inf;
1053
1054         /* allocate the necessary memory */
1055         if (!(inf=TALLOC_P(mem_ctx, SPOOL_PRINTER_INFO_LEVEL_7))) {
1056                 DEBUG(0,("make_spoolss_printer_info_7: Unable to allocate SPOOL_PRINTER_INFO_LEVEL_7 struct!\n"));
1057                 return False;
1058         }
1059
1060         inf->guid_ptr           = (info->guid.buffer!=NULL)?1:0;
1061         inf->action             = info->action;
1062         init_unistr2_from_unistr(&inf->guid,            &info->guid);
1063
1064         *spool_info7 = inf;
1065
1066         return True;
1067 }
1068
1069
1070 /*******************************************************************
1071  * read a structure.
1072  * called from spoolss_q_open_printer_ex (srv_spoolss.c)
1073  ********************************************************************/
1074
1075 BOOL spoolss_io_q_open_printer(const char *desc, SPOOL_Q_OPEN_PRINTER *q_u, prs_struct *ps, int depth)
1076 {
1077         if (q_u == NULL)
1078                 return False;
1079
1080         prs_debug(ps, depth, desc, "spoolss_io_q_open_printer");
1081         depth++;
1082
1083         if (!prs_align(ps))
1084                 return False;
1085
1086         if (!prs_io_unistr2_p("ptr", ps, depth, &q_u->printername))
1087                 return False;
1088         if (!prs_io_unistr2("printername", ps, depth, q_u->printername))
1089                 return False;
1090         
1091         if (!prs_align(ps))
1092                 return False;
1093
1094         if (!spoolss_io_printer_default("", &q_u->printer_default, ps, depth))
1095                 return False;
1096                 
1097         return True;
1098 }
1099
1100 /*******************************************************************
1101  * write a structure.
1102  * called from static spoolss_r_open_printer_ex (srv_spoolss.c)
1103  * called from spoolss_open_printer_ex (cli_spoolss.c)
1104  ********************************************************************/
1105
1106 BOOL spoolss_io_r_open_printer(const char *desc, SPOOL_R_OPEN_PRINTER *r_u, prs_struct *ps, int depth)
1107 {
1108         if (r_u == NULL) return False;
1109
1110         prs_debug(ps, depth, desc, "spoolss_io_r_open_printer");
1111         depth++;
1112         
1113         if (!prs_align(ps))
1114                 return False;
1115
1116         if (!smb_io_pol_hnd("printer handle",&(r_u->handle),ps,depth))
1117                 return False;   
1118
1119         if (!prs_werror("status code", ps, depth, &(r_u->status)))
1120                 return False;
1121                 
1122         return True;
1123 }
1124
1125
1126 /*******************************************************************
1127  * read a structure.
1128  * called from spoolss_q_open_printer_ex (srv_spoolss.c)
1129  ********************************************************************/
1130
1131 BOOL spoolss_io_q_open_printer_ex(const char *desc, SPOOL_Q_OPEN_PRINTER_EX *q_u, prs_struct *ps, int depth)
1132 {
1133         if (q_u == NULL)
1134                 return False;
1135
1136         prs_debug(ps, depth, desc, "spoolss_io_q_open_printer_ex");
1137         depth++;
1138
1139         if (!prs_align(ps))
1140                 return False;
1141
1142         if (!prs_io_unistr2_p("ptr", ps, depth, &q_u->printername))
1143                 return False;
1144         if (!prs_io_unistr2("printername", ps, depth, q_u->printername))
1145                 return False;
1146         
1147         if (!prs_align(ps))
1148                 return False;
1149
1150         if (!spoolss_io_printer_default("", &q_u->printer_default, ps, depth))
1151                 return False;
1152
1153         if (!prs_uint32("user_switch", ps, depth, &q_u->user_switch))
1154                 return False;   
1155         if (!spool_io_user_level("", &q_u->user_ctr, ps, depth))
1156                 return False;
1157         
1158         return True;
1159 }
1160
1161 /*******************************************************************
1162  * write a structure.
1163  * called from static spoolss_r_open_printer_ex (srv_spoolss.c)
1164  * called from spoolss_open_printer_ex (cli_spoolss.c)
1165  ********************************************************************/
1166
1167 BOOL spoolss_io_r_open_printer_ex(const char *desc, SPOOL_R_OPEN_PRINTER_EX *r_u, prs_struct *ps, int depth)
1168 {
1169         if (r_u == NULL) return False;
1170
1171         prs_debug(ps, depth, desc, "spoolss_io_r_open_printer_ex");
1172         depth++;
1173         
1174         if (!prs_align(ps))
1175                 return False;
1176
1177         if (!smb_io_pol_hnd("printer handle",&(r_u->handle),ps,depth))
1178                 return False;
1179
1180         if (!prs_werror("status code", ps, depth, &(r_u->status)))
1181                 return False;
1182
1183         return True;
1184 }
1185
1186 /*******************************************************************
1187  * init a structure.
1188  ********************************************************************/
1189 BOOL make_spoolss_q_deleteprinterdriverex( TALLOC_CTX *mem_ctx,
1190                                            SPOOL_Q_DELETEPRINTERDRIVEREX *q_u, 
1191                                            const char *server,
1192                                            const char* arch, 
1193                                            const char* driver,
1194                                            int version)
1195 {
1196         DEBUG(5,("make_spoolss_q_deleteprinterdriverex\n"));
1197  
1198         q_u->server_ptr = (server!=NULL)?1:0;
1199         q_u->delete_flags = DPD_DELETE_UNUSED_FILES;
1200  
1201         /* these must be NULL terminated or else NT4 will
1202            complain about invalid parameters --jerry */
1203         init_unistr2(&q_u->server, server, UNI_STR_TERMINATE);
1204         init_unistr2(&q_u->arch, arch, UNI_STR_TERMINATE);
1205         init_unistr2(&q_u->driver, driver, UNI_STR_TERMINATE);
1206
1207         if (version >= 0) { 
1208                 q_u->delete_flags |= DPD_DELETE_SPECIFIC_VERSION;
1209                 q_u->version = version;
1210         }
1211
1212         return True;
1213 }
1214
1215
1216 /*******************************************************************
1217  * init a structure.
1218  ********************************************************************/
1219 BOOL make_spoolss_q_deleteprinterdriver(
1220         TALLOC_CTX *mem_ctx,
1221         SPOOL_Q_DELETEPRINTERDRIVER *q_u, 
1222         const char *server,
1223         const char* arch, 
1224         const char* driver 
1225 )
1226 {
1227         DEBUG(5,("make_spoolss_q_deleteprinterdriver\n"));
1228         
1229         q_u->server_ptr = (server!=NULL)?1:0;
1230
1231         /* these must be NULL terminated or else NT4 will
1232            complain about invalid parameters --jerry */
1233         init_unistr2(&q_u->server, server, UNI_STR_TERMINATE);
1234         init_unistr2(&q_u->arch, arch, UNI_STR_TERMINATE);
1235         init_unistr2(&q_u->driver, driver, UNI_STR_TERMINATE);
1236         
1237         return True;
1238 }
1239
1240 /*******************************************************************
1241  * make a structure.
1242  ********************************************************************/
1243
1244 BOOL make_spoolss_q_getprinterdata(SPOOL_Q_GETPRINTERDATA *q_u,
1245                                    const POLICY_HND *handle,
1246                                    const char *valuename, uint32 size)
1247 {
1248         if (q_u == NULL) return False;
1249
1250         DEBUG(5,("make_spoolss_q_getprinterdata\n"));
1251
1252         q_u->handle = *handle;
1253         init_unistr2(&q_u->valuename, valuename, UNI_STR_TERMINATE);
1254         q_u->size = size;
1255
1256         return True;
1257 }
1258
1259 /*******************************************************************
1260  * make a structure.
1261  ********************************************************************/
1262
1263 BOOL make_spoolss_q_getprinterdataex(SPOOL_Q_GETPRINTERDATAEX *q_u,
1264                                      const POLICY_HND *handle,
1265                                      const char *keyname, 
1266                                      const char *valuename, uint32 size)
1267 {
1268         if (q_u == NULL) return False;
1269
1270         DEBUG(5,("make_spoolss_q_getprinterdataex\n"));
1271
1272         q_u->handle = *handle;
1273         init_unistr2(&q_u->valuename, valuename, UNI_STR_TERMINATE);
1274         init_unistr2(&q_u->keyname, keyname, UNI_STR_TERMINATE);
1275         q_u->size = size;
1276
1277         return True;
1278 }
1279
1280 /*******************************************************************
1281  * read a structure.
1282  * called from spoolss_q_getprinterdata (srv_spoolss.c)
1283  ********************************************************************/
1284
1285 BOOL spoolss_io_q_getprinterdata(const char *desc, SPOOL_Q_GETPRINTERDATA *q_u, prs_struct *ps, int depth)
1286 {
1287         if (q_u == NULL)
1288                 return False;
1289
1290         prs_debug(ps, depth, desc, "spoolss_io_q_getprinterdata");
1291         depth++;
1292
1293         if (!prs_align(ps))
1294                 return False;
1295         if (!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
1296                 return False;
1297         if (!prs_align(ps))
1298                 return False;
1299         if (!smb_io_unistr2("valuename", &q_u->valuename,True,ps,depth))
1300                 return False;
1301         if (!prs_align(ps))
1302                 return False;
1303         if (!prs_uint32("size", ps, depth, &q_u->size))
1304                 return False;
1305
1306         return True;
1307 }
1308
1309 /*******************************************************************
1310  * read a structure.
1311  * called from spoolss_q_deleteprinterdata (srv_spoolss.c)
1312  ********************************************************************/
1313
1314 BOOL spoolss_io_q_deleteprinterdata(const char *desc, SPOOL_Q_DELETEPRINTERDATA *q_u, prs_struct *ps, int depth)
1315 {
1316         if (q_u == NULL)
1317                 return False;
1318
1319         prs_debug(ps, depth, desc, "spoolss_io_q_deleteprinterdata");
1320         depth++;
1321
1322         if (!prs_align(ps))
1323                 return False;
1324         if (!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
1325                 return False;
1326         if (!prs_align(ps))
1327                 return False;
1328         if (!smb_io_unistr2("valuename", &q_u->valuename,True,ps,depth))
1329                 return False;
1330
1331         return True;
1332 }
1333
1334 /*******************************************************************
1335  * write a structure.
1336  * called from spoolss_r_deleteprinterdata (srv_spoolss.c)
1337  ********************************************************************/
1338
1339 BOOL spoolss_io_r_deleteprinterdata(const char *desc, SPOOL_R_DELETEPRINTERDATA *r_u, prs_struct *ps, int depth)
1340 {
1341         prs_debug(ps, depth, desc, "spoolss_io_r_deleteprinterdata");
1342         depth++;
1343         if(!prs_werror("status", ps, depth, &r_u->status))
1344                 return False;
1345
1346         return True;
1347 }
1348
1349 /*******************************************************************
1350  * read a structure.
1351  * called from spoolss_q_deleteprinterdataex (srv_spoolss.c)
1352  ********************************************************************/
1353
1354 BOOL spoolss_io_q_deleteprinterdataex(const char *desc, SPOOL_Q_DELETEPRINTERDATAEX *q_u, prs_struct *ps, int depth)
1355 {
1356         if (q_u == NULL)
1357                 return False;
1358
1359         prs_debug(ps, depth, desc, "spoolss_io_q_deleteprinterdataex");
1360         depth++;
1361
1362         if (!prs_align(ps))
1363                 return False;
1364         if (!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
1365                 return False;
1366         
1367         if (!smb_io_unistr2("keyname  ", &q_u->keyname, True, ps, depth))
1368                 return False;
1369         if (!smb_io_unistr2("valuename", &q_u->valuename, True, ps, depth))
1370                 return False;
1371
1372         return True;
1373 }
1374
1375 /*******************************************************************
1376  * write a structure.
1377  * called from spoolss_r_deleteprinterdataex (srv_spoolss.c)
1378  ********************************************************************/
1379
1380 BOOL spoolss_io_r_deleteprinterdataex(const char *desc, SPOOL_R_DELETEPRINTERDATAEX *r_u, prs_struct *ps, int depth)
1381 {
1382         prs_debug(ps, depth, desc, "spoolss_io_r_deleteprinterdataex");
1383         depth++;
1384         
1385         if(!prs_werror("status", ps, depth, &r_u->status))
1386                 return False;
1387
1388         return True;
1389 }
1390
1391 /*******************************************************************
1392  * write a structure.
1393  * called from spoolss_r_getprinterdata (srv_spoolss.c)
1394  ********************************************************************/
1395
1396 BOOL spoolss_io_r_getprinterdata(const char *desc, SPOOL_R_GETPRINTERDATA *r_u, prs_struct *ps, int depth)
1397 {
1398         if (r_u == NULL)
1399                 return False;
1400
1401         prs_debug(ps, depth, desc, "spoolss_io_r_getprinterdata");
1402         depth++;
1403
1404         if (!prs_align(ps))
1405                 return False;
1406         if (!prs_uint32("type", ps, depth, &r_u->type))
1407                 return False;
1408         if (!prs_uint32("size", ps, depth, &r_u->size))
1409                 return False;
1410         
1411         if (UNMARSHALLING(ps) && r_u->size) {
1412                 r_u->data = PRS_ALLOC_MEM(ps, unsigned char, r_u->size);
1413                 if(!r_u->data)
1414                         return False;
1415         }
1416
1417         if (!prs_uint8s( False, "data", ps, depth, r_u->data, r_u->size ))
1418                 return False;
1419                 
1420         if (!prs_align(ps))
1421                 return False;
1422         
1423         if (!prs_uint32("needed", ps, depth, &r_u->needed))
1424                 return False;
1425         if (!prs_werror("status", ps, depth, &r_u->status))
1426                 return False;
1427                 
1428         return True;
1429 }
1430
1431 /*******************************************************************
1432  * make a structure.
1433  ********************************************************************/
1434
1435 BOOL make_spoolss_q_closeprinter(SPOOL_Q_CLOSEPRINTER *q_u, POLICY_HND *hnd)
1436 {
1437         if (q_u == NULL) return False;
1438
1439         DEBUG(5,("make_spoolss_q_closeprinter\n"));
1440
1441         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
1442
1443         return True;
1444 }
1445
1446 /*******************************************************************
1447  * read a structure.
1448  * called from static spoolss_q_abortprinter (srv_spoolss.c)
1449  * called from spoolss_abortprinter (cli_spoolss.c)
1450  ********************************************************************/
1451
1452 BOOL spoolss_io_q_abortprinter(const char *desc, SPOOL_Q_ABORTPRINTER *q_u, prs_struct *ps, int depth)
1453 {
1454         if (q_u == NULL) return False;
1455
1456         prs_debug(ps, depth, desc, "spoolss_io_q_abortprinter");
1457         depth++;
1458
1459         if (!prs_align(ps))
1460                 return False;
1461
1462         if (!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
1463                 return False;
1464
1465         return True;
1466 }
1467
1468 /*******************************************************************
1469  * write a structure.
1470  * called from spoolss_r_abortprinter (srv_spoolss.c)
1471  ********************************************************************/
1472
1473 BOOL spoolss_io_r_abortprinter(const char *desc, SPOOL_R_ABORTPRINTER *r_u, prs_struct *ps, int depth)
1474 {
1475         prs_debug(ps, depth, desc, "spoolss_io_r_abortprinter");
1476         depth++;
1477         if(!prs_werror("status", ps, depth, &r_u->status))
1478                 return False;
1479
1480         return True;
1481 }
1482
1483 /*******************************************************************
1484  * read a structure.
1485  * called from static spoolss_q_deleteprinter (srv_spoolss.c)
1486  * called from spoolss_deleteprinter (cli_spoolss.c)
1487  ********************************************************************/
1488
1489 BOOL spoolss_io_q_deleteprinter(const char *desc, SPOOL_Q_DELETEPRINTER *q_u, prs_struct *ps, int depth)
1490 {
1491         if (q_u == NULL) return False;
1492
1493         prs_debug(ps, depth, desc, "spoolss_io_q_deleteprinter");
1494         depth++;
1495
1496         if (!prs_align(ps))
1497                 return False;
1498
1499         if (!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
1500                 return False;
1501
1502         return True;
1503 }
1504
1505 /*******************************************************************
1506  * write a structure.
1507  * called from static spoolss_r_deleteprinter (srv_spoolss.c)
1508  * called from spoolss_deleteprinter (cli_spoolss.c)
1509  ********************************************************************/
1510
1511 BOOL spoolss_io_r_deleteprinter(const char *desc, SPOOL_R_DELETEPRINTER *r_u, prs_struct *ps, int depth)
1512 {
1513         prs_debug(ps, depth, desc, "spoolss_io_r_deleteprinter");
1514         depth++;
1515         
1516         if (!prs_align(ps))
1517                 return False;
1518
1519         if (!smb_io_pol_hnd("printer handle",&r_u->handle,ps,depth))
1520                 return False;
1521         if (!prs_werror("status", ps, depth, &r_u->status))
1522                 return False;
1523         
1524         return True;
1525 }
1526
1527
1528 /*******************************************************************
1529  * read a structure.
1530  * called from api_spoolss_deleteprinterdriver (srv_spoolss.c)
1531  * called from spoolss_deleteprinterdriver (cli_spoolss.c)
1532  ********************************************************************/
1533
1534 BOOL spoolss_io_q_deleteprinterdriver(const char *desc, SPOOL_Q_DELETEPRINTERDRIVER *q_u, prs_struct *ps, int depth)
1535 {
1536         if (q_u == NULL) return False;
1537
1538         prs_debug(ps, depth, desc, "spoolss_io_q_deleteprinterdriver");
1539         depth++;
1540
1541         if (!prs_align(ps))
1542                 return False;
1543
1544         if(!prs_uint32("server_ptr", ps, depth, &q_u->server_ptr))
1545                 return False;           
1546         if(!smb_io_unistr2("server", &q_u->server, q_u->server_ptr, ps, depth))
1547                 return False;
1548         if(!smb_io_unistr2("arch", &q_u->arch, True, ps, depth))
1549                 return False;
1550         if(!smb_io_unistr2("driver", &q_u->driver, True, ps, depth))
1551                 return False;
1552
1553
1554         return True;
1555 }
1556
1557
1558 /*******************************************************************
1559  * write a structure.
1560  ********************************************************************/
1561 BOOL spoolss_io_r_deleteprinterdriver(const char *desc, SPOOL_R_DELETEPRINTERDRIVER *r_u, prs_struct *ps, int depth)
1562 {
1563         if (r_u == NULL) return False;
1564
1565         prs_debug(ps, depth, desc, "spoolss_io_r_deleteprinterdriver");
1566         depth++;
1567
1568         if (!prs_align(ps))
1569                 return False;
1570
1571         if (!prs_werror("status", ps, depth, &r_u->status))
1572                 return False;
1573
1574         return True;
1575 }
1576
1577
1578 /*******************************************************************
1579  * read a structure.
1580  * called from api_spoolss_deleteprinterdriver (srv_spoolss.c)
1581  * called from spoolss_deleteprinterdriver (cli_spoolss.c)
1582  ********************************************************************/
1583
1584 BOOL spoolss_io_q_deleteprinterdriverex(const char *desc, SPOOL_Q_DELETEPRINTERDRIVEREX *q_u, prs_struct *ps, int depth)
1585 {
1586         if (q_u == NULL) return False;
1587
1588         prs_debug(ps, depth, desc, "spoolss_io_q_deleteprinterdriverex");
1589         depth++;
1590
1591         if (!prs_align(ps))
1592                 return False;
1593
1594         if(!prs_uint32("server_ptr", ps, depth, &q_u->server_ptr))
1595                 return False;           
1596         if(!smb_io_unistr2("server", &q_u->server, q_u->server_ptr, ps, depth))
1597                 return False;
1598         if(!smb_io_unistr2("arch", &q_u->arch, True, ps, depth))
1599                 return False;
1600         if(!smb_io_unistr2("driver", &q_u->driver, True, ps, depth))
1601                 return False;
1602
1603         if (!prs_align(ps))
1604                 return False;
1605
1606         if(!prs_uint32("delete_flags ", ps, depth, &q_u->delete_flags))
1607                 return False;           
1608         if(!prs_uint32("version      ", ps, depth, &q_u->version))
1609                 return False;           
1610
1611
1612         return True;
1613 }
1614
1615
1616 /*******************************************************************
1617  * write a structure.
1618  ********************************************************************/
1619 BOOL spoolss_io_r_deleteprinterdriverex(const char *desc, SPOOL_R_DELETEPRINTERDRIVEREX *r_u, prs_struct *ps, int depth)
1620 {
1621         if (r_u == NULL) return False;
1622
1623         prs_debug(ps, depth, desc, "spoolss_io_r_deleteprinterdriverex");
1624         depth++;
1625
1626         if (!prs_align(ps))
1627                 return False;
1628
1629         if (!prs_werror("status", ps, depth, &r_u->status))
1630                 return False;
1631
1632         return True;
1633 }
1634
1635
1636
1637 /*******************************************************************
1638  * read a structure.
1639  * called from static spoolss_q_closeprinter (srv_spoolss.c)
1640  * called from spoolss_closeprinter (cli_spoolss.c)
1641  ********************************************************************/
1642
1643 BOOL spoolss_io_q_closeprinter(const char *desc, SPOOL_Q_CLOSEPRINTER *q_u, prs_struct *ps, int depth)
1644 {
1645         if (q_u == NULL) return False;
1646
1647         prs_debug(ps, depth, desc, "spoolss_io_q_closeprinter");
1648         depth++;
1649
1650         if (!prs_align(ps))
1651                 return False;
1652
1653         if (!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
1654                 return False;
1655
1656         return True;
1657 }
1658
1659 /*******************************************************************
1660  * write a structure.
1661  * called from static spoolss_r_closeprinter (srv_spoolss.c)
1662  * called from spoolss_closeprinter (cli_spoolss.c)
1663  ********************************************************************/
1664
1665 BOOL spoolss_io_r_closeprinter(const char *desc, SPOOL_R_CLOSEPRINTER *r_u, prs_struct *ps, int depth)
1666 {
1667         prs_debug(ps, depth, desc, "spoolss_io_r_closeprinter");
1668         depth++;
1669         
1670         if (!prs_align(ps))
1671                 return False;
1672
1673         if (!smb_io_pol_hnd("printer handle",&r_u->handle,ps,depth))
1674                 return False;
1675         if (!prs_werror("status", ps, depth, &r_u->status))
1676                 return False;
1677         
1678         return True;
1679 }
1680
1681 /*******************************************************************
1682  * read a structure.
1683  * called from spoolss_q_startdocprinter (srv_spoolss.c)
1684  ********************************************************************/
1685
1686 BOOL spoolss_io_q_startdocprinter(const char *desc, SPOOL_Q_STARTDOCPRINTER *q_u, prs_struct *ps, int depth)
1687 {
1688         if (q_u == NULL) return False;
1689
1690         prs_debug(ps, depth, desc, "spoolss_io_q_startdocprinter");
1691         depth++;
1692
1693         if(!prs_align(ps))
1694                 return False;
1695
1696         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
1697                 return False;
1698         
1699         if(!smb_io_doc_info_container("",&q_u->doc_info_container, ps, depth))
1700                 return False;
1701
1702         return True;
1703 }
1704
1705 /*******************************************************************
1706  * write a structure.
1707  * called from spoolss_r_startdocprinter (srv_spoolss.c)
1708  ********************************************************************/
1709
1710 BOOL spoolss_io_r_startdocprinter(const char *desc, SPOOL_R_STARTDOCPRINTER *r_u, prs_struct *ps, int depth)
1711 {
1712         prs_debug(ps, depth, desc, "spoolss_io_r_startdocprinter");
1713         depth++;
1714         if(!prs_uint32("jobid", ps, depth, &r_u->jobid))
1715                 return False;
1716         if(!prs_werror("status", ps, depth, &r_u->status))
1717                 return False;
1718
1719         return True;
1720 }
1721
1722 /*******************************************************************
1723  * read a structure.
1724  * called from spoolss_q_enddocprinter (srv_spoolss.c)
1725  ********************************************************************/
1726
1727 BOOL spoolss_io_q_enddocprinter(const char *desc, SPOOL_Q_ENDDOCPRINTER *q_u, prs_struct *ps, int depth)
1728 {
1729         if (q_u == NULL) return False;
1730
1731         prs_debug(ps, depth, desc, "spoolss_io_q_enddocprinter");
1732         depth++;
1733
1734         if(!prs_align(ps))
1735                 return False;
1736
1737         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
1738                 return False;
1739
1740         return True;
1741 }
1742
1743 /*******************************************************************
1744  * write a structure.
1745  * called from spoolss_r_enddocprinter (srv_spoolss.c)
1746  ********************************************************************/
1747
1748 BOOL spoolss_io_r_enddocprinter(const char *desc, SPOOL_R_ENDDOCPRINTER *r_u, prs_struct *ps, int depth)
1749 {
1750         prs_debug(ps, depth, desc, "spoolss_io_r_enddocprinter");
1751         depth++;
1752         if(!prs_werror("status", ps, depth, &r_u->status))
1753                 return False;
1754
1755         return True;
1756 }
1757
1758 /*******************************************************************
1759  * read a structure.
1760  * called from spoolss_q_startpageprinter (srv_spoolss.c)
1761  ********************************************************************/
1762
1763 BOOL spoolss_io_q_startpageprinter(const char *desc, SPOOL_Q_STARTPAGEPRINTER *q_u, prs_struct *ps, int depth)
1764 {
1765         if (q_u == NULL) return False;
1766
1767         prs_debug(ps, depth, desc, "spoolss_io_q_startpageprinter");
1768         depth++;
1769
1770         if(!prs_align(ps))
1771                 return False;
1772
1773         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
1774                 return False;
1775
1776         return True;
1777 }
1778
1779 /*******************************************************************
1780  * write a structure.
1781  * called from spoolss_r_startpageprinter (srv_spoolss.c)
1782  ********************************************************************/
1783
1784 BOOL spoolss_io_r_startpageprinter(const char *desc, SPOOL_R_STARTPAGEPRINTER *r_u, prs_struct *ps, int depth)
1785 {
1786         prs_debug(ps, depth, desc, "spoolss_io_r_startpageprinter");
1787         depth++;
1788         if(!prs_werror("status", ps, depth, &r_u->status))
1789                 return False;
1790
1791         return True;
1792 }
1793
1794 /*******************************************************************
1795  * read a structure.
1796  * called from spoolss_q_endpageprinter (srv_spoolss.c)
1797  ********************************************************************/
1798
1799 BOOL spoolss_io_q_endpageprinter(const char *desc, SPOOL_Q_ENDPAGEPRINTER *q_u, prs_struct *ps, int depth)
1800 {
1801         if (q_u == NULL) return False;
1802
1803         prs_debug(ps, depth, desc, "spoolss_io_q_endpageprinter");
1804         depth++;
1805
1806         if(!prs_align(ps))
1807                 return False;
1808
1809         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
1810                 return False;
1811
1812         return True;
1813 }
1814
1815 /*******************************************************************
1816  * write a structure.
1817  * called from spoolss_r_endpageprinter (srv_spoolss.c)
1818  ********************************************************************/
1819
1820 BOOL spoolss_io_r_endpageprinter(const char *desc, SPOOL_R_ENDPAGEPRINTER *r_u, prs_struct *ps, int depth)
1821 {
1822         prs_debug(ps, depth, desc, "spoolss_io_r_endpageprinter");
1823         depth++;
1824         if(!prs_werror("status", ps, depth, &r_u->status))
1825                 return False;
1826
1827         return True;
1828 }
1829
1830 /*******************************************************************
1831  * read a structure.
1832  * called from spoolss_q_writeprinter (srv_spoolss.c)
1833  ********************************************************************/
1834
1835 BOOL spoolss_io_q_writeprinter(const char *desc, SPOOL_Q_WRITEPRINTER *q_u, prs_struct *ps, int depth)
1836 {
1837         if (q_u == NULL) return False;
1838
1839         prs_debug(ps, depth, desc, "spoolss_io_q_writeprinter");
1840         depth++;
1841
1842         if(!prs_align(ps))
1843                 return False;
1844
1845         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
1846                 return False;
1847         if(!prs_uint32("buffer_size", ps, depth, &q_u->buffer_size))
1848                 return False;
1849         
1850         if (q_u->buffer_size!=0)
1851         {
1852                 if (UNMARSHALLING(ps))
1853                         q_u->buffer=PRS_ALLOC_MEM(ps, uint8, q_u->buffer_size);
1854                 if(q_u->buffer == NULL)
1855                         return False;   
1856                 if(!prs_uint8s(True, "buffer", ps, depth, q_u->buffer, q_u->buffer_size))
1857                         return False;
1858         }
1859         if(!prs_align(ps))
1860                 return False;
1861         if(!prs_uint32("buffer_size2", ps, depth, &q_u->buffer_size2))
1862                 return False;
1863
1864         return True;
1865 }
1866
1867 /*******************************************************************
1868  * write a structure.
1869  * called from spoolss_r_writeprinter (srv_spoolss.c)
1870  ********************************************************************/
1871
1872 BOOL spoolss_io_r_writeprinter(const char *desc, SPOOL_R_WRITEPRINTER *r_u, prs_struct *ps, int depth)
1873 {
1874         prs_debug(ps, depth, desc, "spoolss_io_r_writeprinter");
1875         depth++;
1876         if(!prs_uint32("buffer_written", ps, depth, &r_u->buffer_written))
1877                 return False;
1878         if(!prs_werror("status", ps, depth, &r_u->status))
1879                 return False;
1880
1881         return True;
1882 }
1883
1884 /*******************************************************************
1885  * read a structure.
1886  * called from spoolss_q_rffpcnex (srv_spoolss.c)
1887  ********************************************************************/
1888
1889 BOOL spoolss_io_q_rffpcnex(const char *desc, SPOOL_Q_RFFPCNEX *q_u, prs_struct *ps, int depth)
1890 {
1891         prs_debug(ps, depth, desc, "spoolss_io_q_rffpcnex");
1892         depth++;
1893
1894         if(!prs_align(ps))
1895                 return False;
1896
1897         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
1898                 return False;
1899         if(!prs_uint32("flags", ps, depth, &q_u->flags))
1900                 return False;
1901         if(!prs_uint32("options", ps, depth, &q_u->options))
1902                 return False;
1903         if(!prs_uint32("localmachine_ptr", ps, depth, &q_u->localmachine_ptr))
1904                 return False;
1905         if(!smb_io_unistr2("localmachine", &q_u->localmachine, q_u->localmachine_ptr, ps, depth))
1906                 return False;
1907
1908         if(!prs_align(ps))
1909                 return False;
1910                 
1911         if(!prs_uint32("printerlocal", ps, depth, &q_u->printerlocal))
1912                 return False;
1913
1914         if(!prs_uint32("option_ptr", ps, depth, &q_u->option_ptr))
1915                 return False;
1916         
1917         if (q_u->option_ptr!=0) {
1918         
1919                 if (UNMARSHALLING(ps))
1920                         if((q_u->option=PRS_ALLOC_MEM(ps,SPOOL_NOTIFY_OPTION,1)) == NULL)
1921                                 return False;
1922         
1923                 if(!smb_io_notify_option("notify option", q_u->option, ps, depth))
1924                         return False;
1925         }
1926         
1927         return True;
1928 }
1929
1930 /*******************************************************************
1931  * write a structure.
1932  * called from spoolss_r_rffpcnex (srv_spoolss.c)
1933  ********************************************************************/
1934
1935 BOOL spoolss_io_r_rffpcnex(const char *desc, SPOOL_R_RFFPCNEX *r_u, prs_struct *ps, int depth)
1936 {
1937         prs_debug(ps, depth, desc, "spoolss_io_r_rffpcnex");
1938         depth++;
1939
1940         if(!prs_werror("status", ps, depth, &r_u->status))
1941                 return False;
1942
1943         return True;
1944 }
1945
1946 /*******************************************************************
1947  * read a structure.
1948  * called from spoolss_q_rfnpcnex (srv_spoolss.c)
1949  ********************************************************************/
1950
1951 BOOL spoolss_io_q_rfnpcnex(const char *desc, SPOOL_Q_RFNPCNEX *q_u, prs_struct *ps, int depth)
1952 {
1953         prs_debug(ps, depth, desc, "spoolss_io_q_rfnpcnex");
1954         depth++;
1955
1956         if(!prs_align(ps))
1957                 return False;
1958
1959         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
1960                 return False;
1961
1962         if(!prs_uint32("change", ps, depth, &q_u->change))
1963                 return False;
1964         
1965         if(!prs_uint32("option_ptr", ps, depth, &q_u->option_ptr))
1966                 return False;
1967         
1968         if (q_u->option_ptr!=0) {
1969         
1970                 if (UNMARSHALLING(ps))
1971                         if((q_u->option=PRS_ALLOC_MEM(ps,SPOOL_NOTIFY_OPTION,1)) == NULL)
1972                                 return False;
1973         
1974                 if(!smb_io_notify_option("notify option", q_u->option, ps, depth))
1975                         return False;
1976         }
1977
1978         return True;
1979 }
1980
1981 /*******************************************************************
1982  * write a structure.
1983  * called from spoolss_r_rfnpcnex (srv_spoolss.c)
1984  ********************************************************************/
1985
1986 BOOL spoolss_io_r_rfnpcnex(const char *desc, SPOOL_R_RFNPCNEX *r_u, prs_struct *ps, int depth)
1987 {
1988         prs_debug(ps, depth, desc, "spoolss_io_r_rfnpcnex");
1989         depth++;
1990
1991         if(!prs_align(ps))
1992                 return False;
1993                 
1994         if (!prs_uint32("info_ptr", ps, depth, &r_u->info_ptr))
1995                 return False;
1996
1997         if(!smb_io_notify_info("notify info", &r_u->info ,ps,depth))
1998                 return False;
1999         
2000         if(!prs_align(ps))
2001                 return False;
2002         if(!prs_werror("status", ps, depth, &r_u->status))
2003                 return False;
2004
2005         return True;
2006 }
2007
2008 /*******************************************************************
2009  * return the length of a uint16 (obvious, but the code is clean)
2010  ********************************************************************/
2011
2012 static uint32 size_of_uint16(uint16 *value)
2013 {
2014         return (sizeof(*value));
2015 }
2016
2017 /*******************************************************************
2018  * return the length of a uint32 (obvious, but the code is clean)
2019  ********************************************************************/
2020
2021 static uint32 size_of_uint32(uint32 *value)
2022 {
2023         return (sizeof(*value));
2024 }
2025
2026 /*******************************************************************
2027  * return the length of a NTTIME (obvious, but the code is clean)
2028  ********************************************************************/
2029
2030 static uint32 size_of_nttime(NTTIME *value)
2031 {
2032         return (sizeof(*value));
2033 }
2034
2035 /*******************************************************************
2036  * return the length of a uint32 (obvious, but the code is clean)
2037  ********************************************************************/
2038
2039 static uint32 size_of_device_mode(DEVICEMODE *devmode)
2040 {
2041         if (devmode==NULL)
2042                 return (4);
2043         else 
2044                 return (4+devmode->size+devmode->driverextra);
2045 }
2046
2047 /*******************************************************************
2048  * return the length of a uint32 (obvious, but the code is clean)
2049  ********************************************************************/
2050
2051 static uint32 size_of_systemtime(SYSTEMTIME *systime)
2052 {
2053         if (systime==NULL)
2054                 return (4);
2055         else 
2056                 return (sizeof(SYSTEMTIME) +4);
2057 }
2058
2059 /*******************************************************************
2060  Parse a DEVMODE structure and its relative pointer.
2061 ********************************************************************/
2062
2063 static BOOL smb_io_reldevmode(const char *desc, RPC_BUFFER *buffer, int depth, DEVICEMODE **devmode)
2064 {
2065         prs_struct *ps=&buffer->prs;
2066
2067         prs_debug(ps, depth, desc, "smb_io_reldevmode");
2068         depth++;
2069
2070         if (MARSHALLING(ps)) {
2071                 uint32 struct_offset = prs_offset(ps);
2072                 uint32 relative_offset;
2073                 
2074                 if (*devmode == NULL) {
2075                         relative_offset=0;
2076                         if (!prs_uint32("offset", ps, depth, &relative_offset))
2077                                 return False;
2078                         DEBUG(8, ("boing, the devmode was NULL\n"));
2079                         
2080                         return True;
2081                 }
2082                 
2083                 buffer->string_at_end -= ((*devmode)->size + (*devmode)->driverextra);
2084                 
2085                 if(!prs_set_offset(ps, buffer->string_at_end))
2086                         return False;
2087                 
2088                 /* write the DEVMODE */
2089                 if (!spoolss_io_devmode(desc, ps, depth, *devmode))
2090                         return False;
2091
2092                 if(!prs_set_offset(ps, struct_offset))
2093                         return False;
2094                 
2095                 relative_offset=buffer->string_at_end - buffer->struct_start;
2096                 /* write its offset */
2097                 if (!prs_uint32("offset", ps, depth, &relative_offset))
2098                         return False;
2099         }
2100         else {
2101                 uint32 old_offset;
2102                 
2103                 /* read the offset */
2104                 if (!prs_uint32("offset", ps, depth, &buffer->string_at_end))
2105                         return False;
2106                 if (buffer->string_at_end == 0) {
2107                         *devmode = NULL;
2108                         return True;
2109                 }
2110
2111                 old_offset = prs_offset(ps);
2112                 if(!prs_set_offset(ps, buffer->string_at_end + buffer->struct_start))
2113                         return False;
2114
2115                 /* read the string */
2116                 if((*devmode=PRS_ALLOC_MEM(ps,DEVICEMODE,1)) == NULL)
2117                         return False;
2118                 if (!spoolss_io_devmode(desc, ps, depth, *devmode))
2119                         return False;
2120
2121                 if(!prs_set_offset(ps, old_offset))
2122                         return False;
2123         }
2124         return True;
2125 }
2126
2127 /*******************************************************************
2128  Parse a PRINTER_INFO_0 structure.
2129 ********************************************************************/  
2130
2131 BOOL smb_io_printer_info_0(const char *desc, RPC_BUFFER *buffer, PRINTER_INFO_0 *info, int depth)
2132 {
2133         prs_struct *ps=&buffer->prs;
2134
2135         prs_debug(ps, depth, desc, "smb_io_printer_info_0");
2136         depth++;        
2137         
2138         buffer->struct_start=prs_offset(ps);
2139
2140         if (!smb_io_relstr("printername", buffer, depth, &info->printername))
2141                 return False;
2142         if (!smb_io_relstr("servername", buffer, depth, &info->servername))
2143                 return False;
2144         
2145         if(!prs_uint32("cjobs", ps, depth, &info->cjobs))
2146                 return False;
2147         if(!prs_uint32("total_jobs", ps, depth, &info->total_jobs))
2148                 return False;
2149         if(!prs_uint32("total_bytes", ps, depth, &info->total_bytes))
2150                 return False;
2151
2152         if(!prs_uint16("year", ps, depth, &info->year))
2153                 return False;
2154         if(!prs_uint16("month", ps, depth, &info->month))
2155                 return False;
2156         if(!prs_uint16("dayofweek", ps, depth, &info->dayofweek))
2157                 return False;
2158         if(!prs_uint16("day", ps, depth, &info->day))
2159                 return False;
2160         if(!prs_uint16("hour", ps, depth, &info->hour))
2161                 return False;
2162         if(!prs_uint16("minute", ps, depth, &info->minute))
2163                 return False;
2164         if(!prs_uint16("second", ps, depth, &info->second))
2165                 return False;
2166         if(!prs_uint16("milliseconds", ps, depth, &info->milliseconds))
2167                 return False;
2168
2169         if(!prs_uint32("global_counter", ps, depth, &info->global_counter))
2170                 return False;
2171         if(!prs_uint32("total_pages", ps, depth, &info->total_pages))
2172                 return False;
2173
2174         if(!prs_uint16("major_version", ps, depth, &info->major_version))
2175                 return False;
2176         if(!prs_uint16("build_version", ps, depth, &info->build_version))
2177                 return False;
2178         if(!prs_uint32("unknown7", ps, depth, &info->unknown7))
2179                 return False;
2180         if(!prs_uint32("unknown8", ps, depth, &info->unknown8))
2181                 return False;
2182         if(!prs_uint32("unknown9", ps, depth, &info->unknown9))
2183                 return False;
2184         if(!prs_uint32("session_counter", ps, depth, &info->session_counter))
2185                 return False;
2186         if(!prs_uint32("unknown11", ps, depth, &info->unknown11))
2187                 return False;
2188         if(!prs_uint32("printer_errors", ps, depth, &info->printer_errors))
2189                 return False;
2190         if(!prs_uint32("unknown13", ps, depth, &info->unknown13))
2191                 return False;
2192         if(!prs_uint32("unknown14", ps, depth, &info->unknown14))
2193                 return False;
2194         if(!prs_uint32("unknown15", ps, depth, &info->unknown15))
2195                 return False;
2196         if(!prs_uint32("unknown16", ps, depth, &info->unknown16))
2197                 return False;
2198         if(!prs_uint32("change_id", ps, depth, &info->change_id))
2199                 return False;
2200         if(!prs_uint32("unknown18", ps, depth, &info->unknown18))
2201                 return False;
2202         if(!prs_uint32("status"   , ps, depth, &info->status))
2203                 return False;
2204         if(!prs_uint32("unknown20", ps, depth, &info->unknown20))
2205                 return False;
2206         if(!prs_uint32("c_setprinter", ps, depth, &info->c_setprinter))
2207                 return False;
2208         if(!prs_uint16("unknown22", ps, depth, &info->unknown22))
2209                 return False;
2210         if(!prs_uint16("unknown23", ps, depth, &info->unknown23))
2211                 return False;
2212         if(!prs_uint16("unknown24", ps, depth, &info->unknown24))
2213                 return False;
2214         if(!prs_uint16("unknown25", ps, depth, &info->unknown25))
2215                 return False;
2216         if(!prs_uint16("unknown26", ps, depth, &info->unknown26))
2217                 return False;
2218         if(!prs_uint16("unknown27", ps, depth, &info->unknown27))
2219                 return False;
2220         if(!prs_uint16("unknown28", ps, depth, &info->unknown28))
2221                 return False;
2222         if(!prs_uint16("unknown29", ps, depth, &info->unknown29))
2223                 return False;
2224
2225         return True;
2226 }
2227
2228 /*******************************************************************
2229  Parse a PRINTER_INFO_1 structure.
2230 ********************************************************************/  
2231
2232 BOOL smb_io_printer_info_1(const char *desc, RPC_BUFFER *buffer, PRINTER_INFO_1 *info, int depth)
2233 {
2234         prs_struct *ps=&buffer->prs;
2235
2236         prs_debug(ps, depth, desc, "smb_io_printer_info_1");
2237         depth++;        
2238         
2239         buffer->struct_start=prs_offset(ps);
2240
2241         if (!prs_uint32("flags", ps, depth, &info->flags))
2242                 return False;
2243         if (!smb_io_relstr("description", buffer, depth, &info->description))
2244                 return False;
2245         if (!smb_io_relstr("name", buffer, depth, &info->name))
2246                 return False;
2247         if (!smb_io_relstr("comment", buffer, depth, &info->comment))
2248                 return False;   
2249
2250         return True;
2251 }
2252
2253 /*******************************************************************
2254  Parse a PRINTER_INFO_2 structure.
2255 ********************************************************************/  
2256
2257 BOOL smb_io_printer_info_2(const char *desc, RPC_BUFFER *buffer, PRINTER_INFO_2 *info, int depth)
2258 {
2259         prs_struct *ps=&buffer->prs;
2260         uint32 dm_offset, sd_offset, current_offset;
2261         uint32 dummy_value = 0, has_secdesc = 0;
2262
2263         prs_debug(ps, depth, desc, "smb_io_printer_info_2");
2264         depth++;        
2265         
2266         buffer->struct_start=prs_offset(ps);
2267         
2268         if (!smb_io_relstr("servername", buffer, depth, &info->servername))
2269                 return False;
2270         if (!smb_io_relstr("printername", buffer, depth, &info->printername))
2271                 return False;
2272         if (!smb_io_relstr("sharename", buffer, depth, &info->sharename))
2273                 return False;
2274         if (!smb_io_relstr("portname", buffer, depth, &info->portname))
2275                 return False;
2276         if (!smb_io_relstr("drivername", buffer, depth, &info->drivername))
2277                 return False;
2278         if (!smb_io_relstr("comment", buffer, depth, &info->comment))
2279                 return False;
2280         if (!smb_io_relstr("location", buffer, depth, &info->location))
2281                 return False;
2282
2283         /* save current offset and wind forwared by a uint32 */
2284         dm_offset = prs_offset(ps);
2285         if (!prs_uint32("devmode", ps, depth, &dummy_value))
2286                 return False;
2287         
2288         if (!smb_io_relstr("sepfile", buffer, depth, &info->sepfile))
2289                 return False;
2290         if (!smb_io_relstr("printprocessor", buffer, depth, &info->printprocessor))
2291                 return False;
2292         if (!smb_io_relstr("datatype", buffer, depth, &info->datatype))
2293                 return False;
2294         if (!smb_io_relstr("parameters", buffer, depth, &info->parameters))
2295                 return False;
2296
2297         /* save current offset for the sec_desc */
2298         sd_offset = prs_offset(ps);
2299         if (!prs_uint32("sec_desc", ps, depth, &has_secdesc))
2300                 return False;
2301
2302         
2303         /* save current location so we can pick back up here */
2304         current_offset = prs_offset(ps);
2305         
2306         /* parse the devmode */
2307         if (!prs_set_offset(ps, dm_offset))
2308                 return False;
2309         if (!smb_io_reldevmode("devmode", buffer, depth, &info->devmode))
2310                 return False;
2311         
2312         /* parse the sec_desc */
2313         if (info->secdesc) {
2314                 if (!prs_set_offset(ps, sd_offset))
2315                         return False;
2316                 if (!smb_io_relsecdesc("secdesc", buffer, depth, &info->secdesc))
2317                         return False;
2318         }
2319
2320         /* pick up where we left off */
2321         if (!prs_set_offset(ps, current_offset))
2322                 return False;
2323
2324         if (!prs_uint32("attributes", ps, depth, &info->attributes))
2325                 return False;
2326         if (!prs_uint32("priority", ps, depth, &info->priority))
2327                 return False;
2328         if (!prs_uint32("defpriority", ps, depth, &info->defaultpriority))
2329                 return False;
2330         if (!prs_uint32("starttime", ps, depth, &info->starttime))
2331                 return False;
2332         if (!prs_uint32("untiltime", ps, depth, &info->untiltime))
2333                 return False;
2334         if (!prs_uint32("status", ps, depth, &info->status))
2335                 return False;
2336         if (!prs_uint32("jobs", ps, depth, &info->cjobs))
2337                 return False;
2338         if (!prs_uint32("averageppm", ps, depth, &info->averageppm))
2339                 return False;
2340
2341         return True;
2342 }
2343
2344 /*******************************************************************
2345  Parse a PRINTER_INFO_3 structure.
2346 ********************************************************************/  
2347
2348 BOOL smb_io_printer_info_3(const char *desc, RPC_BUFFER *buffer, PRINTER_INFO_3 *info, int depth)
2349 {
2350         prs_struct *ps=&buffer->prs;
2351
2352         prs_debug(ps, depth, desc, "smb_io_printer_info_3");
2353         depth++;        
2354         
2355         buffer->struct_start=prs_offset(ps);
2356         
2357         if (!prs_uint32("flags", ps, depth, &info->flags))
2358                 return False;
2359         if (!sec_io_desc("sec_desc", &info->secdesc, ps, depth))
2360                 return False;
2361
2362         return True;
2363 }
2364
2365 /*******************************************************************
2366  Parse a PRINTER_INFO_4 structure.
2367 ********************************************************************/  
2368
2369 BOOL smb_io_printer_info_4(const char *desc, RPC_BUFFER *buffer, PRINTER_INFO_4 *info, int depth)
2370 {
2371         prs_struct *ps=&buffer->prs;
2372
2373         prs_debug(ps, depth, desc, "smb_io_printer_info_4");
2374         depth++;        
2375         
2376         buffer->struct_start=prs_offset(ps);
2377         
2378         if (!smb_io_relstr("printername", buffer, depth, &info->printername))
2379                 return False;
2380         if (!smb_io_relstr("servername", buffer, depth, &info->servername))
2381                 return False;
2382         if (!prs_uint32("attributes", ps, depth, &info->attributes))
2383                 return False;
2384         return True;
2385 }
2386
2387 /*******************************************************************
2388  Parse a PRINTER_INFO_5 structure.
2389 ********************************************************************/  
2390
2391 BOOL smb_io_printer_info_5(const char *desc, RPC_BUFFER *buffer, PRINTER_INFO_5 *info, int depth)
2392 {
2393         prs_struct *ps=&buffer->prs;
2394
2395         prs_debug(ps, depth, desc, "smb_io_printer_info_5");
2396         depth++;        
2397         
2398         buffer->struct_start=prs_offset(ps);
2399         
2400         if (!smb_io_relstr("printername", buffer, depth, &info->printername))
2401                 return False;
2402         if (!smb_io_relstr("portname", buffer, depth, &info->portname))
2403                 return False;
2404         if (!prs_uint32("attributes", ps, depth, &info->attributes))
2405                 return False;
2406         if (!prs_uint32("device_not_selected_timeout", ps, depth, &info->device_not_selected_timeout))
2407                 return False;
2408         if (!prs_uint32("transmission_retry_timeout", ps, depth, &info->transmission_retry_timeout))
2409                 return False;
2410         return True;
2411 }
2412
2413 /*******************************************************************
2414  Parse a PRINTER_INFO_7 structure.
2415 ********************************************************************/  
2416
2417 BOOL smb_io_printer_info_7(const char *desc, RPC_BUFFER *buffer, PRINTER_INFO_7 *info, int depth)
2418 {
2419         prs_struct *ps=&buffer->prs;
2420
2421         prs_debug(ps, depth, desc, "smb_io_printer_info_7");
2422         depth++;        
2423         
2424         buffer->struct_start=prs_offset(ps);
2425         
2426         if (!smb_io_relstr("guid", buffer, depth, &info->guid))
2427                 return False;
2428         if (!prs_uint32("action", ps, depth, &info->action))
2429                 return False;
2430         return True;
2431 }
2432
2433 /*******************************************************************
2434  Parse a PORT_INFO_1 structure.
2435 ********************************************************************/  
2436
2437 BOOL smb_io_port_info_1(const char *desc, RPC_BUFFER *buffer, PORT_INFO_1 *info, int depth)
2438 {
2439         prs_struct *ps=&buffer->prs;
2440
2441         prs_debug(ps, depth, desc, "smb_io_port_info_1");
2442         depth++;        
2443         
2444         buffer->struct_start=prs_offset(ps);
2445         
2446         if (!smb_io_relstr("port_name", buffer, depth, &info->port_name))
2447                 return False;
2448
2449         return True;
2450 }
2451
2452 /*******************************************************************
2453  Parse a PORT_INFO_2 structure.
2454 ********************************************************************/  
2455
2456 BOOL smb_io_port_info_2(const char *desc, RPC_BUFFER *buffer, PORT_INFO_2 *info, int depth)
2457 {
2458         prs_struct *ps=&buffer->prs;
2459
2460         prs_debug(ps, depth, desc, "smb_io_port_info_2");
2461         depth++;        
2462         
2463         buffer->struct_start=prs_offset(ps);
2464         
2465         if (!smb_io_relstr("port_name", buffer, depth, &info->port_name))
2466                 return False;
2467         if (!smb_io_relstr("monitor_name", buffer, depth, &info->monitor_name))
2468                 return False;
2469         if (!smb_io_relstr("description", buffer, depth, &info->description))
2470                 return False;
2471         if (!prs_uint32("port_type", ps, depth, &info->port_type))
2472                 return False;
2473         if (!prs_uint32("reserved", ps, depth, &info->reserved))
2474                 return False;
2475
2476         return True;
2477 }
2478
2479 /*******************************************************************
2480  Parse a DRIVER_INFO_1 structure.
2481 ********************************************************************/
2482
2483 BOOL smb_io_printer_driver_info_1(const char *desc, RPC_BUFFER *buffer, DRIVER_INFO_1 *info, int depth) 
2484 {
2485         prs_struct *ps=&buffer->prs;
2486
2487         prs_debug(ps, depth, desc, "smb_io_printer_driver_info_1");
2488         depth++;        
2489         
2490         buffer->struct_start=prs_offset(ps);
2491
2492         if (!smb_io_relstr("name", buffer, depth, &info->name))
2493                 return False;
2494
2495         return True;
2496 }
2497
2498 /*******************************************************************
2499  Parse a DRIVER_INFO_2 structure.
2500 ********************************************************************/
2501
2502 BOOL smb_io_printer_driver_info_2(const char *desc, RPC_BUFFER *buffer, DRIVER_INFO_2 *info, int depth) 
2503 {
2504         prs_struct *ps=&buffer->prs;
2505
2506         prs_debug(ps, depth, desc, "smb_io_printer_driver_info_2");
2507         depth++;        
2508         
2509         buffer->struct_start=prs_offset(ps);
2510
2511         if (!prs_uint32("version", ps, depth, &info->version))
2512                 return False;
2513         if (!smb_io_relstr("name", buffer, depth, &info->name))
2514                 return False;
2515         if (!smb_io_relstr("architecture", buffer, depth, &info->architecture))
2516                 return False;
2517         if (!smb_io_relstr("driverpath", buffer, depth, &info->driverpath))
2518                 return False;
2519         if (!smb_io_relstr("datafile", buffer, depth, &info->datafile))
2520                 return False;
2521         if (!smb_io_relstr("configfile", buffer, depth, &info->configfile))
2522                 return False;
2523
2524         return True;
2525 }
2526
2527 /*******************************************************************
2528  Parse a DRIVER_INFO_3 structure.
2529 ********************************************************************/
2530
2531 BOOL smb_io_printer_driver_info_3(const char *desc, RPC_BUFFER *buffer, DRIVER_INFO_3 *info, int depth)
2532 {
2533         prs_struct *ps=&buffer->prs;
2534
2535         prs_debug(ps, depth, desc, "smb_io_printer_driver_info_3");
2536         depth++;        
2537         
2538         buffer->struct_start=prs_offset(ps);
2539
2540         if (!prs_uint32("version", ps, depth, &info->version))
2541                 return False;
2542         if (!smb_io_relstr("name", buffer, depth, &info->name))
2543                 return False;
2544         if (!smb_io_relstr("architecture", buffer, depth, &info->architecture))
2545                 return False;
2546         if (!smb_io_relstr("driverpath", buffer, depth, &info->driverpath))
2547                 return False;
2548         if (!smb_io_relstr("datafile", buffer, depth, &info->datafile))
2549                 return False;
2550         if (!smb_io_relstr("configfile", buffer, depth, &info->configfile))
2551                 return False;
2552         if (!smb_io_relstr("helpfile", buffer, depth, &info->helpfile))
2553                 return False;
2554
2555         if (!smb_io_relarraystr("dependentfiles", buffer, depth, &info->dependentfiles))
2556                 return False;
2557
2558         if (!smb_io_relstr("monitorname", buffer, depth, &info->monitorname))
2559                 return False;
2560         if (!smb_io_relstr("defaultdatatype", buffer, depth, &info->defaultdatatype))
2561                 return False;
2562
2563         return True;
2564 }
2565
2566 /*******************************************************************
2567  Parse a DRIVER_INFO_6 structure.
2568 ********************************************************************/
2569
2570 BOOL smb_io_printer_driver_info_6(const char *desc, RPC_BUFFER *buffer, DRIVER_INFO_6 *info, int depth)
2571 {
2572         prs_struct *ps=&buffer->prs;
2573
2574         prs_debug(ps, depth, desc, "smb_io_printer_driver_info_6");
2575         depth++;        
2576         
2577         buffer->struct_start=prs_offset(ps);
2578
2579         if (!prs_uint32("version", ps, depth, &info->version))
2580                 return False;
2581         if (!smb_io_relstr("name", buffer, depth, &info->name))
2582                 return False;
2583         if (!smb_io_relstr("architecture", buffer, depth, &info->architecture))
2584                 return False;
2585         if (!smb_io_relstr("driverpath", buffer, depth, &info->driverpath))
2586                 return False;
2587         if (!smb_io_relstr("datafile", buffer, depth, &info->datafile))
2588                 return False;
2589         if (!smb_io_relstr("configfile", buffer, depth, &info->configfile))
2590                 return False;
2591         if (!smb_io_relstr("helpfile", buffer, depth, &info->helpfile))
2592                 return False;
2593
2594         if (!smb_io_relarraystr("dependentfiles", buffer, depth, &info->dependentfiles))
2595                 return False;
2596
2597         if (!smb_io_relstr("monitorname", buffer, depth, &info->monitorname))
2598                 return False;
2599         if (!smb_io_relstr("defaultdatatype", buffer, depth, &info->defaultdatatype))
2600                 return False;
2601
2602         if (!smb_io_relarraystr("previousdrivernames", buffer, depth, &info->previousdrivernames))
2603                 return False;
2604
2605         if (!prs_uint32("date.low", ps, depth, &info->driver_date.low))
2606                 return False;
2607         if (!prs_uint32("date.high", ps, depth, &info->driver_date.high))
2608                 return False;
2609
2610         if (!prs_uint32("padding", ps, depth, &info->padding))
2611                 return False;
2612
2613         if (!prs_uint32("driver_version_low", ps, depth, &info->driver_version_low))
2614                 return False;
2615
2616         if (!prs_uint32("driver_version_high", ps, depth, &info->driver_version_high))
2617                 return False;
2618
2619         if (!smb_io_relstr("mfgname", buffer, depth, &info->mfgname))
2620                 return False;
2621         if (!smb_io_relstr("oem_url", buffer, depth, &info->oem_url))
2622                 return False;
2623         if (!smb_io_relstr("hardware_id", buffer, depth, &info->hardware_id))
2624                 return False;
2625         if (!smb_io_relstr("provider", buffer, depth, &info->provider))
2626                 return False;
2627         
2628         return True;
2629 }
2630
2631 /*******************************************************************
2632  Parse a JOB_INFO_1 structure.
2633 ********************************************************************/  
2634
2635 BOOL smb_io_job_info_1(const char *desc, RPC_BUFFER *buffer, JOB_INFO_1 *info, int depth)
2636 {
2637         prs_struct *ps=&buffer->prs;
2638
2639         prs_debug(ps, depth, desc, "smb_io_job_info_1");
2640         depth++;        
2641         
2642         buffer->struct_start=prs_offset(ps);
2643
2644         if (!prs_uint32("jobid", ps, depth, &info->jobid))
2645                 return False;
2646         if (!smb_io_relstr("printername", buffer, depth, &info->printername))
2647                 return False;
2648         if (!smb_io_relstr("machinename", buffer, depth, &info->machinename))
2649                 return False;
2650         if (!smb_io_relstr("username", buffer, depth, &info->username))
2651                 return False;
2652         if (!smb_io_relstr("document", buffer, depth, &info->document))
2653                 return False;
2654         if (!smb_io_relstr("datatype", buffer, depth, &info->datatype))
2655                 return False;
2656         if (!smb_io_relstr("text_status", buffer, depth, &info->text_status))
2657                 return False;
2658         if (!prs_uint32("status", ps, depth, &info->status))
2659                 return False;
2660         if (!prs_uint32("priority", ps, depth, &info->priority))
2661                 return False;
2662         if (!prs_uint32("position", ps, depth, &info->position))
2663                 return False;
2664         if (!prs_uint32("totalpages", ps, depth, &info->totalpages))
2665                 return False;
2666         if (!prs_uint32("pagesprinted", ps, depth, &info->pagesprinted))
2667                 return False;
2668         if (!spoolss_io_system_time("submitted", ps, depth, &info->submitted))
2669                 return False;
2670
2671         return True;
2672 }
2673
2674 /*******************************************************************
2675  Parse a JOB_INFO_2 structure.
2676 ********************************************************************/  
2677
2678 BOOL smb_io_job_info_2(const char *desc, RPC_BUFFER *buffer, JOB_INFO_2 *info, int depth)
2679 {       
2680         uint32 pipo=0;
2681         prs_struct *ps=&buffer->prs;
2682         
2683         prs_debug(ps, depth, desc, "smb_io_job_info_2");
2684         depth++;        
2685
2686         buffer->struct_start=prs_offset(ps);
2687         
2688         if (!prs_uint32("jobid",ps, depth, &info->jobid))
2689                 return False;
2690         if (!smb_io_relstr("printername", buffer, depth, &info->printername))
2691                 return False;
2692         if (!smb_io_relstr("machinename", buffer, depth, &info->machinename))
2693                 return False;
2694         if (!smb_io_relstr("username", buffer, depth, &info->username))
2695                 return False;
2696         if (!smb_io_relstr("document", buffer, depth, &info->document))
2697                 return False;
2698         if (!smb_io_relstr("notifyname", buffer, depth, &info->notifyname))
2699                 return False;
2700         if (!smb_io_relstr("datatype", buffer, depth, &info->datatype))
2701                 return False;
2702
2703         if (!smb_io_relstr("printprocessor", buffer, depth, &info->printprocessor))
2704                 return False;
2705         if (!smb_io_relstr("parameters", buffer, depth, &info->parameters))
2706                 return False;
2707         if (!smb_io_relstr("drivername", buffer, depth, &info->drivername))
2708                 return False;
2709         if (!smb_io_reldevmode("devmode", buffer, depth, &info->devmode))
2710                 return False;
2711         if (!smb_io_relstr("text_status", buffer, depth, &info->text_status))
2712                 return False;
2713
2714 /*      SEC_DESC sec_desc;*/
2715         if (!prs_uint32("Hack! sec desc", ps, depth, &pipo))
2716                 return False;
2717
2718         if (!prs_uint32("status",ps, depth, &info->status))
2719                 return False;
2720         if (!prs_uint32("priority",ps, depth, &info->priority))
2721                 return False;
2722         if (!prs_uint32("position",ps, depth, &info->position)) 
2723                 return False;
2724         if (!prs_uint32("starttime",ps, depth, &info->starttime))
2725                 return False;
2726         if (!prs_uint32("untiltime",ps, depth, &info->untiltime))       
2727                 return False;
2728         if (!prs_uint32("totalpages",ps, depth, &info->totalpages))
2729                 return False;
2730         if (!prs_uint32("size",ps, depth, &info->size))
2731                 return False;
2732         if (!spoolss_io_system_time("submitted", ps, depth, &info->submitted) )
2733                 return False;
2734         if (!prs_uint32("timeelapsed",ps, depth, &info->timeelapsed))
2735                 return False;
2736         if (!prs_uint32("pagesprinted",ps, depth, &info->pagesprinted))
2737                 return False;
2738
2739         return True;
2740 }
2741
2742 /*******************************************************************
2743 ********************************************************************/  
2744
2745 BOOL smb_io_form_1(const char *desc, RPC_BUFFER *buffer, FORM_1 *info, int depth)
2746 {
2747         prs_struct *ps=&buffer->prs;
2748         
2749         prs_debug(ps, depth, desc, "smb_io_form_1");
2750         depth++;
2751                 
2752         buffer->struct_start=prs_offset(ps);
2753         
2754         if (!prs_uint32("flag", ps, depth, &info->flag))
2755                 return False;
2756                 
2757         if (!smb_io_relstr("name", buffer, depth, &info->name))
2758                 return False;
2759
2760         if (!prs_uint32("width", ps, depth, &info->width))
2761                 return False;
2762         if (!prs_uint32("length", ps, depth, &info->length))
2763                 return False;
2764         if (!prs_uint32("left", ps, depth, &info->left))
2765                 return False;
2766         if (!prs_uint32("top", ps, depth, &info->top))
2767                 return False;
2768         if (!prs_uint32("right", ps, depth, &info->right))
2769                 return False;
2770         if (!prs_uint32("bottom", ps, depth, &info->bottom))
2771                 return False;
2772
2773         return True;
2774 }
2775
2776
2777
2778 /*******************************************************************
2779  Parse a DRIVER_DIRECTORY_1 structure.
2780 ********************************************************************/  
2781
2782 BOOL smb_io_driverdir_1(const char *desc, RPC_BUFFER *buffer, DRIVER_DIRECTORY_1 *info, int depth)
2783 {
2784         prs_struct *ps=&buffer->prs;
2785
2786         prs_debug(ps, depth, desc, "smb_io_driverdir_1");
2787         depth++;
2788
2789         buffer->struct_start=prs_offset(ps);
2790
2791         if (!smb_io_unistr(desc, &info->name, ps, depth))
2792                 return False;
2793
2794         return True;
2795 }
2796
2797 /*******************************************************************
2798  Parse a PORT_INFO_1 structure.
2799 ********************************************************************/  
2800
2801 BOOL smb_io_port_1(const char *desc, RPC_BUFFER *buffer, PORT_INFO_1 *info, int depth)
2802 {
2803         prs_struct *ps=&buffer->prs;
2804
2805         prs_debug(ps, depth, desc, "smb_io_port_1");
2806         depth++;
2807
2808         buffer->struct_start=prs_offset(ps);
2809
2810         if(!smb_io_relstr("port_name", buffer, depth, &info->port_name))
2811                 return False;
2812
2813         return True;
2814 }
2815
2816 /*******************************************************************
2817  Parse a PORT_INFO_2 structure.
2818 ********************************************************************/  
2819
2820 BOOL smb_io_port_2(const char *desc, RPC_BUFFER *buffer, PORT_INFO_2 *info, int depth)
2821 {
2822         prs_struct *ps=&buffer->prs;
2823
2824         prs_debug(ps, depth, desc, "smb_io_port_2");
2825         depth++;
2826
2827         buffer->struct_start=prs_offset(ps);
2828
2829         if(!smb_io_relstr("port_name", buffer, depth, &info->port_name))
2830                 return False;
2831         if(!smb_io_relstr("monitor_name", buffer, depth, &info->monitor_name))
2832                 return False;
2833         if(!smb_io_relstr("description", buffer, depth, &info->description))
2834                 return False;
2835         if(!prs_uint32("port_type", ps, depth, &info->port_type))
2836                 return False;
2837         if(!prs_uint32("reserved", ps, depth, &info->reserved))
2838                 return False;
2839
2840         return True;
2841 }
2842
2843 /*******************************************************************
2844 ********************************************************************/  
2845
2846 BOOL smb_io_printprocessor_info_1(const char *desc, RPC_BUFFER *buffer, PRINTPROCESSOR_1 *info, int depth)
2847 {
2848         prs_struct *ps=&buffer->prs;
2849
2850         prs_debug(ps, depth, desc, "smb_io_printprocessor_info_1");
2851         depth++;        
2852
2853         buffer->struct_start=prs_offset(ps);
2854         
2855         if (smb_io_relstr("name", buffer, depth, &info->name))
2856                 return False;
2857
2858         return True;
2859 }
2860
2861 /*******************************************************************
2862 ********************************************************************/  
2863
2864 BOOL smb_io_printprocdatatype_info_1(const char *desc, RPC_BUFFER *buffer, PRINTPROCDATATYPE_1 *info, int depth)
2865 {
2866         prs_struct *ps=&buffer->prs;
2867
2868         prs_debug(ps, depth, desc, "smb_io_printprocdatatype_info_1");
2869         depth++;        
2870
2871         buffer->struct_start=prs_offset(ps);
2872         
2873         if (smb_io_relstr("name", buffer, depth, &info->name))
2874                 return False;
2875
2876         return True;
2877 }
2878
2879 /*******************************************************************
2880 ********************************************************************/  
2881
2882 BOOL smb_io_printmonitor_info_1(const char *desc, RPC_BUFFER *buffer, PRINTMONITOR_1 *info, int depth)
2883 {
2884         prs_struct *ps=&buffer->prs;
2885
2886         prs_debug(ps, depth, desc, "smb_io_printmonitor_info_1");
2887         depth++;        
2888
2889         buffer->struct_start=prs_offset(ps);
2890
2891         if (!smb_io_relstr("name", buffer, depth, &info->name))
2892                 return False;
2893
2894         return True;
2895 }
2896
2897 /*******************************************************************
2898 ********************************************************************/  
2899
2900 BOOL smb_io_printmonitor_info_2(const char *desc, RPC_BUFFER *buffer, PRINTMONITOR_2 *info, int depth)
2901 {
2902         prs_struct *ps=&buffer->prs;
2903
2904         prs_debug(ps, depth, desc, "smb_io_printmonitor_info_2");
2905         depth++;        
2906
2907         buffer->struct_start=prs_offset(ps);
2908
2909         if (!smb_io_relstr("name", buffer, depth, &info->name))
2910                 return False;
2911         if (!smb_io_relstr("environment", buffer, depth, &info->environment))
2912                 return False;
2913         if (!smb_io_relstr("dll_name", buffer, depth, &info->dll_name))
2914                 return False;
2915
2916         return True;
2917 }
2918
2919 /*******************************************************************
2920 return the size required by a struct in the stream
2921 ********************************************************************/  
2922
2923 uint32 spoolss_size_printer_info_0(PRINTER_INFO_0 *info)
2924 {
2925         int size=0;
2926         
2927         size+=size_of_relative_string( &info->printername );
2928         size+=size_of_relative_string( &info->servername );
2929
2930         size+=size_of_uint32( &info->cjobs);
2931         size+=size_of_uint32( &info->total_jobs);
2932         size+=size_of_uint32( &info->total_bytes);
2933
2934         size+=size_of_uint16( &info->year);
2935         size+=size_of_uint16( &info->month);
2936         size+=size_of_uint16( &info->dayofweek);
2937         size+=size_of_uint16( &info->day);
2938         size+=size_of_uint16( &info->hour);
2939         size+=size_of_uint16( &info->minute);
2940         size+=size_of_uint16( &info->second);
2941         size+=size_of_uint16( &info->milliseconds);
2942
2943         size+=size_of_uint32( &info->global_counter);
2944         size+=size_of_uint32( &info->total_pages);
2945
2946         size+=size_of_uint16( &info->major_version);
2947         size+=size_of_uint16( &info->build_version);
2948
2949         size+=size_of_uint32( &info->unknown7);
2950         size+=size_of_uint32( &info->unknown8);
2951         size+=size_of_uint32( &info->unknown9);
2952         size+=size_of_uint32( &info->session_counter);
2953         size+=size_of_uint32( &info->unknown11);
2954         size+=size_of_uint32( &info->printer_errors);
2955         size+=size_of_uint32( &info->unknown13);
2956         size+=size_of_uint32( &info->unknown14);
2957         size+=size_of_uint32( &info->unknown15);
2958         size+=size_of_uint32( &info->unknown16);
2959         size+=size_of_uint32( &info->change_id);
2960         size+=size_of_uint32( &info->unknown18);
2961         size+=size_of_uint32( &info->status);
2962         size+=size_of_uint32( &info->unknown20);
2963         size+=size_of_uint32( &info->c_setprinter);
2964         
2965         size+=size_of_uint16( &info->unknown22);
2966         size+=size_of_uint16( &info->unknown23);
2967         size+=size_of_uint16( &info->unknown24);
2968         size+=size_of_uint16( &info->unknown25);
2969         size+=size_of_uint16( &info->unknown26);
2970         size+=size_of_uint16( &info->unknown27);
2971         size+=size_of_uint16( &info->unknown28);
2972         size+=size_of_uint16( &info->unknown29);
2973         
2974         return size;
2975 }
2976
2977 /*******************************************************************
2978 return the size required by a struct in the stream
2979 ********************************************************************/  
2980
2981 uint32 spoolss_size_printer_info_1(PRINTER_INFO_1 *info)
2982 {
2983         int size=0;
2984                 
2985         size+=size_of_uint32( &info->flags );   
2986         size+=size_of_relative_string( &info->description );
2987         size+=size_of_relative_string( &info->name );
2988         size+=size_of_relative_string( &info->comment );
2989
2990         return size;
2991 }
2992
2993 /*******************************************************************
2994 return the size required by a struct in the stream
2995 ********************************************************************/
2996
2997 uint32 spoolss_size_printer_info_2(PRINTER_INFO_2 *info)
2998 {
2999         uint32 size=0;
3000                 
3001         size += 4;
3002         
3003         size += sec_desc_size( info->secdesc );
3004
3005         size+=size_of_device_mode( info->devmode );
3006         
3007         size+=size_of_relative_string( &info->servername );
3008         size+=size_of_relative_string( &info->printername );
3009         size+=size_of_relative_string( &info->sharename );
3010         size+=size_of_relative_string( &info->portname );
3011         size+=size_of_relative_string( &info->drivername );
3012         size+=size_of_relative_string( &info->comment );
3013         size+=size_of_relative_string( &info->location );
3014         
3015         size+=size_of_relative_string( &info->sepfile );
3016         size+=size_of_relative_string( &info->printprocessor );
3017         size+=size_of_relative_string( &info->datatype );
3018         size+=size_of_relative_string( &info->parameters );
3019
3020         size+=size_of_uint32( &info->attributes );
3021         size+=size_of_uint32( &info->priority );
3022         size+=size_of_uint32( &info->defaultpriority );
3023         size+=size_of_uint32( &info->starttime );
3024         size+=size_of_uint32( &info->untiltime );
3025         size+=size_of_uint32( &info->status );
3026         size+=size_of_uint32( &info->cjobs );
3027         size+=size_of_uint32( &info->averageppm );      
3028                 
3029         /* 
3030          * add any adjustments for alignment.  This is
3031          * not optimal since we could be calling this
3032          * function from a loop (e.g. enumprinters), but 
3033          * it is easier to maintain the calculation here and
3034          * not place the burden on the caller to remember.   --jerry
3035          */
3036         if ((size % 4) != 0)
3037                 size += 4 - (size % 4);
3038         
3039         return size;
3040 }
3041
3042 /*******************************************************************
3043 return the size required by a struct in the stream
3044 ********************************************************************/
3045
3046 uint32 spoolss_size_printer_info_4(PRINTER_INFO_4 *info)
3047 {
3048         uint32 size=0;
3049                 
3050         size+=size_of_relative_string( &info->printername );
3051         size+=size_of_relative_string( &info->servername );
3052
3053         size+=size_of_uint32( &info->attributes );
3054         return size;
3055 }
3056
3057 /*******************************************************************
3058 return the size required by a struct in the stream
3059 ********************************************************************/
3060
3061 uint32 spoolss_size_printer_info_5(PRINTER_INFO_5 *info)
3062 {
3063         uint32 size=0;
3064                 
3065         size+=size_of_relative_string( &info->printername );
3066         size+=size_of_relative_string( &info->portname );
3067
3068         size+=size_of_uint32( &info->attributes );
3069         size+=size_of_uint32( &info->device_not_selected_timeout );
3070         size+=size_of_uint32( &info->transmission_retry_timeout );
3071         return size;
3072 }
3073
3074
3075 /*******************************************************************
3076 return the size required by a struct in the stream
3077 ********************************************************************/
3078
3079 uint32 spoolss_size_printer_info_3(PRINTER_INFO_3 *info)
3080 {
3081         /* The 4 is for the self relative pointer.. */
3082         /* JRA !!!! TESTME - WHAT ABOUT prs_align.... !!! */
3083         return 4 + (uint32)sec_desc_size( info->secdesc );
3084 }
3085
3086 /*******************************************************************
3087 return the size required by a struct in the stream
3088 ********************************************************************/
3089
3090 uint32 spoolss_size_printer_info_7(PRINTER_INFO_7 *info)
3091 {
3092         uint32 size=0;
3093                 
3094         size+=size_of_relative_string( &info->guid );
3095         size+=size_of_uint32( &info->action );
3096         return size;
3097 }
3098
3099 /*******************************************************************
3100 return the size required by a struct in the stream
3101 ********************************************************************/
3102
3103 uint32 spoolss_size_printer_driver_info_1(DRIVER_INFO_1 *info)
3104 {
3105         int size=0;
3106         size+=size_of_relative_string( &info->name );
3107
3108         return size;
3109 }
3110
3111 /*******************************************************************
3112 return the size required by a struct in the stream
3113 ********************************************************************/
3114
3115 uint32 spoolss_size_printer_driver_info_2(DRIVER_INFO_2 *info)
3116 {
3117         int size=0;
3118         size+=size_of_uint32( &info->version ); 
3119         size+=size_of_relative_string( &info->name );
3120         size+=size_of_relative_string( &info->architecture );
3121         size+=size_of_relative_string( &info->driverpath );
3122         size+=size_of_relative_string( &info->datafile );
3123         size+=size_of_relative_string( &info->configfile );
3124
3125         return size;
3126 }
3127
3128 /*******************************************************************
3129 return the size required by a string array.
3130 ********************************************************************/
3131
3132 uint32 spoolss_size_string_array(uint16 *string)
3133 {
3134         uint32 i = 0;
3135
3136         if (string) {
3137                 for (i=0; (string[i]!=0x0000) || (string[i+1]!=0x0000); i++);
3138         }
3139         i=i+2; /* to count all chars including the leading zero */
3140         i=2*i; /* because we need the value in bytes */
3141         i=i+4; /* the offset pointer size */
3142
3143         return i;
3144 }
3145
3146 /*******************************************************************
3147 return the size required by a struct in the stream
3148 ********************************************************************/
3149
3150 uint32 spoolss_size_printer_driver_info_3(DRIVER_INFO_3 *info)
3151 {
3152         int size=0;
3153
3154         size+=size_of_uint32( &info->version ); 
3155         size+=size_of_relative_string( &info->name );
3156         size+=size_of_relative_string( &info->architecture );
3157         size+=size_of_relative_string( &info->driverpath );
3158         size+=size_of_relative_string( &info->datafile );
3159         size+=size_of_relative_string( &info->configfile );
3160         size+=size_of_relative_string( &info->helpfile );
3161         size+=size_of_relative_string( &info->monitorname );
3162         size+=size_of_relative_string( &info->defaultdatatype );
3163         
3164         size+=spoolss_size_string_array(info->dependentfiles);
3165
3166         return size;
3167 }
3168
3169 /*******************************************************************
3170 return the size required by a struct in the stream
3171 ********************************************************************/
3172
3173 uint32 spoolss_size_printer_driver_info_6(DRIVER_INFO_6 *info)
3174 {
3175         uint32 size=0;
3176
3177         size+=size_of_uint32( &info->version ); 
3178         size+=size_of_relative_string( &info->name );
3179         size+=size_of_relative_string( &info->architecture );
3180         size+=size_of_relative_string( &info->driverpath );
3181         size+=size_of_relative_string( &info->datafile );
3182         size+=size_of_relative_string( &info->configfile );
3183         size+=size_of_relative_string( &info->helpfile );
3184
3185         size+=spoolss_size_string_array(info->dependentfiles);
3186
3187         size+=size_of_relative_string( &info->monitorname );
3188         size+=size_of_relative_string( &info->defaultdatatype );
3189         
3190         size+=spoolss_size_string_array(info->previousdrivernames);
3191
3192         size+=size_of_nttime(&info->driver_date);
3193         size+=size_of_uint32( &info->padding ); 
3194         size+=size_of_uint32( &info->driver_version_low );      
3195         size+=size_of_uint32( &info->driver_version_high );     
3196         size+=size_of_relative_string( &info->mfgname );
3197         size+=size_of_relative_string( &info->oem_url );
3198         size+=size_of_relative_string( &info->hardware_id );
3199         size+=size_of_relative_string( &info->provider );
3200
3201         return size;
3202 }
3203
3204 /*******************************************************************
3205 return the size required by a struct in the stream
3206 ********************************************************************/  
3207
3208 uint32 spoolss_size_job_info_1(JOB_INFO_1 *info)
3209 {
3210         int size=0;
3211         size+=size_of_uint32( &info->jobid );
3212         size+=size_of_relative_string( &info->printername );
3213         size+=size_of_relative_string( &info->machinename );
3214         size+=size_of_relative_string( &info->username );
3215         size+=size_of_relative_string( &info->document );
3216         size+=size_of_relative_string( &info->datatype );
3217         size+=size_of_relative_string( &info->text_status );
3218         size+=size_of_uint32( &info->status );
3219         size+=size_of_uint32( &info->priority );
3220         size+=size_of_uint32( &info->position );
3221         size+=size_of_uint32( &info->totalpages );
3222         size+=size_of_uint32( &info->pagesprinted );
3223         size+=size_of_systemtime( &info->submitted );
3224
3225         return size;
3226 }
3227
3228 /*******************************************************************
3229 return the size required by a struct in the stream
3230 ********************************************************************/  
3231
3232 uint32 spoolss_size_job_info_2(JOB_INFO_2 *info)
3233 {
3234         int size=0;
3235
3236         size+=4; /* size of sec desc ptr */
3237
3238         size+=size_of_uint32( &info->jobid );
3239         size+=size_of_relative_string( &info->printername );
3240         size+=size_of_relative_string( &info->machinename );
3241         size+=size_of_relative_string( &info->username );
3242         size+=size_of_relative_string( &info->document );
3243         size+=size_of_relative_string( &info->notifyname );
3244         size+=size_of_relative_string( &info->datatype );
3245         size+=size_of_relative_string( &info->printprocessor );
3246         size+=size_of_relative_string( &info->parameters );
3247         size+=size_of_relative_string( &info->drivername );
3248         size+=size_of_device_mode( info->devmode );
3249         size+=size_of_relative_string( &info->text_status );
3250 /*      SEC_DESC sec_desc;*/
3251         size+=size_of_uint32( &info->status );
3252         size+=size_of_uint32( &info->priority );
3253         size+=size_of_uint32( &info->position );
3254         size+=size_of_uint32( &info->starttime );
3255         size+=size_of_uint32( &info->untiltime );
3256         size+=size_of_uint32( &info->totalpages );
3257         size+=size_of_uint32( &info->size );
3258         size+=size_of_systemtime( &info->submitted );
3259         size+=size_of_uint32( &info->timeelapsed );
3260         size+=size_of_uint32( &info->pagesprinted );
3261
3262         return size;
3263 }
3264
3265 /*******************************************************************
3266 return the size required by a struct in the stream
3267 ********************************************************************/
3268
3269 uint32 spoolss_size_form_1(FORM_1 *info)
3270 {
3271         int size=0;
3272
3273         size+=size_of_uint32( &info->flag );
3274         size+=size_of_relative_string( &info->name );
3275         size+=size_of_uint32( &info->width );
3276         size+=size_of_uint32( &info->length );
3277         size+=size_of_uint32( &info->left );
3278         size+=size_of_uint32( &info->top );
3279         size+=size_of_uint32( &info->right );
3280         size+=size_of_uint32( &info->bottom );
3281
3282         return size;
3283 }
3284
3285 /*******************************************************************
3286 return the size required by a struct in the stream
3287 ********************************************************************/  
3288
3289 uint32 spoolss_size_port_info_1(PORT_INFO_1 *info)
3290 {
3291         int size=0;
3292
3293         size+=size_of_relative_string( &info->port_name );
3294
3295         return size;
3296 }
3297
3298 /*******************************************************************
3299 return the size required by a struct in the stream
3300 ********************************************************************/  
3301
3302 uint32 spoolss_size_driverdir_info_1(DRIVER_DIRECTORY_1 *info)
3303 {
3304         int size=0;
3305
3306         size=str_len_uni(&info->name);  /* the string length       */
3307         size=size+1;                    /* add the leading zero    */
3308         size=size*2;                    /* convert in char         */
3309
3310         return size;
3311 }
3312
3313 /*******************************************************************
3314 return the size required by a struct in the stream
3315 ********************************************************************/  
3316
3317 uint32 spoolss_size_printprocessordirectory_info_1(PRINTPROCESSOR_DIRECTORY_1 *info)
3318 {
3319         int size=0;
3320
3321         size=str_len_uni(&info->name);  /* the string length       */
3322         size=size+1;                    /* add the leading zero    */
3323         size=size*2;                    /* convert in char         */
3324
3325         return size;
3326 }
3327
3328 /*******************************************************************
3329 return the size required by a struct in the stream
3330 ********************************************************************/  
3331
3332 uint32 spoolss_size_port_info_2(PORT_INFO_2 *info)
3333 {
3334         int size=0;
3335
3336         size+=size_of_relative_string( &info->port_name );
3337         size+=size_of_relative_string( &info->monitor_name );
3338         size+=size_of_relative_string( &info->description );
3339
3340         size+=size_of_uint32( &info->port_type );
3341         size+=size_of_uint32( &info->reserved );
3342
3343         return size;
3344 }
3345
3346 /*******************************************************************
3347 return the size required by a struct in the stream
3348 ********************************************************************/  
3349
3350 uint32 spoolss_size_printprocessor_info_1(PRINTPROCESSOR_1 *info)
3351 {
3352         int size=0;
3353         size+=size_of_relative_string( &info->name );
3354
3355         return size;
3356 }
3357
3358 /*******************************************************************
3359 return the size required by a struct in the stream
3360 ********************************************************************/  
3361
3362 uint32 spoolss_size_printprocdatatype_info_1(PRINTPROCDATATYPE_1 *info)
3363 {
3364         int size=0;
3365         size+=size_of_relative_string( &info->name );
3366
3367         return size;
3368 }
3369
3370 /*******************************************************************
3371 return the size required by a struct in the stream
3372 ********************************************************************/  
3373 uint32 spoolss_size_printer_enum_values(PRINTER_ENUM_VALUES *p)
3374 {
3375         uint32  size = 0; 
3376         
3377         if (!p)
3378                 return 0;
3379         
3380         /* uint32(offset) + uint32(length) + length) */
3381         size += (size_of_uint32(&p->value_len)*2) + p->value_len;
3382         size += (size_of_uint32(&p->data_len)*2) + p->data_len + (p->data_len%2) ;
3383         
3384         size += size_of_uint32(&p->type);
3385                        
3386         return size;
3387 }
3388
3389 /*******************************************************************
3390 return the size required by a struct in the stream
3391 ********************************************************************/  
3392
3393 uint32 spoolss_size_printmonitor_info_1(PRINTMONITOR_1 *info)
3394 {
3395         int size=0;
3396         size+=size_of_relative_string( &info->name );
3397
3398         return size;
3399 }
3400
3401 /*******************************************************************
3402 return the size required by a struct in the stream
3403 ********************************************************************/  
3404
3405 uint32 spoolss_size_printmonitor_info_2(PRINTMONITOR_2 *info)
3406 {
3407         int size=0;
3408         size+=size_of_relative_string( &info->name);
3409         size+=size_of_relative_string( &info->environment);
3410         size+=size_of_relative_string( &info->dll_name);
3411
3412         return size;
3413 }
3414
3415 /*******************************************************************
3416  * init a structure.
3417  ********************************************************************/
3418
3419 BOOL make_spoolss_q_getprinterdriver2(SPOOL_Q_GETPRINTERDRIVER2 *q_u, 
3420                                const POLICY_HND *hnd,
3421                                const fstring architecture,
3422                                uint32 level, uint32 clientmajor, uint32 clientminor,
3423                                RPC_BUFFER *buffer, uint32 offered)
3424 {      
3425         if (q_u == NULL)
3426                 return False;
3427
3428         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
3429
3430         init_buf_unistr2(&q_u->architecture, &q_u->architecture_ptr, architecture);
3431
3432         q_u->level=level;
3433         q_u->clientmajorversion=clientmajor;
3434         q_u->clientminorversion=clientminor;
3435
3436         q_u->buffer=buffer;
3437         q_u->offered=offered;
3438
3439         return True;
3440 }
3441
3442 /*******************************************************************
3443  * read a structure.
3444  * called from spoolss_getprinterdriver2 (srv_spoolss.c)
3445  ********************************************************************/
3446
3447 BOOL spoolss_io_q_getprinterdriver2(const char *desc, SPOOL_Q_GETPRINTERDRIVER2 *q_u, prs_struct *ps, int depth)
3448 {
3449         prs_debug(ps, depth, desc, "spoolss_io_q_getprinterdriver2");
3450         depth++;
3451
3452         if(!prs_align(ps))
3453                 return False;
3454         
3455         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
3456                 return False;
3457         if(!prs_uint32("architecture_ptr", ps, depth, &q_u->architecture_ptr))
3458                 return False;
3459         if(!smb_io_unistr2("architecture", &q_u->architecture, q_u->architecture_ptr, ps, depth))
3460                 return False;
3461         
3462         if(!prs_align(ps))
3463                 return False;
3464         if(!prs_uint32("level", ps, depth, &q_u->level))
3465                 return False;
3466                 
3467         if(!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
3468                 return False;
3469
3470         if(!prs_align(ps))
3471                 return False;
3472
3473         if(!prs_uint32("offered", ps, depth, &q_u->offered))
3474                 return False;
3475                 
3476         if(!prs_uint32("clientmajorversion", ps, depth, &q_u->clientmajorversion))
3477                 return False;
3478         if(!prs_uint32("clientminorversion", ps, depth, &q_u->clientminorversion))
3479                 return False;
3480
3481         return True;
3482 }
3483
3484 /*******************************************************************
3485  * read a structure.
3486  * called from spoolss_getprinterdriver2 (srv_spoolss.c)
3487  ********************************************************************/
3488
3489 BOOL spoolss_io_r_getprinterdriver2(const char *desc, SPOOL_R_GETPRINTERDRIVER2 *r_u, prs_struct *ps, int depth)
3490 {
3491         prs_debug(ps, depth, desc, "spoolss_io_r_getprinterdriver2");
3492         depth++;
3493
3494         if (!prs_align(ps))
3495                 return False;
3496                 
3497         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
3498                 return False;
3499
3500         if (!prs_align(ps))
3501                 return False;
3502         if (!prs_uint32("needed", ps, depth, &r_u->needed))
3503                 return False;
3504         if (!prs_uint32("servermajorversion", ps, depth, &r_u->servermajorversion))
3505                 return False;
3506         if (!prs_uint32("serverminorversion", ps, depth, &r_u->serverminorversion))
3507                 return False;           
3508         if (!prs_werror("status", ps, depth, &r_u->status))
3509                 return False;
3510
3511         return True;            
3512 }
3513
3514 /*******************************************************************
3515  * init a structure.
3516  ********************************************************************/
3517
3518 BOOL make_spoolss_q_enumprinters(
3519         SPOOL_Q_ENUMPRINTERS *q_u, 
3520         uint32 flags, 
3521         char *servername, 
3522         uint32 level, 
3523         RPC_BUFFER *buffer, 
3524         uint32 offered
3525 )
3526 {
3527         q_u->flags=flags;
3528         
3529         q_u->servername_ptr = (servername != NULL) ? 1 : 0;
3530         init_buf_unistr2(&q_u->servername, &q_u->servername_ptr, servername);
3531
3532         q_u->level=level;
3533         q_u->buffer=buffer;
3534         q_u->offered=offered;
3535
3536         return True;
3537 }
3538
3539 /*******************************************************************
3540  * init a structure.
3541  ********************************************************************/
3542
3543 BOOL make_spoolss_q_enumports(SPOOL_Q_ENUMPORTS *q_u, 
3544                                 fstring servername, uint32 level, 
3545                                 RPC_BUFFER *buffer, uint32 offered)
3546 {
3547         q_u->name_ptr = (servername != NULL) ? 1 : 0;
3548         init_buf_unistr2(&q_u->name, &q_u->name_ptr, servername);
3549
3550         q_u->level=level;
3551         q_u->buffer=buffer;
3552         q_u->offered=offered;
3553
3554         return True;
3555 }
3556
3557 /*******************************************************************
3558  * read a structure.
3559  * called from spoolss_enumprinters (srv_spoolss.c)
3560  ********************************************************************/
3561
3562 BOOL spoolss_io_q_enumprinters(const char *desc, SPOOL_Q_ENUMPRINTERS *q_u, prs_struct *ps, int depth)
3563 {
3564         prs_debug(ps, depth, desc, "spoolss_io_q_enumprinters");
3565         depth++;
3566
3567         if (!prs_align(ps))
3568                 return False;
3569
3570         if (!prs_uint32("flags", ps, depth, &q_u->flags))
3571                 return False;
3572         if (!prs_uint32("servername_ptr", ps, depth, &q_u->servername_ptr))
3573                 return False;
3574
3575         if (!smb_io_unistr2("", &q_u->servername, q_u->servername_ptr, ps, depth))
3576                 return False;
3577                 
3578         if (!prs_align(ps))
3579                 return False;
3580         if (!prs_uint32("level", ps, depth, &q_u->level))
3581                 return False;
3582
3583         if (!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
3584                 return False;
3585
3586         if (!prs_align(ps))
3587                 return False;
3588         if (!prs_uint32("offered", ps, depth, &q_u->offered))
3589                 return False;
3590
3591         return True;
3592 }
3593
3594 /*******************************************************************
3595  Parse a SPOOL_R_ENUMPRINTERS structure.
3596  ********************************************************************/
3597
3598 BOOL spoolss_io_r_enumprinters(const char *desc, SPOOL_R_ENUMPRINTERS *r_u, prs_struct *ps, int depth)
3599 {
3600         prs_debug(ps, depth, desc, "spoolss_io_r_enumprinters");
3601         depth++;
3602
3603         if (!prs_align(ps))
3604                 return False;
3605                 
3606         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
3607                 return False;
3608
3609         if (!prs_align(ps))
3610                 return False;
3611                 
3612         if (!prs_uint32("needed", ps, depth, &r_u->needed))
3613                 return False;
3614                 
3615         if (!prs_uint32("returned", ps, depth, &r_u->returned))
3616                 return False;
3617                 
3618         if (!prs_werror("status", ps, depth, &r_u->status))
3619                 return False;
3620
3621         return True;            
3622 }
3623
3624 /*******************************************************************
3625  * write a structure.
3626  * called from spoolss_r_enum_printers (srv_spoolss.c)
3627  *
3628  ********************************************************************/
3629
3630 BOOL spoolss_io_r_getprinter(const char *desc, SPOOL_R_GETPRINTER *r_u, prs_struct *ps, int depth)
3631 {       
3632         prs_debug(ps, depth, desc, "spoolss_io_r_getprinter");
3633         depth++;
3634
3635         if (!prs_align(ps))
3636                 return False;
3637                 
3638         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
3639                 return False;
3640
3641         if (!prs_align(ps))
3642                 return False;
3643
3644         if (!prs_uint32("needed", ps, depth, &r_u->needed))
3645                 return False;
3646                 
3647         if (!prs_werror("status", ps, depth, &r_u->status))
3648                 return False;
3649
3650         return True;            
3651 }
3652
3653 /*******************************************************************
3654  * read a structure.
3655  * called from spoolss_getprinter (srv_spoolss.c)
3656  ********************************************************************/
3657
3658 BOOL spoolss_io_q_getprinter(const char *desc, SPOOL_Q_GETPRINTER *q_u, prs_struct *ps, int depth)
3659 {
3660         prs_debug(ps, depth, desc, "spoolss_io_q_getprinter");
3661         depth++;
3662
3663         if (!prs_align(ps))
3664                 return False;
3665
3666         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
3667                 return False;
3668         if (!prs_uint32("level", ps, depth, &q_u->level))
3669                 return False;
3670
3671         if (!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
3672                 return False;
3673
3674         if (!prs_align(ps))
3675                 return False;
3676         if (!prs_uint32("offered", ps, depth, &q_u->offered))
3677                 return False;
3678
3679         return True;
3680 }
3681
3682 /*******************************************************************
3683  * init a structure.
3684  ********************************************************************/
3685
3686 BOOL make_spoolss_q_getprinter(
3687         TALLOC_CTX *mem_ctx,
3688         SPOOL_Q_GETPRINTER *q_u, 
3689         const POLICY_HND *hnd, 
3690         uint32 level, 
3691         RPC_BUFFER *buffer, 
3692         uint32 offered
3693 )
3694 {
3695         if (q_u == NULL)
3696         {
3697                 return False;
3698         }
3699         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
3700
3701         q_u->level=level;
3702         q_u->buffer=buffer;
3703         q_u->offered=offered;
3704
3705         return True;
3706 }
3707
3708 /*******************************************************************
3709  * init a structure.
3710  ********************************************************************/
3711 BOOL make_spoolss_q_setprinter(TALLOC_CTX *mem_ctx, SPOOL_Q_SETPRINTER *q_u, 
3712                                 const POLICY_HND *hnd, uint32 level, PRINTER_INFO_CTR *info, 
3713                                 uint32 command)
3714 {
3715         SEC_DESC *secdesc;
3716         DEVICEMODE *devmode;
3717
3718         if (q_u == NULL)
3719                 return False;
3720         
3721         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
3722
3723         q_u->level = level;
3724         q_u->info.level = level;
3725         q_u->info.info_ptr = (info != NULL) ? 1 : 0;
3726         switch (level) {
3727
3728           /* There's no such thing as a setprinter level 1 */
3729
3730         case 2:
3731                 secdesc = info->printers_2->secdesc;
3732                 devmode = info->printers_2->devmode;
3733                 
3734                 make_spoolss_printer_info_2 (mem_ctx, &q_u->info.info_2, info->printers_2);
3735 #if 1   /* JERRY TEST */
3736                 q_u->secdesc_ctr = SMB_MALLOC_P(SEC_DESC_BUF);
3737                 if (!q_u->secdesc_ctr)
3738                         return False;
3739                 q_u->secdesc_ctr->ptr = (secdesc != NULL) ? 1: 0;
3740                 q_u->secdesc_ctr->max_len = (secdesc) ? sizeof(SEC_DESC) + (2*sizeof(uint32)) : 0;
3741                 q_u->secdesc_ctr->len = (secdesc) ? sizeof(SEC_DESC) + (2*sizeof(uint32)) : 0;
3742                 q_u->secdesc_ctr->sec = secdesc;
3743
3744                 q_u->devmode_ctr.devmode_ptr = (devmode != NULL) ? 1 : 0;
3745                 q_u->devmode_ctr.size = (devmode != NULL) ? sizeof(DEVICEMODE) + (3*sizeof(uint32)) : 0;
3746                 q_u->devmode_ctr.devmode = devmode;
3747 #else
3748                 q_u->secdesc_ctr = NULL;
3749         
3750                 q_u->devmode_ctr.devmode_ptr = 0;
3751                 q_u->devmode_ctr.size = 0;
3752                 q_u->devmode_ctr.devmode = NULL;
3753 #endif
3754                 break;
3755         case 3:
3756                 secdesc = info->printers_3->secdesc;
3757                 
3758                 make_spoolss_printer_info_3 (mem_ctx, &q_u->info.info_3, info->printers_3);
3759                 
3760                 q_u->secdesc_ctr = SMB_MALLOC_P(SEC_DESC_BUF);
3761                 if (!q_u->secdesc_ctr)
3762                         return False;
3763                 q_u->secdesc_ctr->ptr = (secdesc != NULL) ? 1: 0;
3764                 q_u->secdesc_ctr->max_len = (secdesc) ? sizeof(SEC_DESC) + (2*sizeof(uint32)) : 0;
3765                 q_u->secdesc_ctr->len = (secdesc) ? sizeof(SEC_DESC) + (2*sizeof(uint32)) : 0;
3766                 q_u->secdesc_ctr->sec = secdesc;
3767
3768                 break;
3769         case 7:
3770                 make_spoolss_printer_info_7 (mem_ctx, &q_u->info.info_7, info->printers_7);
3771                 break;
3772
3773         default: 
3774                 DEBUG(0,("make_spoolss_q_setprinter: Unknown info level [%d]\n", level));
3775                         break;
3776         }
3777
3778         
3779         q_u->command = command;
3780
3781         return True;
3782 }
3783
3784
3785 /*******************************************************************
3786 ********************************************************************/  
3787
3788 BOOL spoolss_io_r_setprinter(const char *desc, SPOOL_R_SETPRINTER *r_u, prs_struct *ps, int depth)
3789 {               
3790         prs_debug(ps, depth, desc, "spoolss_io_r_setprinter");
3791         depth++;
3792
3793         if(!prs_align(ps))
3794                 return False;
3795         
3796         if(!prs_werror("status", ps, depth, &r_u->status))
3797                 return False;
3798
3799         return True;
3800 }
3801
3802 /*******************************************************************
3803  Marshall/unmarshall a SPOOL_Q_SETPRINTER struct.
3804 ********************************************************************/  
3805
3806 BOOL spoolss_io_q_setprinter(const char *desc, SPOOL_Q_SETPRINTER *q_u, prs_struct *ps, int depth)
3807 {
3808         uint32 ptr_sec_desc = 0;
3809
3810         prs_debug(ps, depth, desc, "spoolss_io_q_setprinter");
3811         depth++;
3812
3813         if(!prs_align(ps))
3814                 return False;
3815
3816         if(!smb_io_pol_hnd("printer handle", &q_u->handle ,ps, depth))
3817                 return False;
3818         if(!prs_uint32("level", ps, depth, &q_u->level))
3819                 return False;
3820         
3821         /* check for supported levels and structures we know about */
3822                 
3823         switch ( q_u->level ) {
3824                 case 0:
3825                 case 2:
3826                 case 3:
3827                 case 7:
3828                         /* supported levels */
3829                         break;
3830                 default:
3831                         DEBUG(0,("spoolss_io_q_setprinter: unsupported printer info level [%d]\n", 
3832                                 q_u->level));
3833                         return True;
3834         }
3835                         
3836
3837         if(!spool_io_printer_info_level("", &q_u->info, ps, depth))
3838                 return False;
3839
3840         if (!spoolss_io_devmode_cont(desc, &q_u->devmode_ctr, ps, depth))
3841                 return False;
3842         
3843         if(!prs_align(ps))
3844                 return False;
3845
3846         switch (q_u->level)
3847         {
3848                 case 2:
3849                 {
3850                         ptr_sec_desc = q_u->info.info_2->secdesc_ptr;
3851                         break;
3852                 }
3853                 case 3:
3854                 {
3855                         ptr_sec_desc = q_u->info.info_3->secdesc_ptr;
3856                         break;
3857                 }
3858         }
3859         if (ptr_sec_desc)
3860         {
3861                 if (!sec_io_desc_buf(desc, &q_u->secdesc_ctr, ps, depth))
3862                         return False;
3863         } else {
3864                 uint32 dummy = 0;
3865
3866                 /* Parse a NULL security descriptor.  This should really
3867                    happen inside the sec_io_desc_buf() function. */
3868
3869                 prs_debug(ps, depth, "", "sec_io_desc_buf");
3870                 if (!prs_uint32("size", ps, depth + 1, &dummy))
3871                         return False;
3872                 if (!prs_uint32("ptr", ps, depth + 1, &dummy)) return
3873                                                                        False;
3874         }
3875         
3876         if(!prs_uint32("command", ps, depth, &q_u->command))
3877                 return False;
3878
3879         return True;
3880 }
3881
3882 /*******************************************************************
3883 ********************************************************************/  
3884
3885 BOOL spoolss_io_r_fcpn(const char *desc, SPOOL_R_FCPN *r_u, prs_struct *ps, int depth)
3886 {               
3887         prs_debug(ps, depth, desc, "spoolss_io_r_fcpn");
3888         depth++;
3889
3890         if(!prs_align(ps))
3891                 return False;
3892         
3893         if(!prs_werror("status", ps, depth, &r_u->status))
3894                 return False;
3895
3896         return True;
3897 }
3898
3899 /*******************************************************************
3900 ********************************************************************/  
3901
3902 BOOL spoolss_io_q_fcpn(const char *desc, SPOOL_Q_FCPN *q_u, prs_struct *ps, int depth)
3903 {
3904
3905         prs_debug(ps, depth, desc, "spoolss_io_q_fcpn");
3906         depth++;
3907
3908         if(!prs_align(ps))
3909                 return False;
3910
3911         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
3912                 return False;
3913
3914         return True;
3915 }
3916
3917
3918 /*******************************************************************
3919 ********************************************************************/  
3920
3921 BOOL spoolss_io_r_addjob(const char *desc, SPOOL_R_ADDJOB *r_u, prs_struct *ps, int depth)
3922 {               
3923         prs_debug(ps, depth, desc, "");
3924         depth++;
3925
3926         if(!prs_align(ps))
3927                 return False;
3928         
3929         if(!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
3930                 return False;
3931
3932         if(!prs_align(ps))
3933                 return False;
3934         
3935         if(!prs_uint32("needed", ps, depth, &r_u->needed))
3936                 return False;
3937
3938         if(!prs_werror("status", ps, depth, &r_u->status))
3939                 return False;
3940
3941         return True;
3942 }
3943
3944 /*******************************************************************
3945 ********************************************************************/  
3946
3947 BOOL spoolss_io_q_addjob(const char *desc, SPOOL_Q_ADDJOB *q_u, prs_struct *ps, int depth)
3948 {
3949         prs_debug(ps, depth, desc, "");
3950         depth++;
3951
3952         if(!prs_align(ps))
3953                 return False;
3954
3955         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
3956                 return False;
3957         if(!prs_uint32("level", ps, depth, &q_u->level))
3958                 return False;
3959         
3960         if(!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
3961                 return False;
3962
3963         if(!prs_align(ps))
3964                 return False;
3965         
3966         if(!prs_uint32("offered", ps, depth, &q_u->offered))
3967                 return False;
3968
3969         return True;
3970 }
3971
3972 /*******************************************************************
3973 ********************************************************************/  
3974
3975 BOOL spoolss_io_r_enumjobs(const char *desc, SPOOL_R_ENUMJOBS *r_u, prs_struct *ps, int depth)
3976 {               
3977         prs_debug(ps, depth, desc, "spoolss_io_r_enumjobs");
3978         depth++;
3979
3980         if (!prs_align(ps))
3981                 return False;
3982                 
3983         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
3984                 return False;
3985
3986         if (!prs_align(ps))
3987                 return False;
3988                 
3989         if (!prs_uint32("needed", ps, depth, &r_u->needed))
3990                 return False;
3991                 
3992         if (!prs_uint32("returned", ps, depth, &r_u->returned))
3993                 return False;
3994                 
3995         if (!prs_werror("status", ps, depth, &r_u->status))
3996                 return False;
3997
3998         return True;            
3999 }
4000
4001 /*******************************************************************
4002 ********************************************************************/  
4003
4004 BOOL make_spoolss_q_enumjobs(SPOOL_Q_ENUMJOBS *q_u, const POLICY_HND *hnd,
4005                                 uint32 firstjob,
4006                                 uint32 numofjobs,
4007                                 uint32 level,
4008                                 RPC_BUFFER *buffer,
4009                                 uint32 offered)
4010 {
4011         if (q_u == NULL)
4012         {
4013                 return False;
4014         }
4015         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
4016         q_u->firstjob = firstjob;
4017         q_u->numofjobs = numofjobs;
4018         q_u->level = level;
4019         q_u->buffer= buffer;
4020         q_u->offered = offered;
4021         return True;
4022 }
4023
4024 /*******************************************************************
4025 ********************************************************************/  
4026
4027 BOOL spoolss_io_q_enumjobs(const char *desc, SPOOL_Q_ENUMJOBS *q_u, prs_struct *ps, int depth)
4028 {
4029         prs_debug(ps, depth, desc, "spoolss_io_q_enumjobs");
4030         depth++;
4031
4032         if (!prs_align(ps))
4033                 return False;
4034
4035         if (!smb_io_pol_hnd("printer handle",&q_u->handle, ps, depth))
4036                 return False;
4037                 
4038         if (!prs_uint32("firstjob", ps, depth, &q_u->firstjob))
4039                 return False;
4040         if (!prs_uint32("numofjobs", ps, depth, &q_u->numofjobs))
4041                 return False;
4042         if (!prs_uint32("level", ps, depth, &q_u->level))
4043                 return False;
4044
4045         if (!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
4046                 return False;   
4047
4048         if(!prs_align(ps))
4049                 return False;
4050
4051         if (!prs_uint32("offered", ps, depth, &q_u->offered))
4052                 return False;
4053
4054         return True;
4055 }
4056
4057 /*******************************************************************
4058 ********************************************************************/  
4059
4060 BOOL spoolss_io_r_schedulejob(const char *desc, SPOOL_R_SCHEDULEJOB *r_u, prs_struct *ps, int depth)
4061 {               
4062         prs_debug(ps, depth, desc, "spoolss_io_r_schedulejob");
4063         depth++;
4064
4065         if(!prs_align(ps))
4066                 return False;
4067         
4068         if(!prs_werror("status", ps, depth, &r_u->status))
4069                 return False;
4070
4071         return True;
4072 }
4073
4074 /*******************************************************************
4075 ********************************************************************/  
4076
4077 BOOL spoolss_io_q_schedulejob(const char *desc, SPOOL_Q_SCHEDULEJOB *q_u, prs_struct *ps, int depth)
4078 {
4079         prs_debug(ps, depth, desc, "spoolss_io_q_schedulejob");
4080         depth++;
4081
4082         if(!prs_align(ps))
4083                 return False;
4084
4085         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
4086                 return False;
4087         if(!prs_uint32("jobid", ps, depth, &q_u->jobid))
4088                 return False;
4089
4090         return True;
4091 }
4092
4093 /*******************************************************************
4094 ********************************************************************/  
4095
4096 BOOL spoolss_io_r_setjob(const char *desc, SPOOL_R_SETJOB *r_u, prs_struct *ps, int depth)
4097 {               
4098         prs_debug(ps, depth, desc, "spoolss_io_r_setjob");
4099         depth++;
4100
4101         if(!prs_align(ps))
4102                 return False;
4103         
4104         if(!prs_werror("status", ps, depth, &r_u->status))
4105                 return False;
4106
4107         return True;
4108 }
4109
4110 /*******************************************************************
4111 ********************************************************************/  
4112
4113 BOOL spoolss_io_q_setjob(const char *desc, SPOOL_Q_SETJOB *q_u, prs_struct *ps, int depth)
4114 {
4115         prs_debug(ps, depth, desc, "spoolss_io_q_setjob");
4116         depth++;
4117
4118         if(!prs_align(ps))
4119                 return False;
4120
4121         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
4122                 return False;
4123         if(!prs_uint32("jobid", ps, depth, &q_u->jobid))
4124                 return False;
4125         /* 
4126          * level is usually 0. If (level!=0) then I'm in trouble !
4127          * I will try to generate setjob command with level!=0, one day.
4128          */
4129         if(!prs_uint32("level", ps, depth, &q_u->level))
4130                 return False;
4131         if(!prs_uint32("command", ps, depth, &q_u->command))
4132                 return False;
4133
4134         return True;
4135 }
4136
4137 /*******************************************************************
4138  Parse a SPOOL_R_ENUMPRINTERDRIVERS structure.
4139 ********************************************************************/  
4140
4141 BOOL spoolss_io_r_enumprinterdrivers(const char *desc, SPOOL_R_ENUMPRINTERDRIVERS *r_u, prs_struct *ps, int depth)
4142 {
4143         prs_debug(ps, depth, desc, "spoolss_io_r_enumprinterdrivers");
4144         depth++;
4145
4146         if (!prs_align(ps))
4147                 return False;
4148                 
4149         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
4150                 return False;
4151
4152         if (!prs_align(ps))
4153                 return False;
4154                 
4155         if (!prs_uint32("needed", ps, depth, &r_u->needed))
4156                 return False;
4157                 
4158         if (!prs_uint32("returned", ps, depth, &r_u->returned))
4159                 return False;
4160                 
4161         if (!prs_werror("status", ps, depth, &r_u->status))
4162                 return False;
4163
4164         return True;            
4165 }
4166
4167 /*******************************************************************
4168  * init a structure.
4169  ********************************************************************/
4170
4171 BOOL make_spoolss_q_enumprinterdrivers(SPOOL_Q_ENUMPRINTERDRIVERS *q_u,
4172                                 const char *name,
4173                                 const char *environment,
4174                                 uint32 level,
4175                                 RPC_BUFFER *buffer, uint32 offered)
4176 {
4177         init_buf_unistr2(&q_u->name, &q_u->name_ptr, name);
4178         init_buf_unistr2(&q_u->environment, &q_u->environment_ptr, environment);
4179
4180         q_u->level=level;
4181         q_u->buffer=buffer;
4182         q_u->offered=offered;
4183
4184         return True;
4185 }
4186
4187 /*******************************************************************
4188  Parse a SPOOL_Q_ENUMPRINTERDRIVERS structure.
4189 ********************************************************************/  
4190
4191 BOOL spoolss_io_q_enumprinterdrivers(const char *desc, SPOOL_Q_ENUMPRINTERDRIVERS *q_u, prs_struct *ps, int depth)
4192 {
4193
4194         prs_debug(ps, depth, desc, "spoolss_io_q_enumprinterdrivers");
4195         depth++;
4196
4197         if (!prs_align(ps))
4198                 return False;
4199                 
4200         if (!prs_uint32("name_ptr", ps, depth, &q_u->name_ptr))
4201                 return False;
4202         if (!smb_io_unistr2("", &q_u->name, q_u->name_ptr,ps, depth))
4203                 return False;
4204                 
4205         if (!prs_align(ps))
4206                 return False;
4207         if (!prs_uint32("environment_ptr", ps, depth, &q_u->environment_ptr))
4208                 return False;
4209         if (!smb_io_unistr2("", &q_u->environment, q_u->environment_ptr, ps, depth))
4210                 return False;
4211                 
4212         if (!prs_align(ps))
4213                 return False;
4214         if (!prs_uint32("level", ps, depth, &q_u->level))
4215                 return False;
4216                 
4217         if (!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
4218                 return False;
4219
4220         if (!prs_align(ps))
4221                 return False;
4222                 
4223         if (!prs_uint32("offered", ps, depth, &q_u->offered))
4224                 return False;
4225
4226         return True;
4227 }
4228
4229 /*******************************************************************
4230 ********************************************************************/  
4231
4232 BOOL spoolss_io_q_enumforms(const char *desc, SPOOL_Q_ENUMFORMS *q_u, prs_struct *ps, int depth)
4233 {
4234
4235         prs_debug(ps, depth, desc, "spoolss_io_q_enumforms");
4236         depth++;
4237
4238         if (!prs_align(ps))
4239                 return False;                   
4240         if (!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
4241                 return False;           
4242         if (!prs_uint32("level", ps, depth, &q_u->level))
4243                 return False;   
4244         
4245         if (!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
4246                 return False;
4247
4248         if (!prs_align(ps))
4249                 return False;
4250         if (!prs_uint32("offered", ps, depth, &q_u->offered))
4251                 return False;
4252
4253         return True;
4254 }
4255
4256 /*******************************************************************
4257 ********************************************************************/  
4258
4259 BOOL spoolss_io_r_enumforms(const char *desc, SPOOL_R_ENUMFORMS *r_u, prs_struct *ps, int depth)
4260 {
4261         prs_debug(ps, depth, desc, "spoolss_io_r_enumforms");
4262         depth++;
4263
4264         if (!prs_align(ps))
4265                 return False;
4266                 
4267         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
4268                 return False;
4269
4270         if (!prs_align(ps))
4271                 return False;
4272                 
4273         if (!prs_uint32("size of buffer needed", ps, depth, &r_u->needed))
4274                 return False;
4275                 
4276         if (!prs_uint32("numofforms", ps, depth, &r_u->numofforms))
4277                 return False;
4278                 
4279         if (!prs_werror("status", ps, depth, &r_u->status))
4280                 return False;
4281
4282         return True;
4283 }
4284
4285 /*******************************************************************
4286 ********************************************************************/  
4287
4288 BOOL spoolss_io_q_getform(const char *desc, SPOOL_Q_GETFORM *q_u, prs_struct *ps, int depth)
4289 {
4290
4291         prs_debug(ps, depth, desc, "spoolss_io_q_getform");
4292         depth++;
4293
4294         if (!prs_align(ps))
4295                 return False;                   
4296         if (!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
4297                 return False;           
4298         if (!smb_io_unistr2("", &q_u->formname,True,ps,depth))
4299                 return False;
4300
4301         if (!prs_align(ps))
4302                 return False;
4303
4304         if (!prs_uint32("level", ps, depth, &q_u->level))
4305                 return False;   
4306         
4307         if (!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
4308                 return False;
4309
4310         if (!prs_align(ps))
4311                 return False;
4312         if (!prs_uint32("offered", ps, depth, &q_u->offered))
4313                 return False;
4314
4315         return True;
4316 }
4317
4318 /*******************************************************************
4319 ********************************************************************/  
4320
4321 BOOL spoolss_io_r_getform(const char *desc, SPOOL_R_GETFORM *r_u, prs_struct *ps, int depth)
4322 {
4323         prs_debug(ps, depth, desc, "spoolss_io_r_getform");
4324         depth++;
4325
4326         if (!prs_align(ps))
4327                 return False;
4328                 
4329         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
4330                 return False;
4331
4332         if (!prs_align(ps))
4333                 return False;
4334                 
4335         if (!prs_uint32("size of buffer needed", ps, depth, &r_u->needed))
4336                 return False;
4337                 
4338         if (!prs_werror("status", ps, depth, &r_u->status))
4339                 return False;
4340
4341         return True;
4342 }
4343
4344 /*******************************************************************
4345  Parse a SPOOL_R_ENUMPORTS structure.
4346 ********************************************************************/  
4347
4348 BOOL spoolss_io_r_enumports(const char *desc, SPOOL_R_ENUMPORTS *r_u, prs_struct *ps, int depth)
4349 {
4350         prs_debug(ps, depth, desc, "spoolss_io_r_enumports");
4351         depth++;
4352
4353         if (!prs_align(ps))
4354                 return False;
4355                 
4356         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
4357                 return False;
4358
4359         if (!prs_align(ps))
4360                 return False;
4361                 
4362         if (!prs_uint32("needed", ps, depth, &r_u->needed))
4363                 return False;
4364                 
4365         if (!prs_uint32("returned", ps, depth, &r_u->returned))
4366                 return False;
4367                 
4368         if (!prs_werror("status", ps, depth, &r_u->status))
4369                 return False;
4370
4371         return True;            
4372 }
4373
4374 /*******************************************************************
4375 ********************************************************************/  
4376
4377 BOOL spoolss_io_q_enumports(const char *desc, SPOOL_Q_ENUMPORTS *q_u, prs_struct *ps, int depth)
4378 {
4379         prs_debug(ps, depth, desc, "");
4380         depth++;
4381
4382         if (!prs_align(ps))
4383                 return False;
4384
4385         if (!prs_uint32("", ps, depth, &q_u->name_ptr))
4386                 return False;
4387         if (!smb_io_unistr2("", &q_u->name,True,ps,depth))
4388                 return False;
4389
4390         if (!prs_align(ps))
4391                 return False;
4392         if (!prs_uint32("level", ps, depth, &q_u->level))
4393                 return False;
4394                 
4395         if (!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
4396                 return False;
4397
4398         if (!prs_align(ps))
4399                 return False;
4400         if (!prs_uint32("offered", ps, depth, &q_u->offered))
4401                 return False;
4402
4403         return True;
4404 }
4405
4406 /*******************************************************************
4407  Parse a SPOOL_PRINTER_INFO_LEVEL_1 structure.
4408 ********************************************************************/  
4409
4410 BOOL spool_io_printer_info_level_1(const char *desc, SPOOL_PRINTER_INFO_LEVEL_1 *il, prs_struct *ps, int depth)
4411 {       
4412         prs_debug(ps, depth, desc, "spool_io_printer_info_level_1");
4413         depth++;
4414                 
4415         if(!prs_align(ps))
4416                 return False;
4417
4418         if(!prs_uint32("flags", ps, depth, &il->flags))
4419                 return False;
4420         if(!prs_uint32("description_ptr", ps, depth, &il->description_ptr))
4421                 return False;
4422         if(!prs_uint32("name_ptr", ps, depth, &il->name_ptr))
4423                 return False;
4424         if(!prs_uint32("comment_ptr", ps, depth, &il->comment_ptr))
4425                 return False;
4426                 
4427         if(!smb_io_unistr2("description", &il->description, il->description_ptr, ps, depth))
4428                 return False;
4429         if(!smb_io_unistr2("name", &il->name, il->name_ptr, ps, depth))
4430                 return False;
4431         if(!smb_io_unistr2("comment", &il->comment, il->comment_ptr, ps, depth))
4432                 return False;
4433
4434         return True;
4435 }
4436
4437 /*******************************************************************
4438  Parse a SPOOL_PRINTER_INFO_LEVEL_3 structure.
4439 ********************************************************************/  
4440
4441 BOOL spool_io_printer_info_level_3(const char *desc, SPOOL_PRINTER_INFO_LEVEL_3 *il, prs_struct *ps, int depth)
4442 {       
4443         prs_debug(ps, depth, desc, "spool_io_printer_info_level_3");
4444         depth++;
4445                 
4446         if(!prs_align(ps))
4447                 return False;
4448
4449         if(!prs_uint32("secdesc_ptr", ps, depth, &il->secdesc_ptr))
4450                 return False;
4451
4452         return True;
4453 }
4454
4455 /*******************************************************************
4456  Parse a SPOOL_PRINTER_INFO_LEVEL_2 structure.
4457 ********************************************************************/  
4458
4459 BOOL spool_io_printer_info_level_2(const char *desc, SPOOL_PRINTER_INFO_LEVEL_2 *il, prs_struct *ps, int depth)
4460 {       
4461         prs_debug(ps, depth, desc, "spool_io_printer_info_level_2");
4462         depth++;
4463                 
4464         if(!prs_align(ps))
4465                 return False;
4466
4467         if(!prs_uint32("servername_ptr", ps, depth, &il->servername_ptr))
4468                 return False;
4469         if(!prs_uint32("printername_ptr", ps, depth, &il->printername_ptr))
4470                 return False;
4471         if(!prs_uint32("sharename_ptr", ps, depth, &il->sharename_ptr))
4472                 return False;
4473         if(!prs_uint32("portname_ptr", ps, depth, &il->portname_ptr))
4474                 return False;
4475
4476         if(!prs_uint32("drivername_ptr", ps, depth, &il->drivername_ptr))
4477                 return False;
4478         if(!prs_uint32("comment_ptr", ps, depth, &il->comment_ptr))
4479                 return False;
4480         if(!prs_uint32("location_ptr", ps, depth, &il->location_ptr))
4481                 return False;
4482         if(!prs_uint32("devmode_ptr", ps, depth, &il->devmode_ptr))
4483                 return False;
4484         if(!prs_uint32("sepfile_ptr", ps, depth, &il->sepfile_ptr))
4485                 return False;
4486         if(!prs_uint32("printprocessor_ptr", ps, depth, &il->printprocessor_ptr))
4487                 return False;
4488         if(!prs_uint32("datatype_ptr", ps, depth, &il->datatype_ptr))
4489                 return False;
4490         if(!prs_uint32("parameters_ptr", ps, depth, &il->parameters_ptr))
4491                 return False;
4492         if(!prs_uint32("secdesc_ptr", ps, depth, &il->secdesc_ptr))
4493                 return False;
4494
4495         if(!prs_uint32("attributes", ps, depth, &il->attributes))
4496                 return False;
4497         if(!prs_uint32("priority", ps, depth, &il->priority))
4498                 return False;
4499         if(!prs_uint32("default_priority", ps, depth, &il->default_priority))
4500                 return False;
4501         if(!prs_uint32("starttime", ps, depth, &il->starttime))
4502                 return False;
4503         if(!prs_uint32("untiltime", ps, depth, &il->untiltime))
4504                 return False;
4505         if(!prs_uint32("status", ps, depth, &il->status))
4506                 return False;
4507         if(!prs_uint32("cjobs", ps, depth, &il->cjobs))
4508                 return False;
4509         if(!prs_uint32("averageppm", ps, depth, &il->averageppm))
4510                 return False;
4511
4512         if(!smb_io_unistr2("servername", &il->servername, il->servername_ptr, ps, depth))
4513                 return False;
4514         if(!smb_io_unistr2("printername", &il->printername, il->printername_ptr, ps, depth))
4515                 return False;
4516         if(!smb_io_unistr2("sharename", &il->sharename, il->sharename_ptr, ps, depth))
4517                 return False;
4518         if(!smb_io_unistr2("portname", &il->portname, il->portname_ptr, ps, depth))
4519                 return False;
4520         if(!smb_io_unistr2("drivername", &il->drivername, il->drivername_ptr, ps, depth))
4521                 return False;
4522         if(!smb_io_unistr2("comment", &il->comment, il->comment_ptr, ps, depth))
4523                 return False;
4524         if(!smb_io_unistr2("location", &il->location, il->location_ptr, ps, depth))
4525                 return False;
4526         if(!smb_io_unistr2("sepfile", &il->sepfile, il->sepfile_ptr, ps, depth))
4527                 return False;
4528         if(!smb_io_unistr2("printprocessor", &il->printprocessor, il->printprocessor_ptr, ps, depth))
4529                 return False;
4530         if(!smb_io_unistr2("datatype", &il->datatype, il->datatype_ptr, ps, depth))
4531                 return False;
4532         if(!smb_io_unistr2("parameters", &il->parameters, il->parameters_ptr, ps, depth))
4533                 return False;
4534
4535         return True;
4536 }
4537
4538 BOOL spool_io_printer_info_level_7(const char *desc, SPOOL_PRINTER_INFO_LEVEL_7 *il, prs_struct *ps, int depth)
4539 {       
4540         prs_debug(ps, depth, desc, "spool_io_printer_info_level_7");
4541         depth++;
4542                 
4543         if(!prs_align(ps))
4544                 return False;
4545
4546         if(!prs_uint32("guid_ptr", ps, depth, &il->guid_ptr))
4547                 return False;
4548         if(!prs_uint32("action", ps, depth, &il->action))
4549                 return False;
4550
4551         if(!smb_io_unistr2("servername", &il->guid, il->guid_ptr, ps, depth))
4552                 return False;
4553         return True;
4554 }
4555
4556 /*******************************************************************
4557 ********************************************************************/  
4558
4559 BOOL spool_io_printer_info_level(const char *desc, SPOOL_PRINTER_INFO_LEVEL *il, prs_struct *ps, int depth)
4560 {
4561         prs_debug(ps, depth, desc, "spool_io_printer_info_level");
4562         depth++;
4563
4564         if(!prs_align(ps))
4565                 return False;
4566         if(!prs_uint32("level", ps, depth, &il->level))
4567                 return False;
4568         if(!prs_uint32("info_ptr", ps, depth, &il->info_ptr))
4569                 return False;
4570         
4571         /* if no struct inside just return */
4572         if (il->info_ptr==0) {
4573                 if (UNMARSHALLING(ps)) {
4574                         il->info_1=NULL;
4575                         il->info_2=NULL;
4576                 }
4577                 return True;
4578         }
4579                         
4580         switch (il->level) {
4581                 /*
4582                  * level 0 is used by setprinter when managing the queue
4583                  * (hold, stop, start a queue)
4584                  */
4585                 case 0:
4586                         break;
4587                 /* DOCUMENT ME!!! What is level 1 used for? */
4588                 case 1:
4589                 {
4590                         if (UNMARSHALLING(ps)) {
4591                                 if ((il->info_1=PRS_ALLOC_MEM(ps,SPOOL_PRINTER_INFO_LEVEL_1,1)) == NULL)
4592                                         return False;
4593                         }
4594                         if (!spool_io_printer_info_level_1("", il->info_1, ps, depth))
4595                                 return False;
4596                         break;          
4597                 }
4598                 /* 
4599                  * level 2 is used by addprinter
4600                  * and by setprinter when updating printer's info
4601                  */     
4602                 case 2:
4603                         if (UNMARSHALLING(ps)) {
4604                                 if ((il->info_2=PRS_ALLOC_MEM(ps,SPOOL_PRINTER_INFO_LEVEL_2,1)) == NULL)
4605                                         return False;
4606                         }
4607                         if (!spool_io_printer_info_level_2("", il->info_2, ps, depth))
4608                                 return False;
4609                         break;          
4610                 /* DOCUMENT ME!!! What is level 3 used for? */
4611                 case 3:
4612                 {
4613                         if (UNMARSHALLING(ps)) {
4614                                 if ((il->info_3=PRS_ALLOC_MEM(ps,SPOOL_PRINTER_INFO_LEVEL_3,1)) == NULL)
4615                                         return False;
4616                         }
4617                         if (!spool_io_printer_info_level_3("", il->info_3, ps, depth))
4618                                 return False;
4619                         break;          
4620                 }
4621                 case 7:
4622                         if (UNMARSHALLING(ps))
4623                                 if ((il->info_7=PRS_ALLOC_MEM(ps,SPOOL_PRINTER_INFO_LEVEL_7,1)) == NULL)
4624                                         return False;
4625                         if (!spool_io_printer_info_level_7("", il->info_7, ps, depth))
4626                                 return False;
4627                         break;
4628         }
4629
4630         return True;
4631 }
4632
4633 /*******************************************************************
4634 ********************************************************************/  
4635
4636 BOOL spoolss_io_q_addprinterex(const char *desc, SPOOL_Q_ADDPRINTEREX *q_u, prs_struct *ps, int depth)
4637 {
4638         uint32 ptr_sec_desc = 0;
4639
4640         prs_debug(ps, depth, desc, "spoolss_io_q_addprinterex");
4641         depth++;
4642
4643         if(!prs_align(ps))
4644                 return False;
4645
4646         if (!prs_io_unistr2_p("ptr", ps, depth, &q_u->server_name))
4647                 return False;
4648         if (!prs_io_unistr2("servername", ps, depth, q_u->server_name))
4649                 return False;
4650
4651         if(!prs_align(ps))
4652                 return False;
4653
4654         if(!prs_uint32("info_level", ps, depth, &q_u->level))
4655                 return False;
4656         
4657         if(!spool_io_printer_info_level("", &q_u->info, ps, depth))
4658                 return False;
4659         
4660         if (!spoolss_io_devmode_cont(desc, &q_u->devmode_ctr, ps, depth))
4661                 return False;
4662
4663         if(!prs_align(ps))
4664                 return False;
4665
4666         switch (q_u->level) {
4667                 case 2:
4668                         ptr_sec_desc = q_u->info.info_2->secdesc_ptr;
4669                         break;
4670                 case 3:
4671                         ptr_sec_desc = q_u->info.info_3->secdesc_ptr;
4672                         break;
4673         }
4674         if (ptr_sec_desc) {
4675                 if (!sec_io_desc_buf(desc, &q_u->secdesc_ctr, ps, depth))
4676                         return False;
4677         } else {
4678                 uint32 dummy;
4679
4680                 /* Parse a NULL security descriptor.  This should really
4681                         happen inside the sec_io_desc_buf() function. */
4682
4683                 prs_debug(ps, depth, "", "sec_io_desc_buf");
4684                 if (!prs_uint32("size", ps, depth + 1, &dummy))
4685                         return False;
4686                 if (!prs_uint32("ptr", ps, depth + 1, &dummy))
4687                         return False;
4688         }
4689
4690         if(!prs_uint32("user_switch", ps, depth, &q_u->user_switch))
4691                 return False;
4692         if(!spool_io_user_level("", &q_u->user_ctr, ps, depth))
4693                 return False;
4694
4695         return True;
4696 }
4697
4698 /*******************************************************************
4699 ********************************************************************/  
4700
4701 BOOL spoolss_io_r_addprinterex(const char *desc, SPOOL_R_ADDPRINTEREX *r_u, 
4702                                prs_struct *ps, int depth)
4703 {
4704         prs_debug(ps, depth, desc, "spoolss_io_r_addprinterex");
4705         depth++;
4706         
4707         if(!smb_io_pol_hnd("printer handle",&r_u->handle,ps,depth))
4708                 return False;
4709
4710         if(!prs_werror("status", ps, depth, &r_u->status))
4711                 return False;
4712
4713         return True;
4714 }
4715
4716 /*******************************************************************
4717 ********************************************************************/  
4718
4719 BOOL spool_io_printer_driver_info_level_3(const char *desc, SPOOL_PRINTER_DRIVER_INFO_LEVEL_3 **q_u, 
4720                                           prs_struct *ps, int depth)
4721 {       
4722         SPOOL_PRINTER_DRIVER_INFO_LEVEL_3 *il;
4723         
4724         prs_debug(ps, depth, desc, "spool_io_printer_driver_info_level_3");
4725         depth++;
4726                 
4727         /* reading */
4728         if (UNMARSHALLING(ps)) {
4729                 il=PRS_ALLOC_MEM(ps,SPOOL_PRINTER_DRIVER_INFO_LEVEL_3,1);
4730                 if(il == NULL)
4731                         return False;
4732                 *q_u=il;
4733         }
4734         else {
4735                 il=*q_u;
4736         }
4737         
4738         if(!prs_align(ps))
4739                 return False;
4740
4741         if(!prs_uint32("cversion", ps, depth, &il->cversion))
4742                 return False;
4743         if(!prs_uint32("name", ps, depth, &il->name_ptr))
4744                 return False;
4745         if(!prs_uint32("environment", ps, depth, &il->environment_ptr))
4746                 return False;
4747         if(!prs_uint32("driverpath", ps, depth, &il->driverpath_ptr))
4748                 return False;
4749         if(!prs_uint32("datafile", ps, depth, &il->datafile_ptr))
4750                 return False;
4751         if(!prs_uint32("configfile", ps, depth, &il->configfile_ptr))
4752                 return False;
4753         if(!prs_uint32("helpfile", ps, depth, &il->helpfile_ptr))
4754                 return False;
4755         if(!prs_uint32("monitorname", ps, depth, &il->monitorname_ptr))
4756                 return False;
4757         if(!prs_uint32("defaultdatatype", ps, depth, &il->defaultdatatype_ptr))
4758                 return False;
4759         if(!prs_uint32("dependentfilessize", ps, depth, &il->dependentfilessize))
4760                 return False;
4761         if(!prs_uint32("dependentfiles", ps, depth, &il->dependentfiles_ptr))
4762                 return False;
4763
4764         if(!prs_align(ps))
4765                 return False;
4766         
4767         if(!smb_io_unistr2("name", &il->name, il->name_ptr, ps, depth))
4768                 return False;
4769         if(!smb_io_unistr2("environment", &il->environment, il->environment_ptr, ps, depth))
4770                 return False;
4771         if(!smb_io_unistr2("driverpath", &il->driverpath, il->driverpath_ptr, ps, depth))
4772                 return False;
4773         if(!smb_io_unistr2("datafile", &il->datafile, il->datafile_ptr, ps, depth))
4774                 return False;
4775         if(!smb_io_unistr2("configfile", &il->configfile, il->configfile_ptr, ps, depth))
4776                 return False;
4777         if(!smb_io_unistr2("helpfile", &il->helpfile, il->helpfile_ptr, ps, depth))
4778                 return False;
4779         if(!smb_io_unistr2("monitorname", &il->monitorname, il->monitorname_ptr, ps, depth))
4780                 return False;
4781         if(!smb_io_unistr2("defaultdatatype", &il->defaultdatatype, il->defaultdatatype_ptr, ps, depth))
4782                 return False;
4783
4784         if(!prs_align(ps))
4785                 return False;
4786                 
4787         if (il->dependentfiles_ptr)
4788                 smb_io_buffer5("", &il->dependentfiles, ps, depth);
4789
4790         return True;
4791 }
4792
4793 /*******************************************************************
4794 parse a SPOOL_PRINTER_DRIVER_INFO_LEVEL_6 structure
4795 ********************************************************************/  
4796
4797 BOOL spool_io_printer_driver_info_level_6(const char *desc, SPOOL_PRINTER_DRIVER_INFO_LEVEL_6 **q_u, 
4798                                           prs_struct *ps, int depth)
4799 {       
4800         SPOOL_PRINTER_DRIVER_INFO_LEVEL_6 *il;
4801         
4802         prs_debug(ps, depth, desc, "spool_io_printer_driver_info_level_6");
4803         depth++;
4804                 
4805         /* reading */
4806         if (UNMARSHALLING(ps)) {
4807                 il=PRS_ALLOC_MEM(ps,SPOOL_PRINTER_DRIVER_INFO_LEVEL_6,1);
4808                 if(il == NULL)
4809                         return False;
4810                 *q_u=il;
4811         }
4812         else {
4813                 il=*q_u;
4814         }
4815         
4816         if(!prs_align(ps))
4817                 return False;
4818
4819         /* 
4820          * I know this seems weird, but I have no other explanation.
4821          * This is observed behavior on both NT4 and 2K servers.
4822          * --jerry
4823          */
4824          
4825         if (!prs_align_uint64(ps))
4826                 return False;
4827
4828         /* parse the main elements the packet */
4829
4830         if(!prs_uint32("cversion       ", ps, depth, &il->version))
4831                 return False;
4832         if(!prs_uint32("name           ", ps, depth, &il->name_ptr))
4833                 return False;
4834         if(!prs_uint32("environment    ", ps, depth, &il->environment_ptr))
4835                 return False;
4836         if(!prs_uint32("driverpath     ", ps, depth, &il->driverpath_ptr))
4837                 return False;
4838         if(!prs_uint32("datafile       ", ps, depth, &il->datafile_ptr))
4839                 return False;
4840         if(!prs_uint32("configfile     ", ps, depth, &il->configfile_ptr))
4841                 return False;
4842         if(!prs_uint32("helpfile       ", ps, depth, &il->helpfile_ptr))
4843                 return False;
4844         if(!prs_uint32("monitorname    ", ps, depth, &il->monitorname_ptr))
4845                 return False;
4846         if(!prs_uint32("defaultdatatype", ps, depth, &il->defaultdatatype_ptr))
4847                 return False;
4848         if(!prs_uint32("dependentfiles ", ps, depth, &il->dependentfiles_len))
4849                 return False;
4850         if(!prs_uint32("dependentfiles ", ps, depth, &il->dependentfiles_ptr))
4851                 return False;
4852         if(!prs_uint32("previousnames  ", ps, depth, &il->previousnames_len))
4853                 return False;
4854         if(!prs_uint32("previousnames  ", ps, depth, &il->previousnames_ptr))
4855                 return False;
4856         if(!smb_io_time("driverdate    ", &il->driverdate, ps, depth))
4857                 return False;
4858         if(!prs_uint32("dummy4         ", ps, depth, &il->dummy4))
4859                 return False;
4860         if(!prs_uint64("driverversion  ", ps, depth, &il->driverversion))
4861                 return False;
4862         if(!prs_uint32("mfgname        ", ps, depth, &il->mfgname_ptr))
4863                 return False;
4864         if(!prs_uint32("oemurl         ", ps, depth, &il->oemurl_ptr))
4865                 return False;
4866         if(!prs_uint32("hardwareid     ", ps, depth, &il->hardwareid_ptr))
4867                 return False;
4868         if(!prs_uint32("provider       ", ps, depth, &il->provider_ptr))
4869                 return False;
4870
4871         /* parse the structures in the packet */
4872
4873         if(!smb_io_unistr2("name", &il->name, il->name_ptr, ps, depth))
4874                 return False;
4875         if(!prs_align(ps))
4876                 return False;
4877
4878         if(!smb_io_unistr2("environment", &il->environment, il->environment_ptr, ps, depth))
4879                 return False;
4880         if(!prs_align(ps))
4881                 return False;
4882
4883         if(!smb_io_unistr2("driverpath", &il->driverpath, il->driverpath_ptr, ps, depth))
4884                 return False;
4885         if(!prs_align(ps))
4886                 return False;
4887
4888         if(!smb_io_unistr2("datafile", &il->datafile, il->datafile_ptr, ps, depth))
4889                 return False;
4890         if(!prs_align(ps))
4891                 return False;
4892
4893         if(!smb_io_unistr2("configfile", &il->configfile, il->configfile_ptr, ps, depth))
4894                 return False;
4895         if(!prs_align(ps))
4896                 return False;
4897
4898         if(!smb_io_unistr2("helpfile", &il->helpfile, il->helpfile_ptr, ps, depth))
4899                 return False;
4900         if(!prs_align(ps))
4901                 return False;
4902
4903         if(!smb_io_unistr2("monitorname", &il->monitorname, il->monitorname_ptr, ps, depth))
4904                 return False;
4905         if(!prs_align(ps))
4906                 return False;
4907
4908         if(!smb_io_unistr2("defaultdatatype", &il->defaultdatatype, il->defaultdatatype_ptr, ps, depth))
4909                 return False;
4910         if(!prs_align(ps))
4911                 return False;
4912         if (il->dependentfiles_ptr) {
4913                 if(!smb_io_buffer5("dependentfiles", &il->dependentfiles, ps, depth))
4914                         return False;
4915                 if(!prs_align(ps))
4916                         return False;
4917         }
4918         if (il->previousnames_ptr) {
4919                 if(!smb_io_buffer5("previousnames", &il->previousnames, ps, depth))
4920                         return False;
4921                 if(!prs_align(ps))
4922                         return False;
4923         }
4924         if(!smb_io_unistr2("mfgname", &il->mfgname, il->mfgname_ptr, ps, depth))
4925                 return False;
4926         if(!prs_align(ps))
4927                 return False;
4928         if(!smb_io_unistr2("oemurl", &il->oemurl, il->oemurl_ptr, ps, depth))
4929                 return False;
4930         if(!prs_align(ps))
4931                 return False;
4932         if(!smb_io_unistr2("hardwareid", &il->hardwareid, il->hardwareid_ptr, ps, depth))
4933                 return False;
4934         if(!prs_align(ps))
4935                 return False;
4936         if(!smb_io_unistr2("provider", &il->provider, il->provider_ptr, ps, depth))
4937                 return False;
4938
4939         return True;
4940 }
4941
4942 /*******************************************************************
4943  convert a buffer of UNICODE strings null terminated
4944  the buffer is terminated by a NULL
4945  
4946  convert to an dos codepage array (null terminated)
4947  
4948  dynamically allocate memory
4949  
4950 ********************************************************************/  
4951 static BOOL uniarray_2_dosarray(BUFFER5 *buf5, fstring **ar)
4952 {
4953         fstring f, *tar;
4954         int n = 0;
4955         char *src;
4956
4957         if (buf5==NULL)
4958                 return False;
4959
4960         src = (char *)buf5->buffer;
4961         *ar = NULL;
4962
4963         while (src < ((char *)buf5->buffer) + buf5->buf_len*2) {
4964                 rpcstr_pull(f, src, sizeof(f)-1, -1, STR_TERMINATE);
4965                 src = skip_unibuf(src, 2*buf5->buf_len - PTR_DIFF(src,buf5->buffer));
4966                 tar = SMB_REALLOC_ARRAY(*ar, fstring, n+2);
4967                 if (!tar)
4968                         return False;
4969                 else
4970                         *ar = tar;
4971                 fstrcpy((*ar)[n], f);
4972                 n++;
4973         }
4974         fstrcpy((*ar)[n], "");
4975  
4976         return True;
4977 }
4978
4979
4980
4981
4982 /*******************************************************************
4983  read a UNICODE array with null terminated strings 
4984  and null terminated array 
4985  and size of array at beginning
4986 ********************************************************************/  
4987
4988 BOOL smb_io_unibuffer(const char *desc, UNISTR2 *buffer, prs_struct *ps, int depth)
4989 {
4990         if (buffer==NULL) return False;
4991
4992         buffer->offset=0;
4993         buffer->uni_str_len=buffer->uni_max_len;
4994         
4995         if(!prs_uint32("buffer_size", ps, depth, &buffer->uni_max_len))
4996                 return False;
4997
4998         if(!prs_unistr2(True, "buffer     ", ps, depth, buffer))
4999                 return False;
5000
5001         return True;
5002 }
5003
5004 /*******************************************************************
5005 ********************************************************************/  
5006
5007 BOOL spool_io_printer_driver_info_level(const char *desc, SPOOL_PRINTER_DRIVER_INFO_LEVEL *il, prs_struct *ps, int depth)
5008 {
5009         prs_debug(ps, depth, desc, "spool_io_printer_driver_info_level");
5010         depth++;
5011
5012         if(!prs_align(ps))
5013                 return False;
5014         if(!prs_uint32("level", ps, depth, &il->level))
5015                 return False;
5016         if(!prs_uint32("ptr", ps, depth, &il->ptr))
5017                 return False;
5018
5019         if (il->ptr==0)
5020                 return True;
5021                 
5022         switch (il->level) {
5023                 case 3:
5024                         if(!spool_io_printer_driver_info_level_3("", &il->info_3, ps, depth))
5025                                 return False;
5026                         break;          
5027                 case 6:
5028                         if(!spool_io_printer_driver_info_level_6("", &il->info_6, ps, depth))
5029                                 return False;
5030                         break;          
5031         default:
5032                 return False;
5033         }
5034
5035         return True;
5036 }
5037
5038 /*******************************************************************
5039  init a SPOOL_Q_ADDPRINTERDRIVER struct
5040  ******************************************************************/
5041
5042 BOOL make_spoolss_q_addprinterdriver(TALLOC_CTX *mem_ctx,
5043                                 SPOOL_Q_ADDPRINTERDRIVER *q_u, const char* srv_name, 
5044                                 uint32 level, PRINTER_DRIVER_CTR *info)
5045 {
5046         DEBUG(5,("make_spoolss_q_addprinterdriver\n"));
5047         
5048         q_u->server_name_ptr = (srv_name!=NULL)?1:0;
5049         init_unistr2(&q_u->server_name, srv_name, UNI_STR_TERMINATE);
5050         
5051         q_u->level = level;
5052         
5053         q_u->info.level = level;
5054         q_u->info.ptr = (info!=NULL)?1:0;
5055         switch (level)
5056         {
5057         /* info level 3 is supported by Windows 95/98, WinNT and Win2k */
5058         case 3 :
5059                 make_spoolss_driver_info_3(mem_ctx, &q_u->info.info_3, info->info3);
5060                 break;
5061                 
5062         default:
5063                 DEBUG(0,("make_spoolss_q_addprinterdriver: Unknown info level [%d]\n", level));
5064                 break;
5065         }
5066         
5067         return True;
5068 }
5069
5070 BOOL make_spoolss_driver_info_3(TALLOC_CTX *mem_ctx, 
5071         SPOOL_PRINTER_DRIVER_INFO_LEVEL_3 **spool_drv_info,
5072                                 DRIVER_INFO_3 *info3)
5073 {
5074         uint32          len = 0;
5075         uint16          *ptr = info3->dependentfiles;
5076         BOOL            done = False;
5077         BOOL            null_char = False;
5078         SPOOL_PRINTER_DRIVER_INFO_LEVEL_3 *inf;
5079
5080         if (!(inf=TALLOC_ZERO_P(mem_ctx, SPOOL_PRINTER_DRIVER_INFO_LEVEL_3)))
5081                 return False;
5082         
5083         inf->cversion   = info3->version;
5084         inf->name_ptr   = (info3->name.buffer!=NULL)?1:0;
5085         inf->environment_ptr    = (info3->architecture.buffer!=NULL)?1:0;
5086         inf->driverpath_ptr     = (info3->driverpath.buffer!=NULL)?1:0;
5087         inf->datafile_ptr       = (info3->datafile.buffer!=NULL)?1:0;
5088         inf->configfile_ptr     = (info3->configfile.buffer!=NULL)?1:0;
5089         inf->helpfile_ptr       = (info3->helpfile.buffer!=NULL)?1:0;
5090         inf->monitorname_ptr    = (info3->monitorname.buffer!=NULL)?1:0;
5091         inf->defaultdatatype_ptr        = (info3->defaultdatatype.buffer!=NULL)?1:0;
5092
5093         init_unistr2_from_unistr(&inf->name, &info3->name);
5094         init_unistr2_from_unistr(&inf->environment, &info3->architecture);
5095         init_unistr2_from_unistr(&inf->driverpath, &info3->driverpath);
5096         init_unistr2_from_unistr(&inf->datafile, &info3->datafile);
5097         init_unistr2_from_unistr(&inf->configfile, &info3->configfile);
5098         init_unistr2_from_unistr(&inf->helpfile, &info3->helpfile);
5099         init_unistr2_from_unistr(&inf->monitorname, &info3->monitorname);
5100         init_unistr2_from_unistr(&inf->defaultdatatype, &info3->defaultdatatype);
5101
5102         while (!done)
5103         {
5104                 switch (*ptr)
5105                 {
5106                         case 0:
5107                                 /* the null_char BOOL is used to help locate
5108                                    two '\0's back to back */
5109                                 if (null_char)
5110                                         done = True;
5111                                 else
5112                                         null_char = True;
5113                                 break;
5114                                         
5115                         default:
5116                                 null_char = False;
5117                                 ;;
5118                                 break;                          
5119                 }
5120                 len++;
5121                 ptr++;
5122         }
5123         inf->dependentfiles_ptr = (info3->dependentfiles != NULL) ? 1 : 0;
5124         inf->dependentfilessize = len;
5125         if(!make_spoolss_buffer5(mem_ctx, &inf->dependentfiles, len, info3->dependentfiles))
5126         {
5127                 SAFE_FREE(inf);
5128                 return False;
5129         }
5130         
5131         *spool_drv_info = inf;
5132         
5133         return True;
5134 }
5135
5136 /*******************************************************************
5137  make a BUFFER5 struct from a uint16*
5138  ******************************************************************/
5139 BOOL make_spoolss_buffer5(TALLOC_CTX *mem_ctx, BUFFER5 *buf5, uint32 len, uint16 *src)
5140 {
5141
5142         buf5->buf_len = len;
5143         if((buf5->buffer=(uint16*)TALLOC_MEMDUP(mem_ctx, src, sizeof(uint16)*len)) == NULL) {
5144                 DEBUG(0,("make_spoolss_buffer5: Unable to malloc memory for buffer!\n"));
5145                 return False;
5146         }
5147         
5148         return True;
5149 }
5150
5151 /*******************************************************************
5152  fill in the prs_struct for a ADDPRINTERDRIVER request PDU
5153  ********************************************************************/  
5154
5155 BOOL spoolss_io_q_addprinterdriver(const char *desc, SPOOL_Q_ADDPRINTERDRIVER *q_u, prs_struct *ps, int depth)
5156 {
5157         prs_debug(ps, depth, desc, "spoolss_io_q_addprinterdriver");
5158         depth++;
5159
5160         if(!prs_align(ps))
5161                 return False;
5162
5163         if(!prs_uint32("server_name_ptr", ps, depth, &q_u->server_name_ptr))
5164                 return False;
5165         if(!smb_io_unistr2("server_name", &q_u->server_name, q_u->server_name_ptr, ps, depth))
5166                 return False;
5167                 
5168         if(!prs_align(ps))
5169                 return False;
5170         if(!prs_uint32("info_level", ps, depth, &q_u->level))
5171                 return False;
5172
5173         if(!spool_io_printer_driver_info_level("", &q_u->info, ps, depth))
5174                 return False;
5175
5176         return True;
5177 }
5178
5179 /*******************************************************************
5180 ********************************************************************/  
5181
5182 BOOL spoolss_io_r_addprinterdriver(const char *desc, SPOOL_R_ADDPRINTERDRIVER *q_u, prs_struct *ps, int depth)
5183 {
5184         prs_debug(ps, depth, desc, "spoolss_io_r_addprinterdriver");
5185         depth++;
5186
5187         if(!prs_werror("status", ps, depth, &q_u->status))
5188                 return False;
5189
5190         return True;
5191 }
5192
5193 /*******************************************************************
5194  fill in the prs_struct for a ADDPRINTERDRIVER request PDU
5195  ********************************************************************/  
5196
5197 BOOL spoolss_io_q_addprinterdriverex(const char *desc, SPOOL_Q_ADDPRINTERDRIVEREX *q_u, prs_struct *ps, int depth)
5198 {
5199         prs_debug(ps, depth, desc, "spoolss_io_q_addprinterdriverex");
5200         depth++;
5201
5202         if(!prs_align(ps))
5203                 return False;
5204
5205         if(!prs_uint32("server_name_ptr", ps, depth, &q_u->server_name_ptr))
5206                 return False;
5207         if(!smb_io_unistr2("server_name", &q_u->server_name, q_u->server_name_ptr, ps, depth))
5208                 return False;
5209                 
5210         if(!prs_align(ps))
5211                 return False;
5212         if(!prs_uint32("info_level", ps, depth, &q_u->level))
5213                 return False;
5214
5215         if(!spool_io_printer_driver_info_level("", &q_u->info, ps, depth))
5216                 return False;
5217
5218         if(!prs_align(ps))
5219                 return False;
5220         if(!prs_uint32("copy flags", ps, depth, &q_u->copy_flags))
5221                 return False;
5222                 
5223         return True;
5224 }
5225
5226 /*******************************************************************
5227 ********************************************************************/  
5228
5229 BOOL spoolss_io_r_addprinterdriverex(const char *desc, SPOOL_R_ADDPRINTERDRIVEREX *q_u, prs_struct *ps, int depth)
5230 {
5231         prs_debug(ps, depth, desc, "spoolss_io_r_addprinterdriverex");
5232         depth++;
5233
5234         if(!prs_werror("status", ps, depth, &q_u->status))
5235                 return False;
5236
5237         return True;
5238 }
5239
5240 /*******************************************************************
5241 ********************************************************************/  
5242
5243 BOOL uni_2_asc_printer_driver_3(SPOOL_PRINTER_DRIVER_INFO_LEVEL_3 *uni,
5244                                 NT_PRINTER_DRIVER_INFO_LEVEL_3 **asc)
5245 {
5246         NT_PRINTER_DRIVER_INFO_LEVEL_3 *d;
5247         
5248         DEBUG(7,("uni_2_asc_printer_driver_3: Converting from UNICODE to ASCII\n"));
5249         
5250         if (*asc==NULL)
5251         {
5252                 *asc=SMB_MALLOC_P(NT_PRINTER_DRIVER_INFO_LEVEL_3);
5253                 if(*asc == NULL)
5254                         return False;
5255                 ZERO_STRUCTP(*asc);
5256         }       
5257
5258         d=*asc;
5259
5260         d->cversion=uni->cversion;
5261
5262         unistr2_to_ascii(d->name,            &uni->name,            sizeof(d->name)-1);
5263         unistr2_to_ascii(d->environment,     &uni->environment,     sizeof(d->environment)-1);
5264         unistr2_to_ascii(d->driverpath,      &uni->driverpath,      sizeof(d->driverpath)-1);
5265         unistr2_to_ascii(d->datafile,        &uni->datafile,        sizeof(d->datafile)-1);
5266         unistr2_to_ascii(d->configfile,      &uni->configfile,      sizeof(d->configfile)-1);
5267         unistr2_to_ascii(d->helpfile,        &uni->helpfile,        sizeof(d->helpfile)-1);
5268         unistr2_to_ascii(d->monitorname,     &uni->monitorname,     sizeof(d->monitorname)-1);
5269         unistr2_to_ascii(d->defaultdatatype, &uni->defaultdatatype, sizeof(d->defaultdatatype)-1);
5270
5271         DEBUGADD(8,( "version:         %d\n", d->cversion));
5272         DEBUGADD(8,( "name:            %s\n", d->name));
5273         DEBUGADD(8,( "environment:     %s\n", d->environment));
5274         DEBUGADD(8,( "driverpath:      %s\n", d->driverpath));
5275         DEBUGADD(8,( "datafile:        %s\n", d->datafile));
5276         DEBUGADD(8,( "configfile:      %s\n", d->configfile));
5277         DEBUGADD(8,( "helpfile:        %s\n", d->helpfile));
5278         DEBUGADD(8,( "monitorname:     %s\n", d->monitorname));
5279         DEBUGADD(8,( "defaultdatatype: %s\n", d->defaultdatatype));
5280
5281         if (uniarray_2_dosarray(&uni->dependentfiles, &d->dependentfiles ))
5282                 return True;
5283         
5284         SAFE_FREE(*asc);
5285         return False;
5286 }
5287
5288 /*******************************************************************
5289 ********************************************************************/  
5290 BOOL uni_2_asc_printer_driver_6(SPOOL_PRINTER_DRIVER_INFO_LEVEL_6 *uni,
5291                                 NT_PRINTER_DRIVER_INFO_LEVEL_6 **asc)
5292 {
5293         NT_PRINTER_DRIVER_INFO_LEVEL_6 *d;
5294         
5295         DEBUG(7,("uni_2_asc_printer_driver_6: Converting from UNICODE to ASCII\n"));
5296         
5297         if (*asc==NULL)
5298         {
5299                 *asc=SMB_MALLOC_P(NT_PRINTER_DRIVER_INFO_LEVEL_6);
5300                 if(*asc == NULL)
5301                         return False;
5302                 ZERO_STRUCTP(*asc);
5303         }       
5304
5305         d=*asc;
5306
5307         d->version=uni->version;
5308
5309         unistr2_to_ascii(d->name,            &uni->name,            sizeof(d->name)-1);
5310         unistr2_to_ascii(d->environment,     &uni->environment,     sizeof(d->environment)-1);
5311         unistr2_to_ascii(d->driverpath,      &uni->driverpath,      sizeof(d->driverpath)-1);
5312         unistr2_to_ascii(d->datafile,        &uni->datafile,        sizeof(d->datafile)-1);
5313         unistr2_to_ascii(d->configfile,      &uni->configfile,      sizeof(d->configfile)-1);
5314         unistr2_to_ascii(d->helpfile,        &uni->helpfile,        sizeof(d->helpfile)-1);
5315         unistr2_to_ascii(d->monitorname,     &uni->monitorname,     sizeof(d->monitorname)-1);
5316         unistr2_to_ascii(d->defaultdatatype, &uni->defaultdatatype, sizeof(d->defaultdatatype)-1);
5317
5318         DEBUGADD(8,( "version:         %d\n", d->version));
5319         DEBUGADD(8,( "name:            %s\n", d->name));
5320         DEBUGADD(8,( "environment:     %s\n", d->environment));
5321         DEBUGADD(8,( "driverpath:      %s\n", d->driverpath));
5322         DEBUGADD(8,( "datafile:        %s\n", d->datafile));
5323         DEBUGADD(8,( "configfile:      %s\n", d->configfile));
5324         DEBUGADD(8,( "helpfile:        %s\n", d->helpfile));
5325         DEBUGADD(8,( "monitorname:     %s\n", d->monitorname));
5326         DEBUGADD(8,( "defaultdatatype: %s\n", d->defaultdatatype));
5327
5328         if (!uniarray_2_dosarray(&uni->dependentfiles, &d->dependentfiles ))
5329                 goto error;
5330         if (!uniarray_2_dosarray(&uni->previousnames, &d->previousnames ))
5331                 goto error;
5332         
5333         return True;
5334         
5335 error:
5336         SAFE_FREE(*asc);
5337         return False;
5338 }
5339
5340 BOOL uni_2_asc_printer_info_2(const SPOOL_PRINTER_INFO_LEVEL_2 *uni,
5341                               NT_PRINTER_INFO_LEVEL_2  **asc)
5342 {
5343         NT_PRINTER_INFO_LEVEL_2 *d;
5344         time_t time_unix;
5345         
5346         DEBUG(7,("Converting from UNICODE to ASCII\n"));
5347         time_unix=time(NULL);
5348         
5349         if (*asc==NULL) {
5350                 DEBUGADD(8,("allocating memory\n"));
5351
5352                 *asc=SMB_MALLOC_P(NT_PRINTER_INFO_LEVEL_2);
5353                 if(*asc == NULL)
5354                         return False;
5355                 ZERO_STRUCTP(*asc);
5356                 
5357                 /* we allocate memory iff called from 
5358                  * addprinter(ex) so we can do one time stuff here.
5359                  */
5360                 (*asc)->setuptime=time_unix;
5361
5362         }       
5363         DEBUGADD(8,("start converting\n"));
5364
5365         d=*asc;
5366                 
5367         d->attributes=uni->attributes;
5368         d->priority=uni->priority;
5369         d->default_priority=uni->default_priority;
5370         d->starttime=uni->starttime;
5371         d->untiltime=uni->untiltime;
5372         d->status=uni->status;
5373         d->cjobs=uni->cjobs;
5374         
5375         unistr2_to_ascii(d->servername, &uni->servername, sizeof(d->servername)-1);
5376         unistr2_to_ascii(d->printername, &uni->printername, sizeof(d->printername)-1);
5377         unistr2_to_ascii(d->sharename, &uni->sharename, sizeof(d->sharename)-1);
5378         unistr2_to_ascii(d->portname, &uni->portname, sizeof(d->portname)-1);
5379         unistr2_to_ascii(d->drivername, &uni->drivername, sizeof(d->drivername)-1);
5380         unistr2_to_ascii(d->comment, &uni->comment, sizeof(d->comment)-1);
5381         unistr2_to_ascii(d->location, &uni->location, sizeof(d->location)-1);
5382         unistr2_to_ascii(d->sepfile, &uni->sepfile, sizeof(d->sepfile)-1);
5383         unistr2_to_ascii(d->printprocessor, &uni->printprocessor, sizeof(d->printprocessor)-1);
5384         unistr2_to_ascii(d->datatype, &uni->datatype, sizeof(d->datatype)-1);
5385         unistr2_to_ascii(d->parameters, &uni->parameters, sizeof(d->parameters)-1);
5386
5387         return True;
5388 }
5389
5390 /*******************************************************************
5391  * init a structure.
5392  ********************************************************************/
5393
5394 BOOL make_spoolss_q_getprinterdriverdir(SPOOL_Q_GETPRINTERDRIVERDIR *q_u,
5395                                 fstring servername, fstring env_name, uint32 level,
5396                                 RPC_BUFFER *buffer, uint32 offered)
5397 {
5398         init_buf_unistr2(&q_u->name, &q_u->name_ptr, servername);
5399         init_buf_unistr2(&q_u->environment, &q_u->environment_ptr, env_name);
5400
5401         q_u->level=level;
5402         q_u->buffer=buffer;
5403         q_u->offered=offered;
5404
5405         return True;
5406 }
5407
5408 /*******************************************************************
5409  Parse a SPOOL_Q_GETPRINTERDRIVERDIR structure.
5410 ********************************************************************/  
5411
5412 BOOL spoolss_io_q_getprinterdriverdir(const char *desc, SPOOL_Q_GETPRINTERDRIVERDIR *q_u, prs_struct *ps, int depth)
5413 {
5414         prs_debug(ps, depth, desc, "spoolss_io_q_getprinterdriverdir");
5415         depth++;
5416
5417         if(!prs_align(ps))
5418                 return False;
5419         if(!prs_uint32("name_ptr", ps, depth, &q_u->name_ptr))
5420                 return False;
5421         if(!smb_io_unistr2("", &q_u->name, q_u->name_ptr, ps, depth))
5422                 return False;
5423
5424         if(!prs_align(ps))
5425                 return False;
5426                 
5427         if(!prs_uint32("", ps, depth, &q_u->environment_ptr))
5428                 return False;
5429         if(!smb_io_unistr2("", &q_u->environment, q_u->environment_ptr, ps, depth))
5430                 return False;
5431                 
5432         if(!prs_align(ps))
5433                 return False;
5434
5435         if(!prs_uint32("level", ps, depth, &q_u->level))
5436                 return False;
5437                 
5438         if(!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
5439                 return False;
5440                 
5441         if(!prs_align(ps))
5442                 return False;
5443                 
5444         if(!prs_uint32("offered", ps, depth, &q_u->offered))
5445                 return False;
5446
5447         return True;
5448 }
5449
5450 /*******************************************************************
5451  Parse a SPOOL_R_GETPRINTERDRIVERDIR structure.
5452 ********************************************************************/  
5453
5454 BOOL spoolss_io_r_getprinterdriverdir(const char *desc, SPOOL_R_GETPRINTERDRIVERDIR *r_u, prs_struct *ps, int depth)
5455 {               
5456         prs_debug(ps, depth, desc, "spoolss_io_r_getprinterdriverdir");
5457         depth++;
5458
5459         if (!prs_align(ps))
5460                 return False;
5461                 
5462         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
5463                 return False;
5464
5465         if (!prs_align(ps))
5466                 return False;
5467                 
5468         if (!prs_uint32("needed", ps, depth, &r_u->needed))
5469                 return False;
5470                 
5471         if (!prs_werror("status", ps, depth, &r_u->status))
5472                 return False;
5473
5474         return True;            
5475 }
5476
5477 /*******************************************************************
5478 ********************************************************************/  
5479
5480 BOOL spoolss_io_r_enumprintprocessors(const char *desc, SPOOL_R_ENUMPRINTPROCESSORS *r_u, prs_struct *ps, int depth)
5481 {               
5482         prs_debug(ps, depth, desc, "spoolss_io_r_enumprintprocessors");
5483         depth++;
5484
5485         if (!prs_align(ps))
5486                 return False;
5487                 
5488         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
5489                 return False;
5490
5491         if (!prs_align(ps))
5492                 return False;
5493                 
5494         if (!prs_uint32("needed", ps, depth, &r_u->needed))
5495                 return False;
5496                 
5497         if (!prs_uint32("returned", ps, depth, &r_u->returned))
5498                 return False;
5499                 
5500         if (!prs_werror("status", ps, depth, &r_u->status))
5501                 return False;
5502
5503         return True;            
5504 }
5505
5506 /*******************************************************************
5507 ********************************************************************/  
5508
5509 BOOL spoolss_io_q_enumprintprocessors(const char *desc, SPOOL_Q_ENUMPRINTPROCESSORS *q_u, prs_struct *ps, int depth)
5510 {
5511         prs_debug(ps, depth, desc, "spoolss_io_q_enumprintprocessors");
5512         depth++;
5513
5514         if (!prs_align(ps))
5515                 return False;
5516                 
5517         if (!prs_uint32("name_ptr", ps, depth, &q_u->name_ptr))
5518                 return False;
5519         if (!smb_io_unistr2("name", &q_u->name, True, ps, depth))
5520                 return False;
5521                 
5522         if (!prs_align(ps))
5523                 return False;
5524                 
5525         if (!prs_uint32("", ps, depth, &q_u->environment_ptr))
5526                 return False;
5527         if (!smb_io_unistr2("", &q_u->environment, q_u->environment_ptr, ps, depth))
5528                 return False;
5529         
5530         if (!prs_align(ps))
5531                 return False;
5532                 
5533         if (!prs_uint32("level", ps, depth, &q_u->level))
5534                 return False;
5535                 
5536         if(!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
5537                 return False;
5538
5539         if (!prs_align(ps))
5540                 return False;
5541
5542         if (!prs_uint32("offered", ps, depth, &q_u->offered))
5543                 return False;
5544
5545         return True;
5546 }
5547
5548 /*******************************************************************
5549 ********************************************************************/  
5550
5551 BOOL spoolss_io_q_addprintprocessor(const char *desc, SPOOL_Q_ADDPRINTPROCESSOR *q_u, prs_struct *ps, int depth)
5552 {
5553         prs_debug(ps, depth, desc, "spoolss_io_q_addprintprocessor");
5554         depth++;
5555
5556         if (!prs_align(ps))
5557                 return False;
5558                 
5559         if (!prs_uint32("server_ptr", ps, depth, &q_u->server_ptr))
5560                 return False;
5561         if (!smb_io_unistr2("server", &q_u->server, q_u->server_ptr, ps, depth))
5562                 return False;
5563                 
5564         if (!prs_align(ps))
5565                 return False;
5566         if (!smb_io_unistr2("environment", &q_u->environment, True, ps, depth))
5567                 return False;
5568                 
5569         if (!prs_align(ps))
5570                 return False;
5571         if (!smb_io_unistr2("path", &q_u->path, True, ps, depth))
5572                 return False;
5573
5574         if (!prs_align(ps))
5575                 return False;
5576         if (!smb_io_unistr2("name", &q_u->name, True, ps, depth))
5577                 return False;
5578
5579         return True;
5580 }
5581
5582 /*******************************************************************
5583 ********************************************************************/  
5584
5585 BOOL spoolss_io_r_addprintprocessor(const char *desc, SPOOL_R_ADDPRINTPROCESSOR *r_u, prs_struct *ps, int depth)
5586 {               
5587         prs_debug(ps, depth, desc, "spoolss_io_r_addprintproicessor");
5588         depth++;
5589
5590         if (!prs_align(ps))
5591                 return False;
5592                 
5593         if (!prs_werror("status", ps, depth, &r_u->status))
5594                 return False;
5595
5596         return True;            
5597 }
5598
5599 /*******************************************************************
5600 ********************************************************************/  
5601
5602 BOOL spoolss_io_r_enumprintprocdatatypes(const char *desc, SPOOL_R_ENUMPRINTPROCDATATYPES *r_u, prs_struct *ps, int depth)
5603 {               
5604         prs_debug(ps, depth, desc, "spoolss_io_r_enumprintprocdatatypes");
5605         depth++;
5606
5607         if (!prs_align(ps))
5608                 return False;
5609                 
5610         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
5611                 return False;
5612
5613         if (!prs_align(ps))
5614                 return False;
5615                 
5616         if (!prs_uint32("needed", ps, depth, &r_u->needed))
5617                 return False;
5618                 
5619         if (!prs_uint32("returned", ps, depth, &r_u->returned))
5620                 return False;
5621                 
5622         if (!prs_werror("status", ps, depth, &r_u->status))
5623                 return False;
5624
5625         return True;            
5626 }
5627
5628 /*******************************************************************
5629 ********************************************************************/  
5630
5631 BOOL spoolss_io_q_enumprintprocdatatypes(const char *desc, SPOOL_Q_ENUMPRINTPROCDATATYPES *q_u, prs_struct *ps, int depth)
5632 {
5633         prs_debug(ps, depth, desc, "spoolss_io_q_enumprintprocdatatypes");
5634         depth++;
5635
5636         if (!prs_align(ps))
5637                 return False;
5638                 
5639         if (!prs_uint32("name_ptr", ps, depth, &q_u->name_ptr))
5640                 return False;
5641         if (!smb_io_unistr2("name", &q_u->name, True, ps, depth))
5642                 return False;
5643                 
5644         if (!prs_align(ps))
5645                 return False;
5646                 
5647         if (!prs_uint32("processor_ptr", ps, depth, &q_u->processor_ptr))
5648                 return False;
5649         if (!smb_io_unistr2("processor", &q_u->processor, q_u->processor_ptr, ps, depth))
5650                 return False;
5651         
5652         if (!prs_align(ps))
5653                 return False;
5654                 
5655         if (!prs_uint32("level", ps, depth, &q_u->level))
5656                 return False;
5657                 
5658         if(!prs_rpcbuffer_p("buffer", ps, depth, &q_u->buffer))
5659                 return False;
5660
5661         if (!prs_align(ps))
5662                 return False;
5663
5664         if (!prs_uint32("offered", ps, depth, &q_u->offered))
5665                 return False;
5666
5667         return True;
5668 }
5669
5670 /*******************************************************************
5671  Parse a SPOOL_Q_ENUMPRINTMONITORS structure.
5672 ********************************************************************/  
5673
5674 BOOL spoolss_io_q_enumprintmonitors(const char *desc, SPOOL_Q_ENUMPRINTMONITORS *q_u, prs_struct *ps, int depth)
5675 {
5676         prs_debug(ps, depth, desc, "spoolss_io_q_enumprintmonitors");
5677         depth++;
5678
5679         if (!prs_align(ps))
5680                 return False;
5681                 
5682         if (!prs_uint32("name_ptr", ps, depth, &q_u->name_ptr))
5683                 return False;
5684         if (!smb_io_unistr2("name", &q_u->name, True, ps, depth))
5685                 return False;
5686                 
5687         if (!prs_align(ps))
5688                 return False;
5689                                 
5690         if (!prs_uint32("level", ps, depth, &q_u->level))
5691                 return False;
5692                 
5693         if(!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
5694                 return False;
5695
5696         if (!prs_align(ps))
5697                 return False;
5698
5699         if (!prs_uint32("offered", ps, depth, &q_u->offered))
5700                 return False;
5701
5702         return True;
5703 }
5704
5705 /*******************************************************************
5706 ********************************************************************/  
5707
5708 BOOL spoolss_io_r_enumprintmonitors(const char *desc, SPOOL_R_ENUMPRINTMONITORS *r_u, prs_struct *ps, int depth)
5709 {               
5710         prs_debug(ps, depth, desc, "spoolss_io_r_enumprintmonitors");
5711         depth++;
5712
5713         if (!prs_align(ps))
5714                 return False;
5715                 
5716         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
5717                 return False;
5718
5719         if (!prs_align(ps))
5720                 return False;
5721                 
5722         if (!prs_uint32("needed", ps, depth, &r_u->needed))
5723                 return False;
5724                 
5725         if (!prs_uint32("returned", ps, depth, &r_u->returned))
5726                 return False;
5727                 
5728         if (!prs_werror("status", ps, depth, &r_u->status))
5729                 return False;
5730
5731         return True;            
5732 }
5733
5734 /*******************************************************************
5735 ********************************************************************/  
5736
5737 BOOL spoolss_io_r_enumprinterdata(const char *desc, SPOOL_R_ENUMPRINTERDATA *r_u, prs_struct *ps, int depth)
5738 {       
5739         prs_debug(ps, depth, desc, "spoolss_io_r_enumprinterdata");
5740         depth++;
5741
5742         if(!prs_align(ps))
5743                 return False;
5744         if(!prs_uint32("valuesize", ps, depth, &r_u->valuesize))
5745                 return False;
5746
5747         if (UNMARSHALLING(ps) && r_u->valuesize) {
5748                 r_u->value = PRS_ALLOC_MEM(ps, uint16, r_u->valuesize);
5749                 if (!r_u->value) {
5750                         DEBUG(0, ("spoolss_io_r_enumprinterdata: out of memory for printerdata value\n"));
5751                         return False;
5752                 }
5753         }
5754
5755         if(!prs_uint16uni(False, "value", ps, depth, r_u->value, r_u->valuesize ))
5756                 return False;
5757
5758         if(!prs_align(ps))
5759                 return False;
5760
5761         if(!prs_uint32("realvaluesize", ps, depth, &r_u->realvaluesize))
5762                 return False;
5763
5764         if(!prs_uint32("type", ps, depth, &r_u->type))
5765                 return False;
5766
5767         if(!prs_uint32("datasize", ps, depth, &r_u->datasize))
5768                 return False;
5769
5770         if (UNMARSHALLING(ps) && r_u->datasize) {
5771                 r_u->data = PRS_ALLOC_MEM(ps, uint8, r_u->datasize);
5772                 if (!r_u->data) {
5773                         DEBUG(0, ("spoolss_io_r_enumprinterdata: out of memory for printerdata data\n"));
5774                         return False;
5775                 }
5776         }
5777
5778         if(!prs_uint8s(False, "data", ps, depth, r_u->data, r_u->datasize))
5779                 return False;
5780         if(!prs_align(ps))
5781                 return False;
5782
5783         if(!prs_uint32("realdatasize", ps, depth, &r_u->realdatasize))
5784                 return False;
5785         if(!prs_werror("status", ps, depth, &r_u->status))
5786                 return False;
5787
5788         return True;
5789 }
5790
5791 /*******************************************************************
5792 ********************************************************************/  
5793
5794 BOOL spoolss_io_q_enumprinterdata(const char *desc, SPOOL_Q_ENUMPRINTERDATA *q_u, prs_struct *ps, int depth)
5795 {
5796         prs_debug(ps, depth, desc, "spoolss_io_q_enumprinterdata");
5797         depth++;
5798
5799         if(!prs_align(ps))
5800                 return False;
5801         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
5802                 return False;
5803         if(!prs_uint32("index", ps, depth, &q_u->index))
5804                 return False;
5805         if(!prs_uint32("valuesize", ps, depth, &q_u->valuesize))
5806                 return False;
5807         if(!prs_uint32("datasize", ps, depth, &q_u->datasize))
5808                 return False;
5809
5810         return True;
5811 }
5812
5813 /*******************************************************************
5814 ********************************************************************/  
5815
5816 BOOL make_spoolss_q_enumprinterdata(SPOOL_Q_ENUMPRINTERDATA *q_u,
5817                 const POLICY_HND *hnd,
5818                 uint32 idx, uint32 valuelen, uint32 datalen)
5819 {
5820         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
5821         q_u->index=idx;
5822         q_u->valuesize=valuelen;
5823         q_u->datasize=datalen;
5824
5825         return True;
5826 }
5827
5828 /*******************************************************************
5829 ********************************************************************/  
5830
5831 BOOL make_spoolss_q_enumprinterdataex(SPOOL_Q_ENUMPRINTERDATAEX *q_u,
5832                                       const POLICY_HND *hnd, const char *key,
5833                                       uint32 size)
5834 {
5835         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
5836         init_unistr2(&q_u->key, key, UNI_STR_TERMINATE);
5837         q_u->size = size;
5838
5839         return True;
5840 }
5841
5842 /*******************************************************************
5843 ********************************************************************/  
5844 BOOL make_spoolss_q_setprinterdata(SPOOL_Q_SETPRINTERDATA *q_u, const POLICY_HND *hnd,
5845                                    char* value, uint32 data_type, char* data, uint32 data_size)
5846 {
5847         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
5848         q_u->type = data_type;
5849         init_unistr2(&q_u->value, value, UNI_STR_TERMINATE);
5850
5851         q_u->max_len = q_u->real_len = data_size;
5852         q_u->data = (unsigned char *)data;
5853         
5854         return True;
5855 }
5856
5857 /*******************************************************************
5858 ********************************************************************/  
5859 BOOL make_spoolss_q_setprinterdataex(SPOOL_Q_SETPRINTERDATAEX *q_u, const POLICY_HND *hnd,
5860                                      char *key, char* value, uint32 data_type, char* data, 
5861                                      uint32 data_size)
5862 {
5863         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
5864         q_u->type = data_type;
5865         init_unistr2(&q_u->value, value, UNI_STR_TERMINATE);
5866         init_unistr2(&q_u->key, key, UNI_STR_TERMINATE);
5867
5868         q_u->max_len = q_u->real_len = data_size;
5869         q_u->data = (unsigned char *)data;
5870         
5871         return True;
5872 }
5873
5874 /*******************************************************************
5875 ********************************************************************/  
5876
5877 BOOL spoolss_io_q_setprinterdata(const char *desc, SPOOL_Q_SETPRINTERDATA *q_u, prs_struct *ps, int depth)
5878 {
5879         prs_debug(ps, depth, desc, "spoolss_io_q_setprinterdata");
5880         depth++;
5881
5882         if(!prs_align(ps))
5883                 return False;
5884         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
5885                 return False;
5886         if(!smb_io_unistr2("", &q_u->value, True, ps, depth))
5887                 return False;
5888
5889         if(!prs_align(ps))
5890                 return False;
5891
5892         if(!prs_uint32("type", ps, depth, &q_u->type))
5893                 return False;
5894
5895         if(!prs_uint32("max_len", ps, depth, &q_u->max_len))
5896                 return False;
5897
5898         switch (q_u->type)
5899         {
5900                 case REG_SZ:
5901                 case REG_BINARY:
5902                 case REG_DWORD:
5903                 case REG_MULTI_SZ:
5904             if (q_u->max_len) {
5905                 if (UNMARSHALLING(ps))
5906                                 q_u->data=PRS_ALLOC_MEM(ps, uint8, q_u->max_len);
5907                         if(q_u->data == NULL)
5908                                 return False;
5909                         if(!prs_uint8s(False,"data", ps, depth, q_u->data, q_u->max_len))
5910                                 return False;
5911             }
5912                         if(!prs_align(ps))
5913                                 return False;
5914                         break;
5915         }       
5916         
5917         if(!prs_uint32("real_len", ps, depth, &q_u->real_len))
5918                 return False;
5919
5920         return True;
5921 }
5922
5923 /*******************************************************************
5924 ********************************************************************/  
5925
5926 BOOL spoolss_io_r_setprinterdata(const char *desc, SPOOL_R_SETPRINTERDATA *r_u, prs_struct *ps, int depth)
5927 {
5928         prs_debug(ps, depth, desc, "spoolss_io_r_setprinterdata");
5929         depth++;
5930
5931         if(!prs_align(ps))
5932                 return False;
5933         if(!prs_werror("status",     ps, depth, &r_u->status))
5934                 return False;
5935
5936         return True;
5937 }
5938
5939 /*******************************************************************
5940 ********************************************************************/  
5941 BOOL spoolss_io_q_resetprinter(const char *desc, SPOOL_Q_RESETPRINTER *q_u, prs_struct *ps, int depth)
5942 {
5943         prs_debug(ps, depth, desc, "spoolss_io_q_resetprinter");
5944         depth++;
5945
5946         if (!prs_align(ps))
5947                 return False;
5948         if (!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
5949                 return False;
5950
5951         if (!prs_uint32("datatype_ptr", ps, depth, &q_u->datatype_ptr))
5952                 return False;
5953                 
5954         if (q_u->datatype_ptr) {
5955                 if (!smb_io_unistr2("datatype", &q_u->datatype, q_u->datatype_ptr?True:False, ps, depth))
5956                 return False;
5957         }
5958
5959         if (!spoolss_io_devmode_cont(desc, &q_u->devmode_ctr, ps, depth))
5960                 return False;
5961
5962         return True;
5963 }
5964
5965
5966 /*******************************************************************
5967 ********************************************************************/  
5968 BOOL spoolss_io_r_resetprinter(const char *desc, SPOOL_R_RESETPRINTER *r_u, prs_struct *ps, int depth)
5969 {
5970         prs_debug(ps, depth, desc, "spoolss_io_r_resetprinter");
5971         depth++;
5972
5973         if(!prs_align(ps))
5974                 return False;
5975         if(!prs_werror("status",     ps, depth, &r_u->status))
5976                 return False;
5977
5978         return True;
5979 }
5980
5981 /*******************************************************************
5982 ********************************************************************/  
5983
5984 static BOOL spoolss_io_addform(const char *desc, FORM *f, uint32 ptr, prs_struct *ps, int depth)
5985 {
5986         prs_debug(ps, depth, desc, "spoolss_io_addform");
5987         depth++;
5988         if(!prs_align(ps))
5989                 return False;
5990
5991         if (ptr!=0)
5992         {
5993                 if(!prs_uint32("flags",    ps, depth, &f->flags))
5994                         return False;
5995                 if(!prs_uint32("name_ptr", ps, depth, &f->name_ptr))
5996                         return False;
5997                 if(!prs_uint32("size_x",   ps, depth, &f->size_x))
5998                         return False;
5999                 if(!prs_uint32("size_y",   ps, depth, &f->size_y))
6000                         return False;
6001                 if(!prs_uint32("left",     ps, depth, &f->left))
6002                         return False;
6003                 if(!prs_uint32("top",      ps, depth, &f->top))
6004                         return False;
6005                 if(!prs_uint32("right",    ps, depth, &f->right))
6006                         return False;
6007                 if(!prs_uint32("bottom",   ps, depth, &f->bottom))
6008                         return False;
6009
6010                 if(!smb_io_unistr2("", &f->name, f->name_ptr, ps, depth))
6011                         return False;
6012         }
6013
6014         return True;
6015 }
6016
6017 /*******************************************************************
6018 ********************************************************************/  
6019
6020 BOOL spoolss_io_q_deleteform(const char *desc, SPOOL_Q_DELETEFORM *q_u, prs_struct *ps, int depth)
6021 {
6022         prs_debug(ps, depth, desc, "spoolss_io_q_deleteform");
6023         depth++;
6024
6025         if(!prs_align(ps))
6026                 return False;
6027         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
6028                 return False;
6029         if(!smb_io_unistr2("form name", &q_u->name, True, ps, depth))
6030                 return False;
6031
6032         return True;
6033 }
6034
6035 /*******************************************************************
6036 ********************************************************************/  
6037
6038 BOOL spoolss_io_r_deleteform(const char *desc, SPOOL_R_DELETEFORM *r_u, prs_struct *ps, int depth)
6039 {
6040         prs_debug(ps, depth, desc, "spoolss_io_r_deleteform");
6041         depth++;
6042
6043         if(!prs_align(ps))
6044                 return False;
6045         if(!prs_werror("status",        ps, depth, &r_u->status))
6046                 return False;
6047
6048         return True;
6049 }
6050
6051 /*******************************************************************
6052 ********************************************************************/  
6053
6054 BOOL spoolss_io_q_addform(const char *desc, SPOOL_Q_ADDFORM *q_u, prs_struct *ps, int depth)
6055 {
6056         uint32 useless_ptr=1;
6057         prs_debug(ps, depth, desc, "spoolss_io_q_addform");
6058         depth++;
6059
6060         if(!prs_align(ps))
6061                 return False;
6062         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
6063                 return False;
6064         if(!prs_uint32("level",  ps, depth, &q_u->level))
6065                 return False;
6066         if(!prs_uint32("level2", ps, depth, &q_u->level2))
6067                 return False;
6068
6069         if (q_u->level==1)
6070         {
6071                 if(!prs_uint32("useless_ptr", ps, depth, &useless_ptr))
6072                         return False;
6073                 if(!spoolss_io_addform("", &q_u->form, useless_ptr, ps, depth))
6074                         return False;
6075         }
6076
6077         return True;
6078 }
6079
6080 /*******************************************************************
6081 ********************************************************************/  
6082
6083 BOOL spoolss_io_r_addform(const char *desc, SPOOL_R_ADDFORM *r_u, prs_struct *ps, int depth)
6084 {
6085         prs_debug(ps, depth, desc, "spoolss_io_r_addform");
6086         depth++;
6087
6088         if(!prs_align(ps))
6089                 return False;
6090         if(!prs_werror("status",        ps, depth, &r_u->status))
6091                 return False;
6092
6093         return True;
6094 }
6095
6096 /*******************************************************************
6097 ********************************************************************/  
6098
6099 BOOL spoolss_io_q_setform(const char *desc, SPOOL_Q_SETFORM *q_u, prs_struct *ps, int depth)
6100 {
6101         uint32 useless_ptr=1;
6102         prs_debug(ps, depth, desc, "spoolss_io_q_setform");
6103         depth++;
6104
6105         if(!prs_align(ps))
6106                 return False;
6107         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
6108                 return False;
6109         if(!smb_io_unistr2("", &q_u->name, True, ps, depth))
6110                 return False;
6111               
6112         if(!prs_align(ps))
6113                 return False;
6114         
6115         if(!prs_uint32("level",  ps, depth, &q_u->level))
6116                 return False;
6117         if(!prs_uint32("level2", ps, depth, &q_u->level2))
6118                 return False;
6119
6120         if (q_u->level==1)
6121         {
6122                 if(!prs_uint32("useless_ptr", ps, depth, &useless_ptr))
6123                         return False;
6124                 if(!spoolss_io_addform("", &q_u->form, useless_ptr, ps, depth))
6125                         return False;
6126         }
6127
6128         return True;
6129 }
6130
6131 /*******************************************************************
6132 ********************************************************************/  
6133
6134 BOOL spoolss_io_r_setform(const char *desc, SPOOL_R_SETFORM *r_u, prs_struct *ps, int depth)
6135 {
6136         prs_debug(ps, depth, desc, "spoolss_io_r_setform");
6137         depth++;
6138
6139         if(!prs_align(ps))
6140                 return False;
6141         if(!prs_werror("status",        ps, depth, &r_u->status))
6142                 return False;
6143
6144         return True;
6145 }
6146
6147 /*******************************************************************
6148  Parse a SPOOL_R_GETJOB structure.
6149 ********************************************************************/  
6150
6151 BOOL spoolss_io_r_getjob(const char *desc, SPOOL_R_GETJOB *r_u, prs_struct *ps, int depth)
6152 {               
6153         prs_debug(ps, depth, desc, "spoolss_io_r_getjob");
6154         depth++;
6155
6156         if (!prs_align(ps))
6157                 return False;
6158                 
6159         if (!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
6160                 return False;
6161
6162         if (!prs_align(ps))
6163                 return False;
6164                 
6165         if (!prs_uint32("needed", ps, depth, &r_u->needed))
6166                 return False;
6167                 
6168         if (!prs_werror("status", ps, depth, &r_u->status))
6169                 return False;
6170
6171         return True;            
6172 }
6173
6174 /*******************************************************************
6175  Parse a SPOOL_Q_GETJOB structure.
6176 ********************************************************************/  
6177
6178 BOOL spoolss_io_q_getjob(const char *desc, SPOOL_Q_GETJOB *q_u, prs_struct *ps, int depth)
6179 {
6180         prs_debug(ps, depth, desc, "");
6181         depth++;
6182
6183         if(!prs_align(ps))
6184                 return False;
6185
6186         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
6187                 return False;
6188         if(!prs_uint32("jobid", ps, depth, &q_u->jobid))
6189                 return False;
6190         if(!prs_uint32("level", ps, depth, &q_u->level))
6191                 return False;
6192         
6193         if(!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
6194                 return False;
6195
6196         if(!prs_align(ps))
6197                 return False;
6198         
6199         if(!prs_uint32("offered", ps, depth, &q_u->offered))
6200                 return False;
6201
6202         return True;
6203 }
6204
6205 void free_devmode(DEVICEMODE *devmode)
6206 {
6207         if (devmode!=NULL) {
6208                 SAFE_FREE(devmode->dev_private);
6209                 SAFE_FREE(devmode);
6210         }
6211 }
6212
6213 void free_printer_info_1(PRINTER_INFO_1 *printer)
6214 {
6215         SAFE_FREE(printer);
6216 }
6217
6218 void free_printer_info_2(PRINTER_INFO_2 *printer)
6219 {
6220         if (printer!=NULL) {
6221                 free_devmode(printer->devmode);
6222                 printer->devmode = NULL;
6223                 SAFE_FREE(printer);
6224         }
6225 }
6226
6227 void free_printer_info_3(PRINTER_INFO_3 *printer)
6228 {
6229         SAFE_FREE(printer);
6230 }
6231
6232 void free_printer_info_4(PRINTER_INFO_4 *printer)
6233 {
6234         SAFE_FREE(printer);
6235 }
6236
6237 void free_printer_info_5(PRINTER_INFO_5 *printer)
6238 {
6239         SAFE_FREE(printer);
6240 }
6241
6242 void free_printer_info_7(PRINTER_INFO_7 *printer)
6243 {
6244         SAFE_FREE(printer);
6245 }
6246
6247 void free_job_info_2(JOB_INFO_2 *job)
6248 {
6249     if (job!=NULL)
6250         free_devmode(job->devmode);
6251 }
6252
6253 /*******************************************************************
6254  * init a structure.
6255  ********************************************************************/
6256
6257 BOOL make_spoolss_q_replyopenprinter(SPOOL_Q_REPLYOPENPRINTER *q_u, 
6258                                const fstring string, uint32 printer, uint32 type)
6259 {      
6260         if (q_u == NULL)
6261                 return False;
6262
6263         init_unistr2(&q_u->string, string, UNI_STR_TERMINATE);
6264
6265         q_u->printer=printer;
6266         q_u->type=type;
6267
6268         q_u->unknown0=0x0;
6269         q_u->unknown1=0x0;
6270
6271         return True;
6272 }
6273
6274 /*******************************************************************
6275  Parse a SPOOL_Q_REPLYOPENPRINTER structure.
6276 ********************************************************************/  
6277
6278 BOOL spoolss_io_q_replyopenprinter(const char *desc, SPOOL_Q_REPLYOPENPRINTER *q_u, prs_struct *ps, int depth)
6279 {
6280         prs_debug(ps, depth, desc, "spoolss_io_q_replyopenprinter");
6281         depth++;
6282
6283         if(!prs_align(ps))
6284                 return False;
6285
6286         if(!smb_io_unistr2("", &q_u->string, True, ps, depth))
6287                 return False;
6288
6289         if(!prs_align(ps))
6290                 return False;
6291
6292         if(!prs_uint32("printer", ps, depth, &q_u->printer))
6293                 return False;
6294         if(!prs_uint32("type", ps, depth, &q_u->type))
6295                 return False;
6296         
6297         if(!prs_uint32("unknown0", ps, depth, &q_u->unknown0))
6298                 return False;
6299         if(!prs_uint32("unknown1", ps, depth, &q_u->unknown1))
6300                 return False;
6301
6302         return True;
6303 }
6304
6305 /*******************************************************************
6306  Parse a SPOOL_R_REPLYOPENPRINTER structure.
6307 ********************************************************************/  
6308
6309 BOOL spoolss_io_r_replyopenprinter(const char *desc, SPOOL_R_REPLYOPENPRINTER *r_u, prs_struct *ps, int depth)
6310 {               
6311         prs_debug(ps, depth, desc, "spoolss_io_r_replyopenprinter");
6312         depth++;
6313
6314         if (!prs_align(ps))
6315                 return False;
6316
6317         if(!smb_io_pol_hnd("printer handle",&r_u->handle,ps,depth))
6318                 return False;
6319
6320         if (!prs_werror("status", ps, depth, &r_u->status))
6321                 return False;
6322
6323         return True;            
6324 }
6325
6326 /*******************************************************************
6327  * init a structure.
6328  ********************************************************************/
6329 BOOL make_spoolss_q_routerreplyprinter(SPOOL_Q_ROUTERREPLYPRINTER *q_u, POLICY_HND *hnd, 
6330                                         uint32 condition, uint32 change_id)
6331 {
6332
6333         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
6334
6335         q_u->condition = condition;
6336         q_u->change_id = change_id;
6337
6338         /* magic values */
6339         q_u->unknown1 = 0x1;
6340         memset(q_u->unknown2, 0x0, 5);
6341         q_u->unknown2[0] = 0x1;
6342
6343         return True;
6344 }
6345
6346 /*******************************************************************
6347  Parse a SPOOL_Q_ROUTERREPLYPRINTER structure.
6348 ********************************************************************/
6349 BOOL spoolss_io_q_routerreplyprinter (const char *desc, SPOOL_Q_ROUTERREPLYPRINTER *q_u, prs_struct *ps, int depth)
6350 {
6351
6352         prs_debug(ps, depth, desc, "spoolss_io_q_routerreplyprinter");
6353         depth++;
6354
6355         if (!prs_align(ps))
6356                 return False;
6357
6358         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
6359                 return False;
6360
6361         if (!prs_uint32("condition", ps, depth, &q_u->condition))
6362                 return False;
6363
6364         if (!prs_uint32("unknown1", ps, depth, &q_u->unknown1))
6365                 return False;
6366
6367         if (!prs_uint32("change_id", ps, depth, &q_u->change_id))
6368                 return False;
6369
6370         if (!prs_uint8s(False, "dev_private",  ps, depth, q_u->unknown2, 5))
6371                 return False;
6372
6373         return True;
6374 }
6375
6376 /*******************************************************************
6377  Parse a SPOOL_R_ROUTERREPLYPRINTER structure.
6378 ********************************************************************/
6379 BOOL spoolss_io_r_routerreplyprinter (const char *desc, SPOOL_R_ROUTERREPLYPRINTER *r_u, prs_struct *ps, int depth)
6380 {
6381         prs_debug(ps, depth, desc, "spoolss_io_r_routerreplyprinter");
6382         depth++;
6383
6384         if (!prs_align(ps))
6385                 return False;
6386
6387         if (!prs_werror("status", ps, depth, &r_u->status))
6388                 return False;
6389
6390         return True;
6391 }
6392
6393 /*******************************************************************
6394  * init a structure.
6395  ********************************************************************/
6396
6397 BOOL make_spoolss_q_reply_closeprinter(SPOOL_Q_REPLYCLOSEPRINTER *q_u, POLICY_HND *hnd)
6398 {      
6399         if (q_u == NULL)
6400                 return False;
6401
6402         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
6403
6404         return True;
6405 }
6406
6407 /*******************************************************************
6408  Parse a SPOOL_Q_REPLYCLOSEPRINTER structure.
6409 ********************************************************************/  
6410
6411 BOOL spoolss_io_q_replycloseprinter(const char *desc, SPOOL_Q_REPLYCLOSEPRINTER *q_u, prs_struct *ps, int depth)
6412 {
6413         prs_debug(ps, depth, desc, "spoolss_io_q_replycloseprinter");
6414         depth++;
6415
6416         if(!prs_align(ps))
6417                 return False;
6418
6419         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
6420                 return False;
6421
6422         return True;
6423 }
6424
6425 /*******************************************************************
6426  Parse a SPOOL_R_REPLYCLOSEPRINTER structure.
6427 ********************************************************************/  
6428
6429 BOOL spoolss_io_r_replycloseprinter(const char *desc, SPOOL_R_REPLYCLOSEPRINTER *r_u, prs_struct *ps, int depth)
6430 {               
6431         prs_debug(ps, depth, desc, "spoolss_io_r_replycloseprinter");
6432         depth++;
6433
6434         if (!prs_align(ps))
6435                 return False;
6436
6437         if(!smb_io_pol_hnd("printer handle",&r_u->handle,ps,depth))
6438                 return False;
6439
6440         if (!prs_werror("status", ps, depth, &r_u->status))
6441                 return False;
6442
6443         return True;            
6444 }
6445
6446 #if 0   /* JERRY - not currently used but could be :-) */
6447
6448 /*******************************************************************
6449  Deep copy a SPOOL_NOTIFY_INFO_DATA structure
6450  ******************************************************************/
6451 static BOOL copy_spool_notify_info_data(SPOOL_NOTIFY_INFO_DATA *dst, 
6452                                 SPOOL_NOTIFY_INFO_DATA *src, int n)
6453 {
6454         int i;
6455
6456         memcpy(dst, src, sizeof(SPOOL_NOTIFY_INFO_DATA)*n);
6457         
6458         for (i=0; i<n; i++) {
6459                 int len;
6460                 uint16 *s = NULL;
6461                 
6462                 if (src->size != POINTER) 
6463                         continue;
6464                 len = src->notify_data.data.length;
6465                 s = SMB_MALLOC_ARRAY(uint16, len);
6466                 if (s == NULL) {
6467                         DEBUG(0,("copy_spool_notify_info_data: malloc() failed!\n"));
6468                         return False;
6469                 }
6470                 
6471                 memcpy(s, src->notify_data.data.string, len*2);
6472                 dst->notify_data.data.string = s;
6473         }
6474         
6475         return True;
6476 }
6477
6478 /*******************************************************************
6479  Deep copy a SPOOL_NOTIFY_INFO structure
6480  ******************************************************************/
6481 static BOOL copy_spool_notify_info(SPOOL_NOTIFY_INFO *dst, SPOOL_NOTIFY_INFO *src)
6482 {
6483         if (!dst) {
6484                 DEBUG(0,("copy_spool_notify_info: NULL destination pointer!\n"));
6485                 return False;
6486         }
6487                 
6488         dst->version = src->version;
6489         dst->flags   = src->flags;
6490         dst->count   = src->count;
6491         
6492         if (dst->count) 
6493         {
6494                 dst->data = SMB_MALLOC_ARRAY(SPOOL_NOTIFY_INFO_DATA, dst->count);
6495                 
6496                 DEBUG(10,("copy_spool_notify_info: allocating space for [%d] PRINTER_NOTIFY_INFO_DATA entries\n",
6497                         dst->count));
6498
6499                 if (dst->data == NULL) {
6500                         DEBUG(0,("copy_spool_notify_info: malloc() failed for [%d] entries!\n", 
6501                                 dst->count));
6502                         return False;
6503                 }
6504                 
6505                 return (copy_spool_notify_info_data(dst->data, src->data, src->count));
6506         }
6507         
6508         return True;
6509 }
6510 #endif  /* JERRY */
6511
6512 /*******************************************************************
6513  * init a structure.
6514  ********************************************************************/
6515
6516 BOOL make_spoolss_q_reply_rrpcn(SPOOL_Q_REPLY_RRPCN *q_u, POLICY_HND *hnd,
6517                                 uint32 change_low, uint32 change_high,
6518                                 SPOOL_NOTIFY_INFO *info)
6519 {      
6520         if (q_u == NULL)
6521                 return False;
6522
6523         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
6524
6525         q_u->change_low=change_low;
6526         q_u->change_high=change_high;
6527
6528         q_u->unknown0=0x0;
6529         q_u->unknown1=0x0;
6530
6531         q_u->info_ptr=0x0FF0ADDE;
6532
6533         q_u->info.version=2;
6534         
6535         if (info->count) {
6536                 DEBUG(10,("make_spoolss_q_reply_rrpcn: [%d] PRINTER_NOTIFY_INFO_DATA\n",
6537                         info->count));
6538                 q_u->info.version = info->version;
6539                 q_u->info.flags   = info->flags;
6540                 q_u->info.count   = info->count;
6541                 /* pointer field - be careful! */
6542                 q_u->info.data    = info->data;
6543         }
6544         else  {
6545         q_u->info.flags=PRINTER_NOTIFY_INFO_DISCARDED;
6546         q_u->info.count=0;
6547         }
6548
6549         return True;
6550 }
6551
6552 /*******************************************************************
6553  Parse a SPOOL_Q_REPLY_RRPCN structure.
6554 ********************************************************************/  
6555
6556 BOOL spoolss_io_q_reply_rrpcn(const char *desc, SPOOL_Q_REPLY_RRPCN *q_u, prs_struct *ps, int depth)
6557 {
6558         prs_debug(ps, depth, desc, "spoolss_io_q_reply_rrpcn");
6559         depth++;
6560
6561         if(!prs_align(ps))
6562                 return False;
6563
6564         if(!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
6565                 return False;
6566
6567         if (!prs_uint32("change_low", ps, depth, &q_u->change_low))
6568                 return False;
6569
6570         if (!prs_uint32("change_high", ps, depth, &q_u->change_high))
6571                 return False;
6572
6573         if (!prs_uint32("unknown0", ps, depth, &q_u->unknown0))
6574                 return False;
6575
6576         if (!prs_uint32("unknown1", ps, depth, &q_u->unknown1))
6577                 return False;
6578
6579         if (!prs_uint32("info_ptr", ps, depth, &q_u->info_ptr))
6580                 return False;
6581
6582         if(q_u->info_ptr!=0)
6583                 if(!smb_io_notify_info(desc, &q_u->info, ps, depth))
6584                         return False;
6585                 
6586         return True;
6587 }
6588
6589 /*******************************************************************
6590  Parse a SPOOL_R_REPLY_RRPCN structure.
6591 ********************************************************************/  
6592
6593 BOOL spoolss_io_r_reply_rrpcn(const char *desc, SPOOL_R_REPLY_RRPCN *r_u, prs_struct *ps, int depth)
6594 {               
6595         prs_debug(ps, depth, desc, "spoolss_io_r_reply_rrpcn");
6596         depth++;
6597
6598         if (!prs_align(ps))
6599                 return False;
6600
6601         if (!prs_uint32("unknown0", ps, depth, &r_u->unknown0))
6602                 return False;
6603
6604         if (!prs_werror("status", ps, depth, &r_u->status))
6605                 return False;
6606
6607         return True;            
6608 }
6609
6610 /*******************************************************************
6611  * read a structure.
6612  * called from spoolss_q_getprinterdataex (srv_spoolss.c)
6613  ********************************************************************/
6614
6615 BOOL spoolss_io_q_getprinterdataex(const char *desc, SPOOL_Q_GETPRINTERDATAEX *q_u, prs_struct *ps, int depth)
6616 {
6617         if (q_u == NULL)
6618                 return False;
6619
6620         prs_debug(ps, depth, desc, "spoolss_io_q_getprinterdataex");
6621         depth++;
6622
6623         if (!prs_align(ps))
6624                 return False;
6625         if (!smb_io_pol_hnd("printer handle",&q_u->handle,ps,depth))
6626                 return False;
6627         if (!prs_align(ps))
6628                 return False;
6629         if (!smb_io_unistr2("keyname", &q_u->keyname,True,ps,depth))
6630                 return False;
6631         if (!prs_align(ps))
6632                 return False;
6633         if (!smb_io_unistr2("valuename", &q_u->valuename,True,ps,depth))
6634                 return False;
6635         if (!prs_align(ps))
6636                 return False;
6637         if (!prs_uint32("size", ps, depth, &q_u->size))
6638                 return False;
6639
6640         return True;
6641 }
6642
6643 /*******************************************************************
6644  * write a structure.
6645  * called from spoolss_r_getprinterdataex (srv_spoolss.c)
6646  ********************************************************************/
6647
6648 BOOL spoolss_io_r_getprinterdataex(const char *desc, SPOOL_R_GETPRINTERDATAEX *r_u, prs_struct *ps, int depth)
6649 {
6650         if (r_u == NULL)
6651                 return False;
6652
6653         prs_debug(ps, depth, desc, "spoolss_io_r_getprinterdataex");
6654         depth++;
6655
6656         if (!prs_align(ps))
6657                 return False;
6658         if (!prs_uint32("type", ps, depth, &r_u->type))
6659                 return False;
6660         if (!prs_uint32("size", ps, depth, &r_u->size))
6661                 return False;
6662         
6663         if (UNMARSHALLING(ps) && r_u->size) {
6664                 r_u->data = PRS_ALLOC_MEM(ps, unsigned char, r_u->size);
6665                 if(!r_u->data)
6666                         return False;
6667         }
6668
6669         if (!prs_uint8s(False,"data", ps, depth, r_u->data, r_u->size))
6670                 return False;
6671                 
6672         if (!prs_align(ps))
6673                 return False;
6674         
6675         if (!prs_uint32("needed", ps, depth, &r_u->needed))
6676                 return False;
6677         if (!prs_werror("status", ps, depth, &r_u->status))
6678                 return False;
6679                 
6680         return True;
6681 }
6682
6683 /*******************************************************************
6684  * read a structure.
6685  ********************************************************************/  
6686
6687 BOOL spoolss_io_q_setprinterdataex(const char *desc, SPOOL_Q_SETPRINTERDATAEX *q_u, prs_struct *ps, int depth)
6688 {
6689         prs_debug(ps, depth, desc, "spoolss_io_q_setprinterdataex");
6690         depth++;
6691
6692         if(!prs_align(ps))
6693                 return False;
6694         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
6695                 return False;
6696         if(!smb_io_unistr2("", &q_u->key, True, ps, depth))
6697                 return False;
6698
6699         if(!prs_align(ps))
6700                 return False;
6701
6702         if(!smb_io_unistr2("", &q_u->value, True, ps, depth))
6703                 return False;
6704
6705         if(!prs_align(ps))
6706                 return False;
6707
6708         if(!prs_uint32("type", ps, depth, &q_u->type))
6709                 return False;
6710
6711         if(!prs_uint32("max_len", ps, depth, &q_u->max_len))
6712                 return False;
6713
6714         switch (q_u->type)
6715         {
6716                 case 0x1:
6717                 case 0x3:
6718                 case 0x4:
6719                 case 0x7:
6720                         if (q_u->max_len) {
6721                                 if (UNMARSHALLING(ps))
6722                                         q_u->data=PRS_ALLOC_MEM(ps, uint8, q_u->max_len);
6723                                 if(q_u->data == NULL)
6724                                         return False;
6725                                 if(!prs_uint8s(False,"data", ps, depth, q_u->data, q_u->max_len))
6726                                         return False;
6727                         }
6728                         if(!prs_align(ps))
6729                                 return False;
6730                         break;
6731         }       
6732         
6733         if(!prs_uint32("real_len", ps, depth, &q_u->real_len))
6734                 return False;
6735
6736         return True;
6737 }
6738
6739 /*******************************************************************
6740  * write a structure.
6741  ********************************************************************/  
6742
6743 BOOL spoolss_io_r_setprinterdataex(const char *desc, SPOOL_R_SETPRINTERDATAEX *r_u, prs_struct *ps, int depth)
6744 {
6745         prs_debug(ps, depth, desc, "spoolss_io_r_setprinterdataex");
6746         depth++;
6747
6748         if(!prs_align(ps))
6749                 return False;
6750         if(!prs_werror("status",     ps, depth, &r_u->status))
6751                 return False;
6752
6753         return True;
6754 }
6755
6756 /*******************************************************************
6757  * read a structure.
6758  ********************************************************************/  
6759 BOOL make_spoolss_q_enumprinterkey(SPOOL_Q_ENUMPRINTERKEY *q_u, 
6760                                    POLICY_HND *hnd, const char *key, 
6761                                    uint32 size)
6762 {
6763         DEBUG(5,("make_spoolss_q_enumprinterkey\n"));
6764
6765         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
6766         init_unistr2(&q_u->key, key, UNI_STR_TERMINATE);
6767         q_u->size = size;
6768
6769         return True;
6770 }
6771
6772 /*******************************************************************
6773  * read a structure.
6774  ********************************************************************/  
6775
6776 BOOL spoolss_io_q_enumprinterkey(const char *desc, SPOOL_Q_ENUMPRINTERKEY *q_u, prs_struct *ps, int depth)
6777 {
6778         prs_debug(ps, depth, desc, "spoolss_io_q_enumprinterkey");
6779         depth++;
6780
6781         if(!prs_align(ps))
6782                 return False;
6783         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
6784                 return False;
6785                 
6786         if(!smb_io_unistr2("", &q_u->key, True, ps, depth))
6787                 return False;
6788
6789         if(!prs_align(ps))
6790                 return False;
6791         
6792         if(!prs_uint32("size", ps, depth, &q_u->size))
6793                 return False;
6794
6795         return True;
6796 }
6797
6798 /*******************************************************************
6799  * write a structure.
6800  ********************************************************************/  
6801
6802 BOOL spoolss_io_r_enumprinterkey(const char *desc, SPOOL_R_ENUMPRINTERKEY *r_u, prs_struct *ps, int depth)
6803 {
6804         prs_debug(ps, depth, desc, "spoolss_io_r_enumprinterkey");
6805         depth++;
6806
6807         if(!prs_align(ps))
6808                 return False;
6809
6810         if (!smb_io_buffer5("", &r_u->keys, ps, depth))
6811                 return False;
6812         
6813         if(!prs_align(ps))
6814                 return False;
6815
6816         if(!prs_uint32("needed",     ps, depth, &r_u->needed))
6817                 return False;
6818
6819         if(!prs_werror("status",     ps, depth, &r_u->status))
6820                 return False;
6821
6822         return True;
6823 }
6824
6825 /*******************************************************************
6826  * read a structure.
6827  ********************************************************************/  
6828
6829 BOOL make_spoolss_q_deleteprinterkey(SPOOL_Q_DELETEPRINTERKEY *q_u, 
6830                                      POLICY_HND *hnd, char *keyname)
6831 {
6832         DEBUG(5,("make_spoolss_q_deleteprinterkey\n"));
6833
6834         memcpy(&q_u->handle, hnd, sizeof(q_u->handle));
6835         init_unistr2(&q_u->keyname, keyname, UNI_STR_TERMINATE);
6836
6837         return True;
6838 }
6839
6840 /*******************************************************************
6841  * read a structure.
6842  ********************************************************************/  
6843
6844 BOOL spoolss_io_q_deleteprinterkey(const char *desc, SPOOL_Q_DELETEPRINTERKEY *q_u, prs_struct *ps, int depth)
6845 {
6846         prs_debug(ps, depth, desc, "spoolss_io_q_deleteprinterkey");
6847         depth++;
6848
6849         if(!prs_align(ps))
6850                 return False;
6851         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
6852                 return False;
6853                 
6854         if(!smb_io_unistr2("", &q_u->keyname, True, ps, depth))
6855                 return False;
6856
6857         return True;
6858 }
6859
6860 /*******************************************************************
6861  * write a structure.
6862  ********************************************************************/  
6863
6864 BOOL spoolss_io_r_deleteprinterkey(const char *desc, SPOOL_R_DELETEPRINTERKEY *r_u, prs_struct *ps, int depth)
6865 {
6866         prs_debug(ps, depth, desc, "spoolss_io_r_deleteprinterkey");
6867         depth++;
6868
6869         if(!prs_align(ps))
6870                 return False;
6871                 
6872         if(!prs_werror("status",     ps, depth, &r_u->status))
6873                 return False;
6874
6875         return True;
6876 }
6877
6878
6879 /*******************************************************************
6880  * read a structure.
6881  ********************************************************************/  
6882
6883 BOOL spoolss_io_q_enumprinterdataex(const char *desc, SPOOL_Q_ENUMPRINTERDATAEX *q_u, prs_struct *ps, int depth)
6884 {
6885         prs_debug(ps, depth, desc, "spoolss_io_q_enumprinterdataex");
6886         depth++;
6887
6888         if(!prs_align(ps))
6889                 return False;
6890         if(!smb_io_pol_hnd("printer handle", &q_u->handle, ps, depth))
6891                 return False;
6892                 
6893         if(!smb_io_unistr2("", &q_u->key, True, ps, depth))
6894                 return False;
6895
6896         if(!prs_align(ps))
6897                 return False;
6898         
6899         if(!prs_uint32("size", ps, depth, &q_u->size))
6900                 return False;
6901
6902         return True;
6903 }
6904
6905 /*******************************************************************
6906 ********************************************************************/  
6907
6908 static BOOL spoolss_io_printer_enum_values_ctr(const char *desc, prs_struct *ps, 
6909                                 PRINTER_ENUM_VALUES_CTR *ctr, int depth)
6910 {
6911         int     i;
6912         uint32  valuename_offset,
6913                 data_offset,
6914                 current_offset;
6915         const uint32 basic_unit = 20; /* size of static portion of enum_values */
6916         
6917         prs_debug(ps, depth, desc, "spoolss_io_printer_enum_values_ctr");
6918         depth++;        
6919         
6920         /* 
6921          * offset data begins at 20 bytes per structure * size_of_array.
6922          * Don't forget the uint32 at the beginning 
6923          * */
6924         
6925         current_offset = basic_unit * ctr->size_of_array;
6926         
6927         /* first loop to write basic enum_value information */
6928         
6929         if (UNMARSHALLING(ps)) {
6930                 ctr->values = PRS_ALLOC_MEM(ps, PRINTER_ENUM_VALUES, ctr->size_of_array);
6931                 if (!ctr->values)
6932                         return False;
6933         }
6934
6935         for (i=0; i<ctr->size_of_array; i++) {
6936                 valuename_offset = current_offset;
6937                 if (!prs_uint32("valuename_offset", ps, depth, &valuename_offset))
6938                         return False;
6939
6940                 if (!prs_uint32("value_len", ps, depth, &ctr->values[i].value_len))
6941                         return False;
6942         
6943                 if (!prs_uint32("type", ps, depth, &ctr->values[i].type))
6944                         return False;
6945         
6946                 data_offset = ctr->values[i].value_len + valuename_offset;
6947                 
6948                 if (!prs_uint32("data_offset", ps, depth, &data_offset))
6949                         return False;
6950
6951                 if (!prs_uint32("data_len", ps, depth, &ctr->values[i].data_len))
6952                         return False;
6953                         
6954                 current_offset  = data_offset + ctr->values[i].data_len - basic_unit;
6955                 /* account for 2 byte alignment */
6956                 current_offset += (current_offset % 2);
6957         }
6958
6959         /* 
6960          * loop #2 for writing the dynamically size objects; pay 
6961          * attention to 2-byte alignment here....
6962          */
6963         
6964         for (i=0; i<ctr->size_of_array; i++) {
6965         
6966                 if (!prs_unistr("valuename", ps, depth, &ctr->values[i].valuename))
6967                         return False;
6968                 
6969                 if ( ctr->values[i].data_len ) {
6970                         if ( UNMARSHALLING(ps) ) {
6971                                 ctr->values[i].data = PRS_ALLOC_MEM(ps, uint8, ctr->values[i].data_len);
6972                                 if (!ctr->values[i].data)
6973                                         return False;
6974                         }
6975                         if (!prs_uint8s(False, "data", ps, depth, ctr->values[i].data, ctr->values[i].data_len))
6976                                 return False;
6977                 }
6978                         
6979                 if ( !prs_align_uint16(ps) )
6980                         return False;
6981         }
6982
6983         return True;    
6984 }
6985
6986 /*******************************************************************
6987  * write a structure.
6988  ********************************************************************/  
6989
6990 BOOL spoolss_io_r_enumprinterdataex(const char *desc, SPOOL_R_ENUMPRINTERDATAEX *r_u, prs_struct *ps, int depth)
6991 {
6992         uint32 data_offset, end_offset;
6993         prs_debug(ps, depth, desc, "spoolss_io_r_enumprinterdataex");
6994         depth++;
6995
6996         if(!prs_align(ps))
6997                 return False;
6998
6999         if (!prs_uint32("size", ps, depth, &r_u->ctr.size))
7000                 return False;
7001
7002         data_offset = prs_offset(ps);
7003
7004         if (!prs_set_offset(ps, data_offset + r_u->ctr.size))
7005                 return False;
7006
7007         if(!prs_align(ps))
7008                 return False;
7009
7010         if(!prs_uint32("needed",     ps, depth, &r_u->needed))
7011                 return False;
7012
7013         if(!prs_uint32("returned",   ps, depth, &r_u->returned))
7014                 return False;
7015
7016         if(!prs_werror("status",     ps, depth, &r_u->status))
7017                 return False;
7018
7019         r_u->ctr.size_of_array = r_u->returned;
7020
7021         end_offset = prs_offset(ps);
7022
7023         if (!prs_set_offset(ps, data_offset))
7024                 return False;
7025
7026         if (r_u->ctr.size)
7027                 if (!spoolss_io_printer_enum_values_ctr("", ps, &r_u->ctr, depth ))
7028                         return False;
7029
7030         if (!prs_set_offset(ps, end_offset))
7031                 return False;
7032         return True;
7033 }
7034
7035 /*******************************************************************
7036  * write a structure.
7037  ********************************************************************/  
7038
7039 /* 
7040    uint32 GetPrintProcessorDirectory(
7041        [in] unistr2 *name,
7042        [in] unistr2 *environment,
7043        [in] uint32 level,
7044        [in,out] RPC_BUFFER buffer,
7045        [in] uint32 offered,
7046        [out] uint32 needed,
7047        [out] uint32 returned
7048    );
7049
7050 */
7051
7052 BOOL make_spoolss_q_getprintprocessordirectory(SPOOL_Q_GETPRINTPROCESSORDIRECTORY *q_u, const char *name, char *environment, int level, RPC_BUFFER *buffer, uint32 offered)
7053 {
7054         DEBUG(5,("make_spoolss_q_getprintprocessordirectory\n"));
7055
7056         init_unistr2(&q_u->name, name, UNI_STR_TERMINATE);
7057         init_unistr2(&q_u->environment, environment, UNI_STR_TERMINATE);
7058
7059         q_u->level = level;
7060
7061         q_u->buffer = buffer;
7062         q_u->offered = offered;
7063
7064         return True;
7065 }
7066
7067 BOOL spoolss_io_q_getprintprocessordirectory(const char *desc, SPOOL_Q_GETPRINTPROCESSORDIRECTORY *q_u, prs_struct *ps, int depth)
7068 {
7069         uint32 ptr;
7070
7071         prs_debug(ps, depth, desc, "spoolss_io_q_getprintprocessordirectory");
7072         depth++;
7073
7074         if(!prs_align(ps))
7075                 return False;   
7076
7077         if (!prs_uint32("ptr", ps, depth, &ptr)) 
7078                 return False;
7079
7080         if (ptr) {
7081                 if(!smb_io_unistr2("name", &q_u->name, True, ps, depth))
7082                         return False;
7083         }
7084
7085         if (!prs_align(ps))
7086                 return False;
7087
7088         if (!prs_uint32("ptr", ps, depth, &ptr))
7089                 return False;
7090
7091         if (ptr) {
7092                 if(!smb_io_unistr2("environment", &q_u->environment, True, 
7093                                    ps, depth))
7094                         return False;
7095         }
7096
7097         if (!prs_align(ps))
7098                 return False;
7099
7100         if(!prs_uint32("level",   ps, depth, &q_u->level))
7101                 return False;
7102
7103         if(!prs_rpcbuffer_p("", ps, depth, &q_u->buffer))
7104                 return False;
7105         
7106         if(!prs_align(ps))
7107                 return False;
7108
7109         if(!prs_uint32("offered", ps, depth, &q_u->offered))
7110                 return False;
7111
7112         return True;
7113 }
7114
7115 /*******************************************************************
7116  * write a structure.
7117  ********************************************************************/  
7118
7119 BOOL spoolss_io_r_getprintprocessordirectory(const char *desc, SPOOL_R_GETPRINTPROCESSORDIRECTORY *r_u, prs_struct *ps, int depth)
7120 {
7121         prs_debug(ps, depth, desc, "spoolss_io_r_getprintprocessordirectory");
7122         depth++;
7123
7124         if(!prs_align(ps))
7125                 return False;
7126
7127         if(!prs_rpcbuffer_p("", ps, depth, &r_u->buffer))
7128                 return False;
7129         
7130         if(!prs_align(ps))
7131                 return False;
7132
7133         if(!prs_uint32("needed",     ps, depth, &r_u->needed))
7134                 return False;
7135                 
7136         if(!prs_werror("status",     ps, depth, &r_u->status))
7137                 return False;
7138
7139         return True;
7140 }
7141
7142 BOOL smb_io_printprocessordirectory_1(const char *desc, RPC_BUFFER *buffer, PRINTPROCESSOR_DIRECTORY_1 *info, int depth)
7143 {
7144         prs_struct *ps=&buffer->prs;
7145
7146         prs_debug(ps, depth, desc, "smb_io_printprocessordirectory_1");
7147         depth++;
7148
7149         buffer->struct_start=prs_offset(ps);
7150
7151         if (!smb_io_unistr(desc, &info->name, ps, depth))
7152                 return False;
7153
7154         return True;
7155 }
7156
7157 /*******************************************************************
7158  * init a structure.
7159  ********************************************************************/
7160
7161 BOOL make_spoolss_q_addform(SPOOL_Q_ADDFORM *q_u, POLICY_HND *handle, 
7162                             int level, FORM *form)
7163 {
7164         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7165         q_u->level = level;
7166         q_u->level2 = level;
7167         memcpy(&q_u->form, form, sizeof(FORM));
7168
7169         return True;
7170 }
7171
7172 /*******************************************************************
7173  * init a structure.
7174  ********************************************************************/
7175
7176 BOOL make_spoolss_q_setform(SPOOL_Q_SETFORM *q_u, POLICY_HND *handle, 
7177                             int level, const char *form_name, FORM *form)
7178 {
7179         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7180         q_u->level = level;
7181         q_u->level2 = level;
7182         memcpy(&q_u->form, form, sizeof(FORM));
7183         init_unistr2(&q_u->name, form_name, UNI_STR_TERMINATE);
7184
7185         return True;
7186 }
7187
7188 /*******************************************************************
7189  * init a structure.
7190  ********************************************************************/
7191
7192 BOOL make_spoolss_q_deleteform(SPOOL_Q_DELETEFORM *q_u, POLICY_HND *handle, 
7193                                const char *form)
7194 {
7195         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7196         init_unistr2(&q_u->name, form, UNI_STR_TERMINATE);
7197         return True;
7198 }
7199
7200 /*******************************************************************
7201  * init a structure.
7202  ********************************************************************/
7203
7204 BOOL make_spoolss_q_getform(SPOOL_Q_GETFORM *q_u, POLICY_HND *handle, 
7205                             const char *formname, uint32 level, 
7206                             RPC_BUFFER *buffer, uint32 offered)
7207 {
7208         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7209         q_u->level = level;
7210         init_unistr2(&q_u->formname, formname, UNI_STR_TERMINATE);
7211         q_u->buffer=buffer;
7212         q_u->offered=offered;
7213
7214         return True;
7215 }
7216
7217 /*******************************************************************
7218  * init a structure.
7219  ********************************************************************/
7220
7221 BOOL make_spoolss_q_enumforms(SPOOL_Q_ENUMFORMS *q_u, POLICY_HND *handle, 
7222                               uint32 level, RPC_BUFFER *buffer,
7223                               uint32 offered)
7224 {
7225         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7226         q_u->level = level;
7227         q_u->buffer=buffer;
7228         q_u->offered=offered;
7229
7230         return True;
7231 }
7232
7233 /*******************************************************************
7234  * init a structure.
7235  ********************************************************************/
7236
7237 BOOL make_spoolss_q_setjob(SPOOL_Q_SETJOB *q_u, POLICY_HND *handle, 
7238                            uint32 jobid, uint32 level, uint32 command)
7239 {
7240         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7241         q_u->jobid = jobid;
7242         q_u->level = level;
7243
7244         /* Hmm - the SPOOL_Q_SETJOB structure has a JOB_INFO ctr in it but
7245            the server side code has it marked as unused. */
7246
7247         q_u->command = command;
7248
7249         return True;
7250 }
7251
7252 /*******************************************************************
7253  * init a structure.
7254  ********************************************************************/
7255
7256 BOOL make_spoolss_q_getjob(SPOOL_Q_GETJOB *q_u, POLICY_HND *handle, 
7257                            uint32 jobid, uint32 level, RPC_BUFFER *buffer,
7258                            uint32 offered)
7259 {
7260         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7261         q_u->jobid = jobid;
7262         q_u->level = level;
7263         q_u->buffer = buffer;
7264         q_u->offered = offered;
7265
7266         return True;
7267 }
7268
7269 /*******************************************************************
7270  * init a structure.
7271  ********************************************************************/
7272
7273 BOOL make_spoolss_q_startpageprinter(SPOOL_Q_STARTPAGEPRINTER *q_u, 
7274                                      POLICY_HND *handle)
7275 {
7276         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7277
7278         return True;
7279 }
7280
7281 /*******************************************************************
7282  * init a structure.
7283  ********************************************************************/
7284
7285 BOOL make_spoolss_q_endpageprinter(SPOOL_Q_ENDPAGEPRINTER *q_u, 
7286                                    POLICY_HND *handle)
7287 {
7288         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7289
7290         return True;
7291 }
7292
7293 /*******************************************************************
7294  * init a structure.
7295  ********************************************************************/
7296
7297 BOOL make_spoolss_q_startdocprinter(SPOOL_Q_STARTDOCPRINTER *q_u, 
7298                                     POLICY_HND *handle, uint32 level,
7299                                     char *docname, char *outputfile,
7300                                     char *datatype)
7301 {
7302         DOC_INFO_CONTAINER *ctr = &q_u->doc_info_container;
7303
7304         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7305
7306         ctr->level = level;
7307
7308         switch (level) {
7309         case 1:
7310                 ctr->docinfo.switch_value = level;
7311
7312                 ctr->docinfo.doc_info_1.p_docname = docname ? 1 : 0;
7313                 ctr->docinfo.doc_info_1.p_outputfile = outputfile ? 1 : 0;
7314                 ctr->docinfo.doc_info_1.p_datatype = datatype ? 1 : 0;
7315
7316                 init_unistr2(&ctr->docinfo.doc_info_1.docname, docname, UNI_STR_TERMINATE);
7317                 init_unistr2(&ctr->docinfo.doc_info_1.outputfile, outputfile, UNI_STR_TERMINATE);
7318                 init_unistr2(&ctr->docinfo.doc_info_1.datatype, datatype, UNI_STR_TERMINATE);
7319
7320                 break;
7321         case 2:
7322                 /* DOC_INFO_2 is only used by Windows 9x and since it
7323                    doesn't do printing over RPC we don't have to worry
7324                    about it. */
7325         default:
7326                 DEBUG(3, ("unsupported info level %d\n", level));
7327                 return False;
7328         }
7329
7330         return True;
7331 }
7332
7333 /*******************************************************************
7334  * init a structure.
7335  ********************************************************************/
7336
7337 BOOL make_spoolss_q_enddocprinter(SPOOL_Q_ENDDOCPRINTER *q_u, 
7338                                   POLICY_HND *handle)
7339 {
7340         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7341
7342         return True;
7343 }
7344
7345 /*******************************************************************
7346  * init a structure.
7347  ********************************************************************/
7348
7349 BOOL make_spoolss_q_writeprinter(SPOOL_Q_WRITEPRINTER *q_u, 
7350                                  POLICY_HND *handle, uint32 data_size,
7351                                  char *data)
7352 {
7353         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7354         q_u->buffer_size = q_u->buffer_size2 = data_size;
7355         q_u->buffer = (unsigned char *)data;
7356         return True;
7357 }
7358
7359 /*******************************************************************
7360  * init a structure.
7361  ********************************************************************/
7362
7363 BOOL make_spoolss_q_deleteprinterdata(SPOOL_Q_DELETEPRINTERDATA *q_u, 
7364                                  POLICY_HND *handle, char *valuename)
7365 {
7366         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7367         init_unistr2(&q_u->valuename, valuename, UNI_STR_TERMINATE);
7368
7369         return True;
7370 }
7371
7372 /*******************************************************************
7373  * init a structure.
7374  ********************************************************************/
7375
7376 BOOL make_spoolss_q_deleteprinterdataex(SPOOL_Q_DELETEPRINTERDATAEX *q_u, 
7377                                         POLICY_HND *handle, char *key,
7378                                         char *value)
7379 {
7380         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7381         init_unistr2(&q_u->valuename, value, UNI_STR_TERMINATE);
7382         init_unistr2(&q_u->keyname, key, UNI_STR_TERMINATE);
7383
7384         return True;
7385 }
7386
7387 /*******************************************************************
7388  * init a structure.
7389  ********************************************************************/
7390
7391 BOOL make_spoolss_q_rffpcnex(SPOOL_Q_RFFPCNEX *q_u, POLICY_HND *handle,
7392                              uint32 flags, uint32 options, const char *localmachine,
7393                              uint32 printerlocal, SPOOL_NOTIFY_OPTION *option)
7394 {
7395         memcpy(&q_u->handle, handle, sizeof(POLICY_HND));
7396
7397         q_u->flags = flags;
7398         q_u->options = options;
7399
7400         q_u->localmachine_ptr = 1;
7401
7402         init_unistr2(&q_u->localmachine, localmachine, UNI_STR_TERMINATE);
7403
7404         q_u->printerlocal = printerlocal;
7405
7406         if (option)
7407                 q_u->option_ptr = 1;
7408
7409         q_u->option = option;
7410
7411         return True;
7412 }