r7839: remove C++ style comment
[ira/wip.git] / source3 / rpc_parse / parse_svcctl.c
1 /* 
2  *  Unix SMB/CIFS implementation.
3  *  RPC Pipe client / server routines
4  *  Copyright (C) Gerald (Jerry) Carter             2005.
5  *  
6  *  This program is free software; you can redistribute it and/or modify
7  *  it under the terms of the GNU General Public License as published by
8  *  the Free Software Foundation; either version 2 of the License, or
9  *  (at your option) any later version.
10  *  
11  *  This program is distributed in the hope that it will be useful,
12  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  *  GNU General Public License for more details.
15  *  
16  *  You should have received a copy of the GNU General Public License
17  *  along with this program; if not, write to the Free Software
18  *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19  */
20
21 #include "includes.h"
22
23 #undef DBGC_CLASS
24 #define DBGC_CLASS DBGC_RPC_PARSE
25
26 /*******************************************************************
27 ********************************************************************/
28
29 static BOOL svcctl_io_service_status( const char *desc, SERVICE_STATUS *status, prs_struct *ps, int depth )
30 {
31
32         prs_debug(ps, depth, desc, "svcctl_io_service_status");
33         depth++;
34
35         if(!prs_uint32("type", ps, depth, &status->type))
36                 return False;
37
38         if(!prs_uint32("state", ps, depth, &status->state))
39                 return False;
40
41         if(!prs_uint32("controls_accepted", ps, depth, &status->controls_accepted))
42                 return False;
43
44         if(!prs_uint32("win32_exit_code", ps, depth, &status->win32_exit_code))
45                 return False;
46
47         if(!prs_uint32("service_exit_code", ps, depth, &status->service_exit_code))
48                 return False;
49
50         if(!prs_uint32("check_point", ps, depth, &status->check_point))
51                 return False;
52
53         if(!prs_uint32("wait_hint", ps, depth, &status->wait_hint))
54                 return False;
55
56         return True;
57 }
58
59 /*******************************************************************
60 ********************************************************************/
61
62 static BOOL svcctl_io_service_config( const char *desc, SERVICE_CONFIG *config, prs_struct *ps, int depth )
63 {
64
65         prs_debug(ps, depth, desc, "svcctl_io_service_config");
66         depth++;
67
68         if(!prs_uint32("service_type", ps, depth, &config->service_type))
69                 return False;
70         if(!prs_uint32("start_type", ps, depth, &config->start_type))
71                 return False;
72         if(!prs_uint32("error_control", ps, depth, &config->error_control))
73                 return False;
74
75         if (!prs_io_unistr2_p("", ps, depth, &config->executablepath))
76                 return False;
77         if (!prs_io_unistr2_p("", ps, depth, &config->loadordergroup))
78                 return False;
79
80         if(!prs_uint32("tag_id", ps, depth, &config->tag_id))
81                 return False;
82
83         if (!prs_io_unistr2_p("", ps, depth, &config->dependencies))
84                 return False;
85         if (!prs_io_unistr2_p("", ps, depth, &config->startname))
86                 return False;
87         if (!prs_io_unistr2_p("", ps, depth, &config->displayname))
88                 return False;
89
90         if (!prs_io_unistr2("", ps, depth, config->executablepath))
91                 return False;
92         if (!prs_io_unistr2("", ps, depth, config->loadordergroup))
93                 return False;
94         if (!prs_io_unistr2("", ps, depth, config->dependencies))
95                 return False;
96         if (!prs_io_unistr2("", ps, depth, config->startname))
97                 return False;
98         if (!prs_io_unistr2("", ps, depth, config->displayname))
99                 return False;
100
101         return True;
102 }
103 /*******************************************************************
104 ********************************************************************/
105
106 BOOL svcctl_io_service_description( const char *desc, UNISTR2 *svcdesc, prs_struct *ps, int depth )
107 {
108
109         prs_debug(ps, depth, desc, "svcctl_io_service_description");
110         depth++;
111
112         if (!prs_io_unistr2("", ps, depth, svcdesc))
113                 return False;
114
115         return True;
116 }
117
118
119 /*******************************************************************
120 ********************************************************************/
121
122 BOOL svcctl_io_enum_services_status( const char *desc, ENUM_SERVICES_STATUS *enum_status, RPC_BUFFER *buffer, int depth )
123 {
124         prs_struct *ps=&buffer->prs;
125         
126         prs_debug(ps, depth, desc, "svcctl_io_enum_services_status");
127         depth++;
128         
129         if ( !smb_io_relstr("servicename", buffer, depth, &enum_status->servicename) )
130                 return False;
131         if ( !smb_io_relstr("displayname", buffer, depth, &enum_status->displayname) )
132                 return False;
133
134         if ( !svcctl_io_service_status("svc_status", &enum_status->status, ps, depth) )
135                 return False;
136         
137         return True;
138 }
139
140 /*******************************************************************
141 ********************************************************************/
142
143 uint32 svcctl_sizeof_enum_services_status( ENUM_SERVICES_STATUS *status )
144 {
145         uint32 size = 0;
146         
147         size += size_of_relative_string( &status->servicename );
148         size += size_of_relative_string( &status->displayname );
149         size += sizeof(SERVICE_STATUS);
150
151         return size;
152 }
153
154 /*******************************************************************
155 ********************************************************************/
156
157 BOOL svcctl_io_q_close_service(const char *desc, SVCCTL_Q_CLOSE_SERVICE *q_u, prs_struct *ps, int depth)
158 {
159         
160         if (q_u == NULL)
161                 return False;
162
163         prs_debug(ps, depth, desc, "svcctl_io_q_close_service");
164         depth++;
165
166         if(!prs_align(ps))
167                 return False;
168
169         if(!smb_io_pol_hnd("scm_pol", &q_u->handle, ps, depth))
170                 return False;
171
172         return True;
173 }
174
175
176 /*******************************************************************
177 ********************************************************************/
178
179 BOOL svcctl_io_r_close_service(const char *desc, SVCCTL_R_CLOSE_SERVICE *r_u, prs_struct *ps, int depth)
180 {
181         if (r_u == NULL)
182                 return False;
183
184         prs_debug(ps, depth, desc, "svcctl_io_r_close_service");
185         depth++;
186
187         if(!prs_align(ps))
188             return False;
189
190         if(!smb_io_pol_hnd("pol_handle", &r_u->handle, ps, depth))
191            return False; 
192
193         if(!prs_werror("status", ps, depth, &r_u->status))
194                 return False;
195
196         return True;
197 }
198
199 /*******************************************************************
200 ********************************************************************/
201
202 BOOL svcctl_io_q_open_scmanager(const char *desc, SVCCTL_Q_OPEN_SCMANAGER *q_u, prs_struct *ps, int depth)
203 {
204         if (q_u == NULL)
205                 return False;
206
207         prs_debug(ps, depth, desc, "svcctl_io_q_open_scmanager");
208         depth++;
209
210         if(!prs_align(ps))
211                 return False;
212
213         if(!prs_pointer("servername", ps, depth, (void**)&q_u->servername, sizeof(UNISTR2), (PRS_POINTER_CAST)prs_io_unistr2))
214                 return False;
215         if(!prs_align(ps))
216                 return False;
217
218         if(!prs_pointer("database", ps, depth, (void**)&q_u->database, sizeof(UNISTR2), (PRS_POINTER_CAST)prs_io_unistr2))
219                 return False;
220         if(!prs_align(ps))
221                 return False;
222
223         if(!prs_uint32("access", ps, depth, &q_u->access))
224                 return False;
225
226         return True;
227 }
228
229 /*******************************************************************
230 ********************************************************************/
231
232 BOOL svcctl_io_r_open_scmanager(const char *desc, SVCCTL_R_OPEN_SCMANAGER *r_u, prs_struct *ps, int depth)
233 {
234         if (r_u == NULL)
235                 return False;
236
237         prs_debug(ps, depth, desc, "svcctl_io_r_open_scmanager");
238         depth++;
239
240         if(!prs_align(ps))
241                 return False;
242
243         if(!smb_io_pol_hnd("scm_pol", &r_u->handle, ps, depth))
244                 return False;
245
246         if(!prs_werror("status", ps, depth, &r_u->status))
247                 return False;
248
249         return True;
250 }
251
252 /*******************************************************************
253 ********************************************************************/
254
255 BOOL svcctl_io_q_get_display_name(const char *desc, SVCCTL_Q_GET_DISPLAY_NAME *q_u, prs_struct *ps, int depth)
256 {
257         if (q_u == NULL)
258                 return False;
259
260         prs_debug(ps, depth, desc, "svcctl_io_q_get_display_name");
261         depth++;
262
263         if(!prs_align(ps))
264                 return False;
265
266         if(!smb_io_pol_hnd("scm_pol", &q_u->handle, ps, depth))
267                 return False;
268
269         if(!smb_io_unistr2("servicename", &q_u->servicename, 1, ps, depth))
270                 return False;
271
272         if(!prs_align(ps))
273                 return False;
274
275         if(!prs_uint32("display_name_len", ps, depth, &q_u->display_name_len))
276                 return False;
277         
278         return True;
279 }
280
281 /*******************************************************************
282 ********************************************************************/
283
284 BOOL init_svcctl_r_get_display_name( SVCCTL_R_GET_DISPLAY_NAME *r_u, const char *displayname )
285 {
286         r_u->display_name_len = strlen(displayname);
287         init_unistr2( &r_u->displayname, displayname, UNI_STR_TERMINATE );
288
289         return True;
290 }
291
292 /*******************************************************************
293 ********************************************************************/
294
295 BOOL svcctl_io_r_get_display_name(const char *desc, SVCCTL_R_GET_DISPLAY_NAME *r_u, prs_struct *ps, int depth)
296 {
297         if (r_u == NULL)
298                 return False;
299
300         prs_debug(ps, depth, desc, "svcctl_io_r_get_display_name");
301         depth++;
302
303         if(!prs_align(ps))
304                 return False;
305
306         
307         if(!smb_io_unistr2("displayname", &r_u->displayname, 1, ps, depth))
308                 return False;
309
310         if(!prs_align(ps))
311                 return False;
312
313         if(!prs_uint32("display_name_len", ps, depth, &r_u->display_name_len))
314                 return False;
315
316         if(!prs_werror("status", ps, depth, &r_u->status))
317                 return False;
318
319         return True;
320 }
321
322
323 /*******************************************************************
324 ********************************************************************/
325
326 BOOL svcctl_io_q_open_service(const char *desc, SVCCTL_Q_OPEN_SERVICE *q_u, prs_struct *ps, int depth)
327 {
328         if (q_u == NULL)
329                 return False;
330
331         prs_debug(ps, depth, desc, "svcctl_io_q_open_service");
332         depth++;
333
334         if(!prs_align(ps))
335                 return False;
336
337         if(!smb_io_pol_hnd("scm_pol", &q_u->handle, ps, depth))
338                 return False;
339
340         if(!smb_io_unistr2("servicename", &q_u->servicename, 1, ps, depth))
341                 return False;
342
343         if(!prs_align(ps))
344                 return False;
345
346         if(!prs_uint32("access", ps, depth, &q_u->access))
347                 return False;
348         
349         return True;
350 }
351
352 /*******************************************************************
353 ********************************************************************/
354
355 BOOL svcctl_io_r_open_service(const char *desc, SVCCTL_R_OPEN_SERVICE *r_u, prs_struct *ps, int depth)
356 {
357         if (r_u == NULL)
358                 return False;
359
360         prs_debug(ps, depth, desc, "svcctl_io_r_open_service");
361         depth++;
362
363         if(!prs_align(ps))
364                 return False;
365
366         if(!smb_io_pol_hnd("service_pol", &r_u->handle, ps, depth))
367                 return False;
368
369         if(!prs_werror("status", ps, depth, &r_u->status))
370                 return False;
371
372         return True;
373 }
374
375 /*******************************************************************
376 ********************************************************************/
377
378 BOOL svcctl_io_q_query_status(const char *desc, SVCCTL_Q_QUERY_STATUS *q_u, prs_struct *ps, int depth)
379 {
380         if (q_u == NULL)
381                 return False;
382
383         prs_debug(ps, depth, desc, "svcctl_io_q_query_status");
384         depth++;
385
386         if(!prs_align(ps))
387                 return False;
388
389         if(!smb_io_pol_hnd("service_pol", &q_u->handle, ps, depth))
390                 return False;
391         
392         return True;
393 }
394
395 /*******************************************************************
396 ********************************************************************/
397
398 BOOL svcctl_io_r_query_status(const char *desc, SVCCTL_R_QUERY_STATUS *r_u, prs_struct *ps, int depth)
399 {
400         if (r_u == NULL)
401                 return False;
402
403         prs_debug(ps, depth, desc, "svcctl_io_r_query_status");
404         depth++;
405
406         if(!prs_align(ps))
407                 return False;
408
409         if(!svcctl_io_service_status("service_status", &r_u->svc_status, ps, depth))
410                 return False;
411
412         if(!prs_werror("status", ps, depth, &r_u->status))
413                 return False;
414
415         return True;
416 }
417
418 /*******************************************************************
419 ********************************************************************/
420
421 BOOL svcctl_io_q_enum_services_status(const char *desc, SVCCTL_Q_ENUM_SERVICES_STATUS *q_u, prs_struct *ps, int depth)
422 {
423         if (q_u == NULL)
424                 return False;
425
426         prs_debug(ps, depth, desc, "svcctl_io_q_enum_services_status");
427         depth++;
428
429         if(!prs_align(ps))
430                 return False;
431
432         if(!smb_io_pol_hnd("scm_pol", &q_u->handle, ps, depth))
433                 return False;
434
435         if(!prs_uint32("type", ps, depth, &q_u->type))
436                 return False;
437         if(!prs_uint32("state", ps, depth, &q_u->state))
438                 return False;
439         if(!prs_uint32("buffer_size", ps, depth, &q_u->buffer_size))
440                 return False;
441
442         if(!prs_pointer("resume", ps, depth, (void**)&q_u->resume, sizeof(uint32), (PRS_POINTER_CAST)prs_uint32))
443                 return False;
444         
445         return True;
446 }
447
448 /*******************************************************************
449 ********************************************************************/
450
451 BOOL svcctl_io_r_enum_services_status(const char *desc, SVCCTL_R_ENUM_SERVICES_STATUS *r_u, prs_struct *ps, int depth)
452 {
453         if (r_u == NULL)
454                 return False;
455
456         prs_debug(ps, depth, desc, "svcctl_io_r_enum_services_status");
457         depth++;
458
459         if(!prs_align(ps))
460                 return False;
461
462         if (!prs_rpcbuffer("", ps, depth, &r_u->buffer))
463                 return False;
464
465         if(!prs_align(ps))
466                 return False;
467
468         if(!prs_uint32("needed", ps, depth, &r_u->needed))
469                 return False;
470         if(!prs_uint32("returned", ps, depth, &r_u->returned))
471                 return False;
472
473         if(!prs_pointer("resume", ps, depth, (void**)&r_u->resume, sizeof(uint32), (PRS_POINTER_CAST)prs_uint32))
474                 return False;
475
476         if(!prs_werror("status", ps, depth, &r_u->status))
477                 return False;
478
479         return True;
480 }
481
482 /*******************************************************************
483 ********************************************************************/
484
485 BOOL svcctl_io_q_start_service(const char *desc, SVCCTL_Q_START_SERVICE *q_u, prs_struct *ps, int depth)
486 {
487         if (q_u == NULL)
488                 return False;
489
490         prs_debug(ps, depth, desc, "svcctl_io_q_start_service");
491         depth++;
492
493         if(!prs_align(ps))
494                 return False;
495
496         if(!smb_io_pol_hnd("service_pol", &q_u->handle, ps, depth))
497                 return False;
498
499         if(!prs_uint32("parmcount", ps, depth, &q_u->parmcount))
500                 return False;
501
502         if ( !prs_pointer("rights", ps, depth, (void**)&q_u->parameters, sizeof(UNISTR4_ARRAY), (PRS_POINTER_CAST)prs_unistr4_array) )
503                 return False;
504
505         return True;
506 }
507
508 /*******************************************************************
509 ********************************************************************/
510
511 BOOL svcctl_io_r_start_service(const char *desc, SVCCTL_R_START_SERVICE *r_u, prs_struct *ps, int depth)
512 {
513         if (r_u == NULL)
514                 return False;
515
516         prs_debug(ps, depth, desc, "svcctl_io_r_start_service");
517         depth++;
518
519         if(!prs_werror("status", ps, depth, &r_u->status))
520                 return False;
521
522         return True;
523 }
524
525
526 /*******************************************************************
527 ********************************************************************/
528
529 BOOL svcctl_io_q_enum_dependent_services(const char *desc, SVCCTL_Q_ENUM_DEPENDENT_SERVICES *q_u, prs_struct *ps, int depth)
530 {
531         if (q_u == NULL)
532                 return False;
533
534         prs_debug(ps, depth, desc, "svcctl_io_q_enum_dependent_services");
535         depth++;
536
537         if(!prs_align(ps))
538                 return False;
539
540         if(!smb_io_pol_hnd("service_pol", &q_u->handle, ps, depth))
541                 return False;
542
543         if(!prs_uint32("state", ps, depth, &q_u->state))
544                 return False;
545         if(!prs_uint32("buffer_size", ps, depth, &q_u->buffer_size))
546                 return False;
547
548         return True;
549 }
550
551 /*******************************************************************
552 ********************************************************************/
553
554 BOOL svcctl_io_r_enum_dependent_services(const char *desc, SVCCTL_R_ENUM_DEPENDENT_SERVICES *r_u, prs_struct *ps, int depth)
555 {
556         if (r_u == NULL)
557                 return False;
558
559         prs_debug(ps, depth, desc, "svcctl_io_r_enum_dependent_services");
560         depth++;
561
562         if(!prs_align(ps))
563                 return False;
564
565         if (!prs_rpcbuffer("", ps, depth, &r_u->buffer))
566                 return False;
567
568         if(!prs_align(ps))
569                 return False;
570
571         if(!prs_uint32("needed", ps, depth, &r_u->needed))
572                 return False;
573         if(!prs_uint32("returned", ps, depth, &r_u->returned))
574                 return False;
575
576         if(!prs_werror("status", ps, depth, &r_u->status))
577                 return False;
578
579         return True;
580 }
581
582 /*******************************************************************
583 ********************************************************************/
584
585 BOOL svcctl_io_q_control_service(const char *desc, SVCCTL_Q_CONTROL_SERVICE *q_u, prs_struct *ps, int depth)
586 {
587         if (q_u == NULL)
588                 return False;
589
590         prs_debug(ps, depth, desc, "svcctl_io_q_control_service");
591         depth++;
592
593         if(!prs_align(ps))
594                 return False;
595
596         if(!smb_io_pol_hnd("service_pol", &q_u->handle, ps, depth))
597                 return False;
598
599         if(!prs_uint32("control", ps, depth, &q_u->control))
600                 return False;
601
602         return True;
603 }
604
605 /*******************************************************************
606 ********************************************************************/
607
608 BOOL svcctl_io_r_control_service(const char *desc, SVCCTL_R_CONTROL_SERVICE *r_u, prs_struct *ps, int depth)
609 {
610         if (r_u == NULL)
611                 return False;
612
613         prs_debug(ps, depth, desc, "svcctl_io_r_control_service");
614         depth++;
615
616         if(!prs_align(ps))
617                 return False;
618
619         if(!svcctl_io_service_status("service_status", &r_u->svc_status, ps, depth))
620                 return False;
621
622         if(!prs_werror("status", ps, depth, &r_u->status))
623                 return False;
624
625         return True;
626 }
627
628
629 /*******************************************************************
630 ********************************************************************/
631
632 BOOL svcctl_io_q_query_service_config(const char *desc, SVCCTL_Q_QUERY_SERVICE_CONFIG *q_u, prs_struct *ps, int depth)
633 {
634         if (q_u == NULL)
635                 return False;
636
637         prs_debug(ps, depth, desc, "svcctl_io_q_query_service_config");
638         depth++;
639
640         if(!prs_align(ps))
641                 return False;
642
643         if(!smb_io_pol_hnd("service_pol", &q_u->handle, ps, depth))
644                 return False;
645
646         if(!prs_uint32("buffer_size", ps, depth, &q_u->buffer_size))
647                 return False;
648
649         return True;
650 }
651
652 /*******************************************************************
653 ********************************************************************/
654
655 BOOL svcctl_io_r_query_service_config(const char *desc, SVCCTL_R_QUERY_SERVICE_CONFIG *r_u, prs_struct *ps, int depth)
656 {
657         if (r_u == NULL)
658                 return False;
659
660         prs_debug(ps, depth, desc, "svcctl_io_r_query_service_config");
661         depth++;
662
663
664         if(!prs_align(ps))
665                 return False;
666
667         if(!svcctl_io_service_config("config", &r_u->config, ps, depth))
668                 return False;
669
670         if(!prs_uint32("needed", ps, depth, &r_u->needed))
671                 return False;
672
673         if(!prs_werror("status", ps, depth, &r_u->status))
674                 return False;
675
676
677         return True;
678 }
679
680 /*******************************************************************
681 ********************************************************************/
682
683 BOOL svcctl_io_q_query_service_config2(const char *desc, SVCCTL_Q_QUERY_SERVICE_CONFIG2 *q_u, prs_struct *ps, int depth)
684 {
685         if (q_u == NULL)
686                 return False;
687
688         prs_debug(ps, depth, desc, "svcctl_io_q_query_service_config2");
689         depth++;
690
691         if(!prs_align(ps))
692                 return False;
693
694         if(!smb_io_pol_hnd("service_pol", &q_u->handle, ps, depth))
695                 return False;
696
697         if(!prs_uint32("info_level", ps, depth, &q_u->info_level))
698                 return False;
699
700         if(!prs_uint32("buffer_size", ps, depth, &q_u->buffer_size))
701                 return False;
702
703         return True;
704 }
705
706
707 /*******************************************************************
708  Creates a service description response buffer.
709  The format seems to be DWORD:length of buffer
710                         DWORD:offset (fixed as four)
711                         UNISTR: unicode description in the rest of the buffer
712 ********************************************************************/
713
714 void init_service_description_buffer(RPC_DATA_BLOB *str,  const char *service_desc, int blob_length)
715 {
716         uint32 offset;
717         char *bp;
718
719         ZERO_STRUCTP(str);
720
721         offset = 4;
722
723         /* set up string lengths. */
724
725         str->buf_len = create_rpc_blob(str, blob_length);
726         DEBUG(10, ("init_service_description buffer: Allocated a blob of [%d] \n",str->buf_len));
727
728         if ( str && str->buffer && str->buf_len) {
729                 memset(str->buffer,0,str->buf_len);
730                 memcpy(str->buffer, &offset, sizeof(uint32));
731                 bp = &str->buffer[4];
732                 if (service_desc) {
733                         rpcstr_push(bp, service_desc,str->buf_len-4,0);
734                 }
735         }
736 }
737
738 /*******************************************************************
739 ********************************************************************/
740
741 BOOL svcctl_io_q_query_service_status_ex(const char *desc, SVCCTL_Q_QUERY_SERVICE_STATUSEX *q_u, prs_struct *ps, int depth)
742 {
743         if (q_u == NULL)
744                 return False;
745
746         prs_debug(ps, depth, desc, "svcctl_io_q_query_service_status_ex");
747         depth++;
748
749         if(!prs_align(ps))
750                 return False;
751
752         if(!smb_io_pol_hnd("service_pol", &q_u->handle, ps, depth))
753                 return False;
754
755         if(!prs_uint32("info_level", ps, depth, &q_u->info_level))
756                 return False;
757
758         if(!prs_uint32("buffer_size", ps, depth, &q_u->buffer_size))
759                 return False;
760
761         return True;
762
763 }
764
765 /*******************************************************************
766 ********************************************************************/
767
768 BOOL svcctl_io_r_query_service_status_ex(const char *desc, SVCCTL_R_QUERY_SERVICE_STATUSEX *r_u, prs_struct *ps, int depth)
769 {
770         if ( !r_u )
771                 return False;
772
773         prs_debug(ps, depth, desc, "svcctl_io_r_query_service_status_ex");
774                 depth++;
775
776         if (!prs_rpcbuffer("", ps, depth, &r_u->buffer))
777                 return False;
778
779         if(!prs_align(ps))
780                 return False;
781
782         if(!prs_uint32("needed", ps, depth, &r_u->needed))
783                 return False;
784
785         if(!prs_werror("status", ps, depth, &r_u->status))
786                 return False;
787
788         return True;
789 }
790
791 /*******************************************************************
792 ********************************************************************/
793
794 BOOL svcctl_io_r_query_service_config2(const char *desc, SVCCTL_R_QUERY_SERVICE_CONFIG2 *r_u, prs_struct *ps, int depth)
795 {
796         if ( !r_u )
797                 return False;
798
799         prs_debug(ps, depth, desc, "svcctl_io_r_query_service_config2");
800         depth++;
801
802         if(!prs_align(ps))
803                 return False;
804
805         if(!prs_uint32("returned", ps, depth, &r_u->returned))
806                 return False;
807
808         if (r_u->returned > 4) {
809                 if (!prs_uint32("offset", ps, depth, &r_u->offset))
810                         return False;
811                 if(!prs_unistr2(True, "description     ", ps, depth, r_u->description))
812                         return False;
813                 if(!prs_align(ps))
814                         return False;
815         } else {
816                 /* offset does double duty here */
817                 r_u->offset = 0;
818                 if (!prs_uint32("offset", ps, depth, &r_u->offset))
819                         return False;
820         }
821
822         if (!prs_uint32("needed", ps, depth, &r_u->needed))
823                 return False;
824
825         if(!prs_werror("status", ps, depth, &r_u->status))
826                 return False;
827
828         return True;
829 }
830
831