adding some enumerate services code, client and server.
[samba.git] / source / rpc_parse / parse_svc.c
1
2 /* 
3  *  Unix SMB/Netbios implementation.
4  *  Version 1.9.
5  *  RPC Pipe client / server routines
6  *  Copyright (C) Andrew Tridgell              1992-1997,
7  *  Copyright (C) Luke Kenneth Casson Leighton 1996-1997,
8  *  Copyright (C) Paul Ashton                       1997.
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
26 #include "includes.h"
27
28 extern int DEBUGLEVEL;
29
30 /*******************************************************************
31  make_svc_q_open_sc_man
32  ********************************************************************/
33 void make_svc_q_open_sc_man(SVC_Q_OPEN_SC_MAN *q_u,
34                                 char *server, char *database,
35                                 uint32 des_access)  
36 {
37         DEBUG(5,("make_svc_q_open_sc_man\n"));
38
39         make_buf_unistr2(&(q_u->uni_srv_name), &(q_u->ptr_srv_name), server);
40         make_buf_unistr2(&(q_u->uni_db_name ), &(q_u->ptr_db_name), database);
41         q_u->des_access = des_access;
42
43 }
44
45 /*******************************************************************
46 reads or writes a SVC_Q_OPEN_SC_MAN structure.
47 ********************************************************************/
48 void svc_io_q_open_sc_man(char *desc, SVC_Q_OPEN_SC_MAN *q_u, prs_struct *ps, int depth)
49 {
50         if (q_u == NULL) return;
51
52         prs_debug(ps, depth, desc, "svc_io_q_open_sc_man");
53         depth++;
54
55         prs_align(ps);
56
57         prs_uint32("ptr_srv_name", ps, depth, &(q_u->ptr_srv_name));
58         smb_io_unistr2("", &(q_u->uni_srv_name), q_u->ptr_srv_name, ps, depth); 
59         prs_align(ps);
60
61         prs_uint32("ptr_db_name", ps, depth, &(q_u->ptr_db_name));
62         smb_io_unistr2("", &(q_u->uni_db_name), q_u->ptr_db_name, ps, depth); 
63         prs_align(ps);
64
65         prs_uint32("des_access", ps, depth, &(q_u->des_access));
66         prs_align(ps);
67 }
68
69 /*******************************************************************
70  make_svc_r_open_sc_man
71  ********************************************************************/
72 void make_svc_r_open_sc_man(SVC_R_OPEN_SC_MAN *r_u, POLICY_HND *hnd,
73                                 uint32 status)  
74 {
75         DEBUG(5,("make_svc_r_unknown_0: %d\n", __LINE__));
76
77         memcpy(&(r_u->pol), hnd, sizeof(r_u->pol));
78         r_u->status = status;
79 }
80
81 /*******************************************************************
82 reads or writes a structure.
83 ********************************************************************/
84 void svc_io_r_open_sc_man(char *desc,  SVC_R_OPEN_SC_MAN *r_u, prs_struct *ps, int depth)
85 {
86         if (r_u == NULL) return;
87
88         prs_debug(ps, depth, desc, "svc_io_r_open_sc_man");
89         depth++;
90
91         prs_align(ps);
92
93         smb_io_pol_hnd("", &(r_u->pol), ps, depth);
94
95         prs_uint32("status      ", ps, depth, &(r_u->status));
96 }
97
98 /*******************************************************************
99 makes an SVC_Q_ENUM_SVCS_STATUS structure.
100 ********************************************************************/
101 void make_svc_q_enum_svcs_status(SVC_Q_ENUM_SVCS_STATUS *q_c, POLICY_HND *hnd,
102                                 uint32 service_type, uint32 service_state,
103                                 uint32 buf_size, uint32 resume_hnd )
104 {
105         if (q_c == NULL || hnd == NULL) return;
106
107         DEBUG(5,("make_svc_q_enum_svcs_status\n"));
108
109         memcpy(&(q_c->pol), hnd, sizeof(q_c->pol));
110         q_c->service_type = service_type;
111         q_c->service_state = service_state;
112         q_c->buf_size = buf_size;
113         make_enum_hnd(&q_c->resume_hnd, resume_hnd);
114 }
115
116 /*******************************************************************
117 reads or writes a structure.
118 ********************************************************************/
119 void svc_io_q_enum_svcs_status(char *desc,  SVC_Q_ENUM_SVCS_STATUS *q_u, prs_struct *ps, int depth)
120 {
121         if (q_u == NULL) return;
122
123         prs_debug(ps, depth, desc, "svc_io_q_enum_svcs_status");
124         depth++;
125
126         prs_align(ps);
127
128         smb_io_pol_hnd("", &(q_u->pol), ps, depth); 
129         prs_align(ps);
130
131         prs_uint32("service_type ", ps, depth, &(q_u->service_type ));
132         prs_uint32("service_state", ps, depth, &(q_u->service_state));
133         prs_uint32("buf_size     ", ps, depth, &(q_u->buf_size     ));
134         smb_io_enum_hnd("resume_hnd", &(q_u->resume_hnd), ps, depth); 
135 }
136
137 /*******************************************************************
138 makes an SVC_R_ENUM_SVCS_STATUS structure.
139 ********************************************************************/
140 void make_svc_r_enum_svcs_status(SVC_R_ENUM_SVCS_STATUS *r_c, 
141                                 ENUM_SRVC_STATUS *svcs, uint32 more_buf_size,
142                                 uint32 num_svcs, uint32 resume_hnd,
143                                 uint32 dos_status)
144 {
145         if (r_c == NULL) return;
146
147         DEBUG(5,("make_svc_r_enum_svcs_status\n"));
148
149         r_c->svcs          = svcs;
150         r_c->more_buf_size = more_buf_size;
151         r_c->num_svcs      = num_svcs;
152         make_enum_hnd(&r_c->resume_hnd, resume_hnd);
153         r_c->dos_status = dos_status;
154 }
155
156 /*******************************************************************
157 reads or writes a SVC_R_ENUM_SVCS_STATUS structure.
158
159 this is another wierd structure.  WHY oh WHY can the microsoft teams
160 not COMMUNICATE and get some CONSISTENCY TO THEIR DATA STRUCTURES!
161 ARGH!
162
163 ********************************************************************/
164 void svc_io_r_enum_svcs_status(char *desc, SVC_R_ENUM_SVCS_STATUS *svc, prs_struct *ps, int depth)
165 {
166         int i;
167         if (svc == NULL) return;
168
169         prs_debug(ps, depth, desc, "svc_io_r_enum_svcs_status");
170         depth++;
171
172         prs_align(ps);
173         
174         /*
175          * format is actually as laid out in SVC_R_ENUM_SVCS_STATUS.
176          * the reason for all the jumping about, which is horrible
177          * and can be avoided, is due to the use of offsets instead
178          * of pointers.
179          *
180          * if i ever find out that these offsets are in fact non-zero
181          * tokens just like pointer-tokens, i am going to go MAD.
182          */
183
184         if (ps->io)
185         {
186                 /* reading */
187
188                 uint32 buf_offset;
189                 uint32 new_offset;
190
191                 prs_uint32("buf_size", ps, depth, &(svc->buf_size));
192
193                 buf_offset = ps->offset;
194                 ps->offset = buf_offset + svc->buf_size;
195
196                 prs_uint32("more_buf_size", ps, depth, &(svc->more_buf_size));
197                 prs_uint32("num_svcs", ps, depth, &(svc->num_svcs));
198                 smb_io_enum_hnd("resume_hnd", &(svc->resume_hnd), ps, depth); 
199                 prs_uint32("dos_status", ps, depth, &(svc->dos_status));
200
201                 new_offset = ps->offset;
202                 ps->offset = buf_offset;
203
204                 svc->svcs = Realloc(NULL, svc->num_svcs * sizeof(ENUM_SRVC_STATUS));
205
206                 if (svc->svcs == NULL)
207                 {
208                         DEBUG(0,("svc_io_r_enum_svcs_status: Realloc failed\n"));
209                         ps->offset = 0x7fffffff;
210                         return;
211                 }
212
213                 bzero(svc->svcs, svc->num_svcs * sizeof(ENUM_SRVC_STATUS));
214
215                 for (i = 0; i < svc->num_svcs; i++)
216                 {
217                         fstring name;
218                         uint32 old_offset;
219                         uint32 srvc_offset;
220                         uint32 disp_offset;
221
222                         prs_uint32("srvc_offset", ps, depth, &srvc_offset);
223                         prs_uint32("disp_offset", ps, depth, &disp_offset);
224                         svc_io_svc_status("status", &svc->svcs[i].status, ps, depth); 
225
226                         old_offset = ps->offset;
227
228                         ps->offset = buf_offset + srvc_offset;
229                         slprintf(name, sizeof(name)-1, "srvc[%02d]", i);
230                         smb_io_unistr(name, &svc->svcs[i].uni_srvc_name, ps, depth);
231
232                         ps->offset = buf_offset + disp_offset;
233                         slprintf(name, sizeof(name)-1, "disp[%02d]", i);
234                         smb_io_unistr(name, &svc->svcs[i].uni_disp_name, ps, depth);
235
236                         ps->offset = old_offset;
237                 }
238
239                 ps->offset = new_offset;
240         }
241         else
242         {
243                 /* writing */
244
245                 uint32 buf_offset;
246                 uint32 old_buf_offset;
247                 uint32 srvc_offset = 9 * sizeof(uint32) * svc->num_svcs;
248
249                 prs_uint32_pre("buf_size", ps, depth, &svc->buf_size, &buf_offset);
250                 old_buf_offset = ps->offset;
251
252                 srvc_offset += old_buf_offset;
253
254                 if (svc->svcs == NULL)
255                 {
256                         return;
257                 }
258
259                 for (i = 0; i < svc->num_svcs; i++)
260                 {
261                         fstring name;
262                         uint32 old_offset;
263
264                         /*
265                          * store unicode string offset and unicode string
266                          */
267
268                         srvc_offset -= old_buf_offset;
269                         prs_uint32("srvc_offset", ps, depth, &srvc_offset);
270                         srvc_offset += old_buf_offset;
271
272                         slprintf(name, sizeof(name)-1, "srvc[%02d]", i);
273
274                         old_offset = ps->offset;
275                         ps->offset = srvc_offset;
276                         smb_io_unistr(name, &svc->svcs[i].uni_srvc_name, ps, depth);
277                         srvc_offset = ps->offset;
278                         ps->offset = old_offset;
279
280                         /*
281                          * store unicode string offset and unicode string
282                          */
283
284                         srvc_offset -= old_buf_offset;
285                         prs_uint32("disp_offset", ps, depth, &srvc_offset);
286                         srvc_offset += old_buf_offset;
287
288                         slprintf(name, sizeof(name)-1, "disp[%02d]", i);
289
290                         old_offset = ps->offset;
291                         ps->offset = srvc_offset;
292                         smb_io_unistr(name, &svc->svcs[i].uni_disp_name, ps, depth);
293                         srvc_offset = ps->offset;
294                         ps->offset = old_offset;
295
296                         /*
297                          * store status info
298                          */
299
300                         svc_io_svc_status("status", &svc->svcs[i].status, ps, depth); 
301                 }
302
303                 prs_uint32_post("buf_size", ps, depth, &svc->buf_size, buf_offset, srvc_offset - buf_offset - sizeof(uint32));
304
305                 ps->offset = srvc_offset;
306
307                 prs_uint32("more_buf_size", ps, depth, &(svc->more_buf_size));
308                 prs_uint32("num_svcs", ps, depth, &(svc->num_svcs));
309                 smb_io_enum_hnd("resume_hnd", &(svc->resume_hnd), ps, depth); 
310                 prs_uint32("dos_status", ps, depth, &(svc->dos_status));
311         }
312 }
313
314 /*******************************************************************
315 reads or writes a structure.
316 ********************************************************************/
317 void svc_io_svc_status(char *desc,  SVC_STATUS *svc, prs_struct *ps, int depth)
318 {
319         if (svc == NULL) return;
320
321         prs_debug(ps, depth, desc, "svc_io_svc_status");
322         depth++;
323
324         prs_align(ps);
325
326         prs_uint32("svc_type", ps, depth, &(svc->svc_type));
327         prs_uint32("current_state", ps, depth, &(svc->current_state));
328         prs_uint32("controls_accepted", ps, depth, &(svc->controls_accepted));
329         prs_uint32("win32_exit_code", ps, depth, &(svc->win32_exit_code));
330         prs_uint32("svc_specific_exit_code", ps, depth, &(svc->svc_specific_exit_code));
331         prs_uint32("check_point", ps, depth, &(svc->check_point));
332         prs_uint32("wait_hint", ps, depth, &(svc->wait_hint));
333 }
334
335 /*******************************************************************
336 makes an SVC_Q_CLOSE structure.
337 ********************************************************************/
338 void make_svc_q_close(SVC_Q_CLOSE *q_c, POLICY_HND *hnd)
339 {
340         if (q_c == NULL || hnd == NULL) return;
341
342         DEBUG(5,("make_svc_q_close\n"));
343
344         memcpy(&(q_c->pol), hnd, sizeof(q_c->pol));
345 }
346
347 /*******************************************************************
348 reads or writes a structure.
349 ********************************************************************/
350 void svc_io_q_close(char *desc,  SVC_Q_CLOSE *q_u, prs_struct *ps, int depth)
351 {
352         if (q_u == NULL) return;
353
354         prs_debug(ps, depth, desc, "svc_io_q_close");
355         depth++;
356
357         prs_align(ps);
358
359         smb_io_pol_hnd("", &(q_u->pol), ps, depth); 
360         prs_align(ps);
361 }
362
363 /*******************************************************************
364 reads or writes a structure.
365 ********************************************************************/
366 void svc_io_r_close(char *desc,  SVC_R_CLOSE *r_u, prs_struct *ps, int depth)
367 {
368         if (r_u == NULL) return;
369
370         prs_debug(ps, depth, desc, "svc_io_r_close");
371         depth++;
372
373         prs_align(ps);
374
375         smb_io_pol_hnd("", &(r_u->pol), ps, depth); 
376         prs_align(ps);
377
378         prs_uint32("status", ps, depth, &(r_u->status));
379 }
380