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 #ifdef NTDOMAIN
31 
32 #ifdef USE_ARCFOUR
33 void arcfour(unsigned char data[16], unsigned char data_out[16], unsigned char data_in[16]);
34 #endif
35 
36 /*******************************************************************
37 reads or writes a UTIME type.
38 ********************************************************************/
smb_io_utime(BOOL io,UTIME * t,char * q,char * base,int align,int depth)39 char* smb_io_utime(BOOL io, UTIME *t, char *q, char *base, int align, int depth)
40 {
41 	if (t == NULL) return NULL;
42 
43 	DEBUG(5,("%s%04x smb_io_utime\n",  tab_depth(depth), PTR_DIFF(q, base)));
44 	depth++;
45 
46 	q = align_offset(q, base, align);
47 
48 	DBG_RW_IVAL ("time", depth, base, io, q, t->time); q += 4;
49 
50 	return q;
51 }
52 
53 /*******************************************************************
54 reads or writes an NTTIME structure.
55 ********************************************************************/
smb_io_time(BOOL io,NTTIME * nttime,char * q,char * base,int align,int depth)56 char* smb_io_time(BOOL io, NTTIME *nttime, char *q, char *base, int align, int depth)
57 {
58 	if (nttime == NULL) return NULL;
59 
60 	DEBUG(5,("%s%04x smb_io_time\n",  tab_depth(depth), PTR_DIFF(q, base)));
61 	depth++;
62 
63 	q = align_offset(q, base, align);
64 
65 	DBG_RW_IVAL("low ", depth, base, io, q, nttime->low ); q += 4; /* low part */
66 	DBG_RW_IVAL("high", depth, base, io, q, nttime->high); q += 4; /* high part */
67 
68 	return q;
69 }
70 
71 /*******************************************************************
72 creates a DOM_SID structure.
73 
74 BIG NOTE: this function only does SIDS where the identauth is not >= 2^32
75 identauth >= 2^32 can be detected because it will be specified in hex
76 
77 ********************************************************************/
make_dom_sid(DOM_SID * sid,char * domsid)78 void make_dom_sid(DOM_SID *sid, char *domsid)
79 {
80 	int identauth;
81 	char *p;
82 
83 	if (sid == NULL) return;
84 
85 	if (domsid == NULL)
86 	{
87 		DEBUG(4,("netlogon domain SID: none\n"));
88 		sid->sid_rev_num = 0;
89 		sid->num_auths = 0;
90 		return;
91 	}
92 
93 	DEBUG(4,("netlogon domain SID: %s\n", domsid));
94 
95 	/* assume, but should check, that domsid starts "S-" */
96 	p = strtok(domsid+2,"-");
97 	sid->sid_rev_num = atoi(p);
98 
99 	/* identauth in decimal should be <  2^32 */
100 	/* identauth in hex     should be >= 2^32 */
101 	identauth = atoi(strtok(0,"-"));
102 
103 	DEBUG(4,("netlogon rev %d\n", sid->sid_rev_num));
104 	DEBUG(4,("netlogon %s ia %d\n", p, identauth));
105 
106 	sid->id_auth[0] = 0;
107 	sid->id_auth[1] = 0;
108 	sid->id_auth[2] = (identauth & 0xff000000) >> 24;
109 	sid->id_auth[3] = (identauth & 0x00ff0000) >> 16;
110 	sid->id_auth[4] = (identauth & 0x0000ff00) >> 8;
111 	sid->id_auth[5] = (identauth & 0x000000ff);
112 
113 	sid->num_auths = 0;
114 
115 	while ((p = strtok(0, "-")) != NULL)
116 	{
117 		sid->sub_auths[sid->num_auths++] = atoi(p);
118 	}
119 }
120 
121 /*******************************************************************
122 reads or writes a DOM_SID structure.
123 ********************************************************************/
smb_io_dom_sid(BOOL io,DOM_SID * sid,char * q,char * base,int align,int depth)124 char* smb_io_dom_sid(BOOL io, DOM_SID *sid, char *q, char *base, int align, int depth)
125 {
126 	int i;
127 
128 	if (sid == NULL) return NULL;
129 
130 	DEBUG(5,("%s%04x smb_io_dom_sid\n",  tab_depth(depth), PTR_DIFF(q, base)));
131 	depth++;
132 
133 	q = align_offset(q, base, align);
134 
135 	DBG_RW_IVAL("num_auths  ", depth, base, io, q, sid->num_auths); q += 4;
136 	DBG_RW_CVAL("sid_rev_num", depth, base, io, q, sid->sid_rev_num); q++;
137 	DBG_RW_CVAL("num_auths  ", depth, base, io, q, sid->num_auths); q++;
138 
139 	for (i = 0; i < 6; i++)
140 	{
141 		fstring tmp;
142 		slprintf(tmp, sizeof(tmp)-1,"id_auth[%d] ", i);
143 		DBG_RW_CVAL(tmp, depth, base, io, q, sid->id_auth[i]); q++;
144 	}
145 
146 	/* oops! XXXX should really issue a warning here... */
147 	if (sid->num_auths > MAXSUBAUTHS) sid->num_auths = MAXSUBAUTHS;
148 
149 	DBG_RW_PIVAL(False, "sub_auths ", depth, base, io, q, sid->sub_auths, sid->num_auths); q += sid->num_auths * 4;
150 
151 	return q;
152 }
153 
154 /*******************************************************************
155 creates a UNIHDR structure.
156 ********************************************************************/
make_uni_hdr(UNIHDR * hdr,int max_len,int len,uint16 terminate)157 void make_uni_hdr(UNIHDR *hdr, int max_len, int len, uint16 terminate)
158 {
159 	hdr->uni_max_len = 2 * max_len;
160 	hdr->uni_str_len = 2 * len;
161 	hdr->undoc       = terminate;
162 }
163 
164 /*******************************************************************
165 reads or writes a UNIHDR structure.
166 ********************************************************************/
smb_io_unihdr(BOOL io,UNIHDR * hdr,char * q,char * base,int align,int depth)167 char* smb_io_unihdr(BOOL io, UNIHDR *hdr, char *q, char *base, int align, int depth)
168 {
169 	if (hdr == NULL) return NULL;
170 
171 	DEBUG(5,("%s%04x smb_io_unihdr\n",  tab_depth(depth), PTR_DIFF(q, base)));
172 	depth++;
173 
174 	q = align_offset(q, base, align);
175 
176 	DBG_RW_SVAL("uni_str_len", depth, base, io, q, hdr->uni_str_len); q += 2;
177 	DBG_RW_SVAL("uni_max_len", depth, base, io, q, hdr->uni_max_len); q += 2;
178 	DBG_RW_IVAL("undoc      ", depth, base, io, q, hdr->undoc      ); q += 4;
179 
180 	/* oops! XXXX maybe issue a warning that this is happening... */
181 	if (hdr->uni_max_len > MAX_UNISTRLEN) hdr->uni_max_len = MAX_UNISTRLEN;
182 	if (hdr->uni_str_len > MAX_UNISTRLEN) hdr->uni_str_len = MAX_UNISTRLEN;
183 
184 	return q;
185 }
186 
187 /*******************************************************************
188 creates a UNIHDR2 structure.
189 ********************************************************************/
make_uni_hdr2(UNIHDR2 * hdr,int max_len,int len,uint16 terminate)190 void make_uni_hdr2(UNIHDR2 *hdr, int max_len, int len, uint16 terminate)
191 {
192 	make_uni_hdr(&(hdr->unihdr), max_len, len, terminate);
193 	hdr->undoc_buffer = len > 0 ? 1 : 0;
194 }
195 
196 /*******************************************************************
197 reads or writes a UNIHDR2 structure.
198 ********************************************************************/
smb_io_unihdr2(BOOL io,UNIHDR2 * hdr2,char * q,char * base,int align,int depth)199 char* smb_io_unihdr2(BOOL io, UNIHDR2 *hdr2, char *q, char *base, int align, int depth)
200 {
201 	if (hdr2 == NULL) return NULL;
202 
203 	DEBUG(5,("%s%04x smb_io_unihdr2\n",  tab_depth(depth), PTR_DIFF(q, base)));
204 	depth++;
205 
206 	q = align_offset(q, base, align);
207 
208 	q = smb_io_unihdr(io, &(hdr2->unihdr), q, base, align, depth);
209 	DBG_RW_IVAL("undoc_buffer", depth, base, io, q, hdr2->undoc_buffer); q += 4;
210 
211 	return q;
212 }
213 
214 /*******************************************************************
215 creates a UNISTR structure.
216 ********************************************************************/
make_unistr(UNISTR * str,char * buf)217 void make_unistr(UNISTR *str, char *buf)
218 {
219 	/* store the string (null-terminated copy) */
220 	struni2(str->buffer, buf);
221 }
222 
223 /*******************************************************************
224 reads or writes a UNISTR structure.
225 XXXX NOTE: UNISTR structures NEED to be null-terminated.
226 ********************************************************************/
smb_io_unistr(BOOL io,UNISTR * uni,char * q,char * base,int align,int depth)227 char* smb_io_unistr(BOOL io, UNISTR *uni, char *q, char *base, int align, int depth)
228 {
229 	int i = 0;
230 
231 	if (uni == NULL) return NULL;
232 
233 	DEBUG(5,("%s%04x smb_io_unistr\n",  tab_depth(depth), PTR_DIFF(q, base)));
234 	depth++;
235 
236 	q = align_offset(q, base, align);
237 
238 	do
239 	{
240 		RW_SVAL(io, q, uni->buffer[i], 0); q += 2;
241 		i++;
242 
243 	} while ((i < sizeof(uni->buffer) / sizeof(uni->buffer[0])) &&
244 		     (uni->buffer[i] != 0));
245 
246 	return q;
247 }
248 
249 /*******************************************************************
250 creates a UNISTR2 structure.
251 ********************************************************************/
make_unistr2(UNISTR2 * str,char * buf,int len)252 void make_unistr2(UNISTR2 *str, char *buf, int len)
253 {
254 	/* set up string lengths. add one if string is not null-terminated */
255 	str->uni_max_len = len;
256 	str->undoc       = 0;
257 	str->uni_str_len = len;
258 
259 	/* store the string (null-terminated copy) */
260 	struni2(str->buffer, buf);
261 }
262 
263 /*******************************************************************
264 reads or writes a UNISTR2 structure.
265 XXXX NOTE: UNISTR2 structures need NOT be null-terminated.
266      the uni_str_len member tells you how long the string is;
267      the uni_max_len member tells you how large the buffer is.
268 ********************************************************************/
smb_io_unistr2(BOOL io,UNISTR2 * uni2,char * q,char * base,int align,int depth)269 char* smb_io_unistr2(BOOL io, UNISTR2 *uni2, char *q, char *base, int align, int depth)
270 {
271 	if (uni2 == NULL) return NULL;
272 
273 	DEBUG(5,("%s%04x smb_io_unistr2\n",  tab_depth(depth), PTR_DIFF(q, base)));
274 	depth++;
275 
276 	q = align_offset(q, base, align);
277 
278 	/* should be value 0, so enforce it. */
279 	uni2->undoc = 0;
280 
281 	DBG_RW_IVAL("uni_max_len", depth, base, io, q, uni2->uni_max_len); q += 4;
282 	DBG_RW_IVAL("undoc      ", depth, base, io, q, uni2->undoc      ); q += 4;
283 	DBG_RW_IVAL("uni_str_len", depth, base, io, q, uni2->uni_str_len); q += 4;
284 
285 	/* oops! XXXX maybe issue a warning that this is happening... */
286 	if (uni2->uni_max_len > MAX_UNISTRLEN) uni2->uni_max_len = MAX_UNISTRLEN;
287 	if (uni2->uni_str_len > MAX_UNISTRLEN) uni2->uni_str_len = MAX_UNISTRLEN;
288 
289 	/* buffer advanced by indicated length of string
290        NOT by searching for null-termination */
291 	DBG_RW_PSVAL(True, "buffer     ", depth, base, io, q, uni2->buffer, uni2->uni_max_len); q += uni2->uni_str_len * 2;
292 
293 	return q;
294 }
295 
296 /*******************************************************************
297 creates a DOM_SID2 structure.
298 ********************************************************************/
make_dom_sid2(DOM_SID2 * sid2,char * sid_str)299 void make_dom_sid2(DOM_SID2 *sid2, char *sid_str)
300 {
301 	int len_sid_str = strlen(sid_str);
302 
303 	sid2->type = 0x5;
304 	sid2->undoc = 0;
305 	make_uni_hdr2(&(sid2->hdr), len_sid_str, len_sid_str, 0);
306 	make_unistr  (&(sid2->str), sid_str);
307 }
308 
309 /*******************************************************************
310 reads or writes a DOM_SID2 structure.
311 ********************************************************************/
smb_io_dom_sid2(BOOL io,DOM_SID2 * sid2,char * q,char * base,int align,int depth)312 char* smb_io_dom_sid2(BOOL io, DOM_SID2 *sid2, char *q, char *base, int align, int depth)
313 {
314 	if (sid2 == NULL) return NULL;
315 
316 	DEBUG(5,("%s%04x smb_io_dom_sid2\n",  tab_depth(depth), PTR_DIFF(q, base)));
317 	depth++;
318 
319 	q = align_offset(q, base, align);
320 
321 	/* should be value 5, so enforce it */
322 	sid2->type = 5;
323 
324 	/* should be value 0, so enforce it */
325 	sid2->undoc = 0;
326 
327 	DBG_RW_IVAL("type ", depth, base, io, q, sid2->type ); q += 4;
328 	DBG_RW_IVAL("undoc", depth, base, io, q, sid2->undoc); q += 4;
329 
330 	q = smb_io_unihdr2(io, &(sid2->hdr), q, base, align, depth);
331 	q = smb_io_unistr (io, &(sid2->str), q, base, align, depth);
332 
333 	return q;
334 }
335 
336 /*******************************************************************
337 creates a DOM_RID2 structure.
338 ********************************************************************/
make_dom_rid2(DOM_RID2 * rid2,uint32 rid)339 void make_dom_rid2(DOM_RID2 *rid2, uint32 rid)
340 {
341 	rid2->type    = 0x5;
342 	rid2->undoc   = 0x5;
343 	rid2->rid     = rid;
344 	rid2->rid_idx = 0;
345 }
346 
347 /*******************************************************************
348 reads or writes a DOM_RID2 structure.
349 ********************************************************************/
smb_io_dom_rid2(BOOL io,DOM_RID2 * rid2,char * q,char * base,int align,int depth)350 char* smb_io_dom_rid2(BOOL io, DOM_RID2 *rid2, char *q, char *base, int align, int depth)
351 {
352 	if (rid2 == NULL) return NULL;
353 
354 	DEBUG(5,("%s%04x smb_io_dom_rid2\n",  tab_depth(depth), PTR_DIFF(q, base)));
355 	depth++;
356 
357 	q = align_offset(q, base, align);
358 
359 	/* should be value 5, so enforce it */
360 	rid2->type = 5;
361 
362 	/* should be value 5, so enforce it */
363 	rid2->undoc = 5;
364 
365 	DBG_RW_IVAL("type   ", depth, base, io, q, rid2->type); q += 4;
366 	DBG_RW_IVAL("undoc  ", depth, base, io, q, rid2->undoc   ); q += 4;
367 	DBG_RW_IVAL("rid    ", depth, base, io, q, rid2->rid     ); q += 4;
368 	DBG_RW_IVAL("rid_idx", depth, base, io, q, rid2->rid_idx ); q += 4;
369 
370 	return q;
371 }
372 
373 /*******************************************************************
374 creates a DOM_RID3 structure.
375 ********************************************************************/
make_dom_rid3(DOM_RID3 * rid3,uint32 rid)376 void make_dom_rid3(DOM_RID3 *rid3, uint32 rid)
377 {
378 	rid3->rid      = rid;
379 	rid3->type1    = 0x1;
380 	rid3->ptr_type = 0x1; /* non-zero, basically. */
381 	rid3->type2    = 0x1;
382 }
383 
384 /*******************************************************************
385 reads or writes a DOM_RID3 structure.
386 ********************************************************************/
smb_io_dom_rid3(BOOL io,DOM_RID3 * rid3,char * q,char * base,int align,int depth)387 char* smb_io_dom_rid3(BOOL io, DOM_RID3 *rid3, char *q, char *base, int align, int depth)
388 {
389 	if (rid3 == NULL) return NULL;
390 
391 	DEBUG(5,("%s%04x smb_io_dom_rid3\n",  tab_depth(depth), PTR_DIFF(q, base)));
392 	depth++;
393 
394 	q = align_offset(q, base, align);
395 
396 	DBG_RW_IVAL("rid     ", depth, base, io, q, rid3->rid     ); q += 4;
397 	DBG_RW_IVAL("type1   ", depth, base, io, q, rid3->type1   ); q += 4;
398 	DBG_RW_IVAL("ptr_type", depth, base, io, q, rid3->ptr_type); q += 4;
399 	DBG_RW_IVAL("type2   ", depth, base, io, q, rid3->type2   ); q += 4;
400 
401 	return q;
402 }
403 
404 /*******************************************************************
405 makes a DOM_CLNT_SRV structure.
406 ********************************************************************/
make_clnt_srv(DOM_CLNT_SRV * log,char * logon_srv,char * comp_name)407 void make_clnt_srv(DOM_CLNT_SRV *log, char *logon_srv, char *comp_name)
408 {
409 	if (log == NULL) return;
410 
411 	DEBUG(5,("make_clnt_srv: %d\n", __LINE__));
412 
413 	if (logon_srv != NULL)
414 	{
415 		log->undoc_buffer = 1;
416 		make_unistr2(&(log->uni_logon_srv), logon_srv, strlen(logon_srv));
417 	}
418 	else
419 	{
420 		log->undoc_buffer = 1;
421 	}
422 
423 	if (comp_name != NULL)
424 	{
425 		log->undoc_buffer2 = 1;
426 		make_unistr2(&(log->uni_comp_name), comp_name, strlen(comp_name));
427 	}
428 	else
429 	{
430 		log->undoc_buffer2 = 1;
431 	}
432 }
433 
434 /*******************************************************************
435 reads or writes a DOM_CLNT_SRV structure.
436 ********************************************************************/
smb_io_clnt_srv(BOOL io,DOM_CLNT_SRV * log,char * q,char * base,int align,int depth)437 char* smb_io_clnt_srv(BOOL io, DOM_CLNT_SRV *log, char *q, char *base, int align, int depth)
438 {
439 	if (log == NULL) return NULL;
440 
441 	DEBUG(5,("%s%04x smb_io_clnt_srv\n",  tab_depth(depth), PTR_DIFF(q, base)));
442 	depth++;
443 
444 	q = align_offset(q, base, align);
445 
446 	DBG_RW_IVAL("undoc_buffer ", depth, base, io, q, log->undoc_buffer ); q += 4;
447 	q = smb_io_unistr2(io, &(log->uni_logon_srv), q, base, align, depth);
448 
449 	DBG_RW_IVAL("undoc_buffer2", depth, base, io, q, log->undoc_buffer2); q += 4;
450 	q = smb_io_unistr2(io, &(log->uni_comp_name), q, base, align, depth);
451 
452 	return q;
453 }
454 
455 /*******************************************************************
456 makes a DOM_LOG_INFO structure.
457 ********************************************************************/
make_log_info(DOM_LOG_INFO * log,char * logon_srv,char * acct_name,uint16 sec_chan,char * comp_name)458 void make_log_info(DOM_LOG_INFO *log, char *logon_srv, char *acct_name,
459 		uint16 sec_chan, char *comp_name)
460 {
461 	if (log == NULL) return;
462 
463 	DEBUG(5,("make_log_info %d\n", __LINE__));
464 
465 	log->undoc_buffer = 1;
466 
467 	make_unistr2(&(log->uni_logon_srv), logon_srv, strlen(logon_srv));
468 	make_unistr2(&(log->uni_acct_name), acct_name, strlen(acct_name));
469 
470 	log->sec_chan = sec_chan;
471 
472 	make_unistr2(&(log->uni_comp_name), comp_name, strlen(comp_name));
473 }
474 
475 /*******************************************************************
476 reads or writes a DOM_LOG_INFO structure.
477 ********************************************************************/
smb_io_log_info(BOOL io,DOM_LOG_INFO * log,char * q,char * base,int align,int depth)478 char* smb_io_log_info(BOOL io, DOM_LOG_INFO *log, char *q, char *base, int align, int depth)
479 {
480 	if (log == NULL) return NULL;
481 
482 	DEBUG(5,("%s%04x smb_io_log_info\n",  tab_depth(depth), PTR_DIFF(q, base)));
483 	depth++;
484 
485 	q = align_offset(q, base, align);
486 
487 	DBG_RW_IVAL("undoc_buffer", depth, base, io, q, log->undoc_buffer); q += 4;
488 
489 	q = smb_io_unistr2(io, &(log->uni_logon_srv), q, base, align, depth);
490 	q = smb_io_unistr2(io, &(log->uni_acct_name), q, base, align, depth);
491 
492 	DBG_RW_SVAL("sec_chan", depth, base, io, q, log->sec_chan); q += 2;
493 
494 	q = smb_io_unistr2(io, &(log->uni_comp_name), q, base, align, depth);
495 
496 	return q;
497 }
498 
499 /*******************************************************************
500 reads or writes a DOM_CHAL structure.
501 ********************************************************************/
smb_io_chal(BOOL io,DOM_CHAL * chal,char * q,char * base,int align,int depth)502 char* smb_io_chal(BOOL io, DOM_CHAL *chal, char *q, char *base, int align, int depth)
503 {
504 	if (chal == NULL) return NULL;
505 
506 	DEBUG(5,("%s%04x smb_io_chal\n",  tab_depth(depth), PTR_DIFF(q, base)));
507 	depth++;
508 
509 	q = align_offset(q, base, align);
510 
511 	DBG_RW_PCVAL(False, "data", depth, base, io, q, chal->data, 8); q += 8;
512 	return q;
513 }
514 
515 /*******************************************************************
516 reads or writes a DOM_CRED structure.
517 ********************************************************************/
smb_io_cred(BOOL io,DOM_CRED * cred,char * q,char * base,int align,int depth)518 char* smb_io_cred(BOOL io, DOM_CRED *cred, char *q, char *base, int align, int depth)
519 {
520 	if (cred == NULL) return NULL;
521 
522 	DEBUG(5,("%s%04x smb_io_cred\n",  tab_depth(depth), PTR_DIFF(q, base)));
523 	depth++;
524 
525 	q = align_offset(q, base, align);
526 
527 	q = smb_io_chal (io, &(cred->challenge), q, base, align, depth);
528 	q = smb_io_utime(io, &(cred->timestamp), q, base, align, depth);
529 
530 	return q;
531 }
532 
533 /*******************************************************************
534 makes a DOM_CLNT_INFO2 structure.
535 ********************************************************************/
make_clnt_info2(DOM_CLNT_INFO2 * clnt,char * logon_srv,char * comp_name,DOM_CRED * clnt_cred)536 void make_clnt_info2(DOM_CLNT_INFO2 *clnt,
537 				char *logon_srv, char *comp_name,
538 				DOM_CRED *clnt_cred)
539 {
540 	if (clnt == NULL) return;
541 
542 	DEBUG(5,("make_clnt_info: %d\n", __LINE__));
543 
544 	make_clnt_srv(&(clnt->login), logon_srv, comp_name);
545 
546 	if (clnt_cred != NULL)
547 	{
548 		clnt->ptr_cred = 1;
549 		memcpy(&(clnt->cred), clnt_cred, sizeof(clnt->cred));
550 	}
551 	else
552 	{
553 		clnt->ptr_cred = 0;
554 	}
555 }
556 
557 /*******************************************************************
558 reads or writes a DOM_CLNT_INFO2 structure.
559 ********************************************************************/
smb_io_clnt_info2(BOOL io,DOM_CLNT_INFO2 * clnt,char * q,char * base,int align,int depth)560 char* smb_io_clnt_info2(BOOL io, DOM_CLNT_INFO2 *clnt, char *q, char *base, int align, int depth)
561 {
562 	if (clnt == NULL) return NULL;
563 
564 	DEBUG(5,("%s%04x smb_io_clnt_info2\n",  tab_depth(depth), PTR_DIFF(q, base)));
565 	depth++;
566 
567 	q = align_offset(q, base, align);
568 
569 	q = smb_io_clnt_srv(io, &(clnt->login), q, base, align, depth);
570 
571 	q = align_offset(q, base, align);
572 
573 	DBG_RW_IVAL("ptr_cred", depth, base, io, q, clnt->ptr_cred); q += 4;
574 	q = smb_io_cred    (io, &(clnt->cred ), q, base, align, depth);
575 
576 	return q;
577 }
578 
579 /*******************************************************************
580 makes a DOM_CLNT_INFO structure.
581 ********************************************************************/
make_clnt_info(DOM_CLNT_INFO * clnt,char * logon_srv,char * acct_name,uint16 sec_chan,char * comp_name,DOM_CRED * cred)582 char* make_clnt_info(DOM_CLNT_INFO *clnt,
583 		char *logon_srv, char *acct_name,
584 		uint16 sec_chan, char *comp_name,
585 				DOM_CRED *cred)
586 {
587 	if (clnt == NULL || cred == NULL) return NULL;
588 
589 	DEBUG(5,("make_clnt_info\n"));
590 
591 	make_log_info(&(clnt->login), logon_srv, acct_name, sec_chan, comp_name);
592 	memcpy(&(clnt->cred), cred, sizeof(clnt->cred));
593 }
594 
595 /*******************************************************************
596 reads or writes a DOM_CLNT_INFO structure.
597 ********************************************************************/
smb_io_clnt_info(BOOL io,DOM_CLNT_INFO * clnt,char * q,char * base,int align,int depth)598 char* smb_io_clnt_info(BOOL io, DOM_CLNT_INFO *clnt, char *q, char *base, int align, int depth)
599 {
600 	if (clnt == NULL) return NULL;
601 
602 	DEBUG(5,("%s%04x smb_io_clnt_info\n",  tab_depth(depth), PTR_DIFF(q, base)));
603 	depth++;
604 
605 	q = align_offset(q, base, align);
606 
607 	q = smb_io_log_info(io, &(clnt->login), q, base, align, depth);
608 	q = smb_io_cred    (io, &(clnt->cred ), q, base, align, depth);
609 
610 	return q;
611 }
612 
613 /*******************************************************************
614 makes a DOM_LOGON_ID structure.
615 ********************************************************************/
make_logon_id(DOM_LOGON_ID * log,uint32 log_id_low,uint32 log_id_high)616 void make_logon_id(DOM_LOGON_ID *log, uint32 log_id_low, uint32 log_id_high)
617 {
618 	if (log == NULL) return;
619 
620 	DEBUG(5,("make_logon_id: %d\n", __LINE__));
621 
622 	log->low  = log_id_low;
623 	log->high = log_id_high;
624 }
625 
626 /*******************************************************************
627 reads or writes a DOM_LOGON_ID structure.
628 ********************************************************************/
smb_io_logon_id(BOOL io,DOM_LOGON_ID * log,char * q,char * base,int align,int depth)629 char* smb_io_logon_id(BOOL io, DOM_LOGON_ID *log, char *q, char *base, int align, int depth)
630 {
631 	if (log == NULL) return NULL;
632 
633 	DEBUG(5,("%s%04x smb_io_logon_id\n",  tab_depth(depth), PTR_DIFF(q, base)));
634 	depth++;
635 
636 	q = align_offset(q, base, align);
637 
638 	DBG_RW_IVAL("low ", depth, base, io, q, log->low ); q += 4;
639 	DBG_RW_IVAL("high", depth, base, io, q, log->high); q += 4;
640 
641 	return q;
642 }
643 
644 /*******************************************************************
645 makes an ARC4_OWF structure.
646 ********************************************************************/
make_arc4_owf(ARC4_OWF * hash,char data[16])647 void make_arc4_owf(ARC4_OWF *hash, char data[16])
648 {
649 	if (hash == NULL) return;
650 
651 	DEBUG(5,("make_arc4_owf: %d\n", __LINE__));
652 
653 	if (data != NULL)
654 	{
655 		memcpy(hash->data, data, sizeof(hash->data));
656 	}
657 	else
658 	{
659 		bzero(hash->data, sizeof(hash->data));
660 	}
661 }
662 
663 /*******************************************************************
664 reads or writes an ARC4_OWF structure.
665 ********************************************************************/
smb_io_arc4_owf(BOOL io,ARC4_OWF * hash,char * q,char * base,int align,int depth)666 char* smb_io_arc4_owf(BOOL io, ARC4_OWF *hash, char *q, char *base, int align, int depth)
667 {
668 	if (hash == NULL) return NULL;
669 
670 	DEBUG(5,("%s%04x smb_io_arc4_owf\n",  tab_depth(depth), PTR_DIFF(q, base)));
671 	depth++;
672 
673 	q = align_offset(q, base, align);
674 
675 	DBG_RW_PCVAL(False, "data", depth, base, io, q, hash->data, 16); q += 16;
676 
677 	return q;
678 }
679 
680 /*******************************************************************
681 makes a DOM_ID_INFO_1 structure.
682 ********************************************************************/
make_id_info1(DOM_ID_INFO_1 * id,char * domain_name,uint32 param_ctrl,uint32 log_id_low,uint32 log_id_high,char * user_name,char * wksta_name,char * sess_key,unsigned char lm_cypher[16],unsigned char nt_cypher[16])683 void make_id_info1(DOM_ID_INFO_1 *id, char *domain_name,
684 				uint32 param_ctrl, uint32 log_id_low, uint32 log_id_high,
685 				char *user_name, char *wksta_name,
686 				char *sess_key,
687 				unsigned char lm_cypher[16], unsigned char nt_cypher[16])
688 {
689 	int len_domain_name = strlen(domain_name);
690 	int len_user_name   = strlen(user_name  );
691 	int len_wksta_name  = strlen(wksta_name );
692 
693 	unsigned char arc4_lm_owf[16];
694 	unsigned char arc4_nt_owf[16];
695 
696 	if (id == NULL) return;
697 
698 	DEBUG(5,("make_id_info1: %d\n", __LINE__));
699 
700 	id->ptr_id_info1 = 1;
701 
702 	make_uni_hdr(&(id->hdr_domain_name), len_domain_name, len_domain_name, 4);
703 
704 	id->param_ctrl = param_ctrl;
705 	make_logon_id(&(id->logon_id), log_id_low, log_id_high);
706 
707 	make_uni_hdr(&(id->hdr_user_name  ), len_user_name  , len_user_name  , 4);
708 	make_uni_hdr(&(id->hdr_wksta_name ), len_wksta_name , len_wksta_name , 4);
709 
710 #ifdef USE_ARCFOUR
711 
712 	if (lm_cypher && nt_cypher)
713 	{
714 		unsigned char arc4_key[16];
715 #ifdef DEBUG_PASSWORD
716 		DEBUG(100,("lm cypher:"));
717 		dump_data(100, lm_cypher, 16);
718 
719 		DEBUG(100,("nt cypher:"));
720 		dump_data(100, nt_cypher, 16);
721 #endif
722 
723 		memset(arc4_key, 0, 16);
724 		memcpy(arc4_key, sess_key, 8);
725 
726 		arcfour(arc4_key, arc4_lm_owf, lm_cypher);
727 		arcfour(arc4_key, arc4_nt_owf, nt_cypher);
728 
729 #ifdef DEBUG_PASSWORD
730 		DEBUG(100,("arcfour encrypt of lm owf password:"));
731 		dump_data(100, arc4_lm_owf, 16);
732 
733 		DEBUG(100,("arcfour encrypt of nt owf password:"));
734 		dump_data(100, arc4_nt_owf, 16);
735 #endif
736 		/* set up pointers to cypher blocks */
737 		lm_cypher = arc4_lm_owf;
738 		nt_cypher = arc4_nt_owf;
739 	}
740 
741 #else
742 
743 	if (lm_cypher)
744 	{
745 		/* oops.  can only send what-ever-it-is direct */
746 		memcpy(arc4_lm_owf, lm_cypher, 16);
747 		lm_cypher = arc4_lm_owf;
748 	}
749 	if (nt_cypher)
750 	{
751 		/* oops.  can only send what-ever-it-is direct */
752 		memcpy(arc4_nt_owf, nt_cypher, 16);
753 		nt_cypher = arc4_nt_owf;
754 	}
755 
756 #endif
757 
758 	make_arc4_owf(&(id->arc4_lm_owf), lm_cypher);
759 	make_arc4_owf(&(id->arc4_nt_owf), nt_cypher);
760 
761 	make_unistr2(&(id->uni_domain_name), domain_name, len_domain_name);
762 	make_unistr2(&(id->uni_user_name  ), user_name  , len_user_name  );
763 	make_unistr2(&(id->uni_wksta_name ), wksta_name , len_wksta_name );
764 }
765 
766 /*******************************************************************
767 reads or writes an DOM_ID_INFO_1 structure.
768 ********************************************************************/
smb_io_id_info1(BOOL io,DOM_ID_INFO_1 * id,char * q,char * base,int align,int depth)769 char* smb_io_id_info1(BOOL io, DOM_ID_INFO_1 *id, char *q, char *base, int align, int depth)
770 {
771 	if (id == NULL) return NULL;
772 
773 	DEBUG(5,("%s%04x smb_io_id_info1\n",  tab_depth(depth), PTR_DIFF(q, base)));
774 	depth++;
775 
776 	q = align_offset(q, base, align);
777 
778 	DBG_RW_IVAL("ptr_id_info1", depth, base, io, q, id->ptr_id_info1); q += 4;
779 
780 	if (id->ptr_id_info1 != 0)
781 	{
782 		q = smb_io_unihdr(io, &(id->hdr_domain_name), q, base, align, depth);
783 
784 		DBG_RW_IVAL("param_ctrl", depth, base, io, q, id->param_ctrl); q += 4;
785 		q = smb_io_logon_id(io, &(id->logon_id), q, base, align, depth);
786 
787 		q = smb_io_unihdr(io, &(id->hdr_user_name  ), q, base, align, depth);
788 		q = smb_io_unihdr(io, &(id->hdr_wksta_name ), q, base, align, depth);
789 
790 		q = smb_io_arc4_owf(io, &(id->arc4_lm_owf), q, base, align, depth);
791 		q = smb_io_arc4_owf(io, &(id->arc4_nt_owf), q, base, align, depth);
792 
793 		q = smb_io_unistr2(io, &(id->uni_domain_name), q, base, align, depth);
794 		q = smb_io_unistr2(io, &(id->uni_user_name  ), q, base, align, depth);
795 		q = smb_io_unistr2(io, &(id->uni_wksta_name ), q, base, align, depth);
796 	}
797 
798 	return q;
799 }
800 
801 /*******************************************************************
802 makes a DOM_SAM_INFO structure.
803 ********************************************************************/
make_sam_info(DOM_SAM_INFO * sam,char * logon_srv,char * comp_name,DOM_CRED * clnt_cred,DOM_CRED * rtn_cred,uint16 logon_level,uint16 switch_value,DOM_ID_INFO_1 * id1)804 void make_sam_info(DOM_SAM_INFO *sam,
805 				char *logon_srv, char *comp_name, DOM_CRED *clnt_cred,
806 				DOM_CRED *rtn_cred, uint16 logon_level, uint16 switch_value,
807 				DOM_ID_INFO_1 *id1)
808 {
809 	if (sam == NULL) return;
810 
811 	DEBUG(5,("make_sam_info: %d\n", __LINE__));
812 
813 	make_clnt_info2(&(sam->client), logon_srv, comp_name, clnt_cred);
814 
815 	if (rtn_cred != NULL)
816 	{
817 		sam->ptr_rtn_cred = 1;
818 		memcpy(&(sam->rtn_cred), rtn_cred, sizeof(sam->rtn_cred));
819 	}
820 	else
821 	{
822 		sam->ptr_rtn_cred = 0;
823 	}
824 
825 	sam->logon_level  = logon_level;
826 	sam->switch_value = switch_value;
827 
828 	switch (sam->switch_value)
829 	{
830 		case 1:
831 		{
832 			sam->auth.id1 = id1;
833 			break;
834 		}
835 		default:
836 		{
837 			/* PANIC! */
838 			DEBUG(4,("make_sam_info: unknown switch_value!\n"));
839 			break;
840 		}
841 	}
842 }
843 
844 /*******************************************************************
845 reads or writes a DOM_SAM_INFO structure.
846 ********************************************************************/
smb_io_sam_info(BOOL io,DOM_SAM_INFO * sam,char * q,char * base,int align,int depth)847 char* smb_io_sam_info(BOOL io, DOM_SAM_INFO *sam, char *q, char *base, int align, int depth)
848 {
849 	if (sam == NULL) return NULL;
850 
851 	DEBUG(5,("%s%04x smb_io_sam_info\n",  tab_depth(depth), PTR_DIFF(q, base)));
852 	depth++;
853 
854 	q = align_offset(q, base, align);
855 
856 	q = smb_io_clnt_info2(io, &(sam->client  ), q, base, align, depth);
857 
858 	DBG_RW_IVAL("ptr_rtn_cred", depth, base, io, q, sam->ptr_rtn_cred); q += 4;
859 	q = smb_io_cred      (io, &(sam->rtn_cred), q, base, align, depth);
860 
861 	DBG_RW_SVAL("logon_level ", depth, base, io, q, sam->logon_level); q += 2;
862 	DBG_RW_SVAL("switch_value", depth, base, io, q, sam->switch_value); q += 2;
863 
864 	switch (sam->switch_value)
865 	{
866 		case 1:
867 		{
868 			q = smb_io_id_info1(io, sam->auth.id1, q, base, align, depth);
869 			break;
870 		}
871 		default:
872 		{
873 			/* PANIC! */
874 			DEBUG(4,("smb_io_sam_info: unknown switch_value!\n"));
875 			break;
876 		}
877 	}
878 	return q;
879 }
880 
881 /*******************************************************************
882 reads or writes a DOM_GID structure.
883 ********************************************************************/
smb_io_gid(BOOL io,DOM_GID * gid,char * q,char * base,int align,int depth)884 char* smb_io_gid(BOOL io, DOM_GID *gid, char *q, char *base, int align, int depth)
885 {
886 	if (gid == NULL) return NULL;
887 
888 	DEBUG(5,("%s%04x smb_io_gid\n",  tab_depth(depth), PTR_DIFF(q, base)));
889 	depth++;
890 
891 	q = align_offset(q, base, align);
892 
893 	DBG_RW_IVAL("g_rid", depth, base, io, q, gid->g_rid); q += 4;
894 	DBG_RW_IVAL("attr ", depth, base, io, q, gid->attr ); q += 4;
895 
896 	return q;
897 }
898 
899 /*******************************************************************
900 creates an RPC_HDR structure.
901 ********************************************************************/
make_rpc_hdr(RPC_HDR * hdr,enum RPC_PKT_TYPE pkt_type,uint8 frag,uint32 call_id,int data_len)902 void make_rpc_hdr(RPC_HDR *hdr, enum RPC_PKT_TYPE pkt_type, uint8 frag,
903 				uint32 call_id, int data_len)
904 {
905 	if (hdr == NULL) return;
906 
907 	hdr->major        = 5;               /* RPC version 5 */
908 	hdr->minor        = 0;               /* minor version 0 */
909 	hdr->pkt_type     = pkt_type;        /* RPC packet type */
910 	hdr->frag         = frag;            /* first frag + last frag */
911 	hdr->pack_type    = 0x10;            /* packed data representation */
912 	hdr->frag_len     = data_len;        /* fragment length, fill in later */
913 	hdr->auth_len     = 0;               /* authentication length */
914 	hdr->call_id      = call_id;         /* call identifier - match incoming RPC */
915 }
916 
917 /*******************************************************************
918 reads or writes an RPC_HDR structure.
919 ********************************************************************/
smb_io_rpc_hdr(BOOL io,RPC_HDR * rpc,char * q,char * base,int align,int depth)920 char* smb_io_rpc_hdr(BOOL io, RPC_HDR *rpc, char *q, char *base, int align, int depth)
921 {
922 	if (rpc == NULL) return NULL;
923 
924 	DEBUG(5,("%s%04x smb_io_rpc_hdr\n",  tab_depth(depth), PTR_DIFF(q, base)));
925 	depth++;
926 
927 	DBG_RW_CVAL("major     ", depth, base, io, q, rpc->major); q++;
928 	DBG_RW_CVAL("minor     ", depth, base, io, q, rpc->minor); q++;
929 	DBG_RW_CVAL("pkt_type  ", depth, base, io, q, rpc->pkt_type); q++;
930 	DBG_RW_CVAL("frag      ", depth, base, io, q, rpc->frag); q++;
931 	DBG_RW_IVAL("pack_type ", depth, base, io, q, rpc->pack_type); q += 4;
932 	DBG_RW_SVAL("frag_len  ", depth, base, io, q, rpc->frag_len); q += 2;
933 	DBG_RW_SVAL("auth_len  ", depth, base, io, q, rpc->auth_len); q += 2;
934 	DBG_RW_IVAL("call_id   ", depth, base, io, q, rpc->call_id); q += 4;
935 
936 	return q;
937 }
938 
939 /*******************************************************************
940 creates an RPC_IFACE structure.
941 ********************************************************************/
make_rpc_iface(RPC_IFACE * ifc,char data[16],uint32 version)942 void make_rpc_iface(RPC_IFACE *ifc, char data[16], uint32 version)
943 {
944 	if (ifc == NULL || data == NULL) return;
945 
946 	memcpy(ifc->data, data, sizeof(ifc->data)); /* 16 bytes of number */
947 	ifc->version = version; /* the interface number */
948 }
949 
950 /*******************************************************************
951 reads or writes an RPC_IFACE structure.
952 ********************************************************************/
smb_io_rpc_iface(BOOL io,RPC_IFACE * ifc,char * q,char * base,int align,int depth)953 char* smb_io_rpc_iface(BOOL io, RPC_IFACE *ifc, char *q, char *base, int align, int depth)
954 {
955 	if (ifc == NULL) return NULL;
956 
957 	DEBUG(5,("%s%04x smb_io_rpc_iface\n", tab_depth(depth), PTR_DIFF(q, base)));
958 	depth++;
959 
960 	q = align_offset(q, base, align);
961 
962 	DBG_RW_PCVAL(False, "data   ", depth, base, io, q, ifc->data, sizeof(ifc->data)); q += sizeof(ifc->data);
963 	DBG_RW_IVAL (       "version", depth, base, io, q, ifc->version); q += 4;
964 
965 	return q;
966 }
967 
968 /*******************************************************************
969 creates an RPC_ADDR_STR structure.
970 ********************************************************************/
make_rpc_addr_str(RPC_ADDR_STR * str,char * name)971 void make_rpc_addr_str(RPC_ADDR_STR *str, char *name)
972 {
973 	if (str == NULL || name == NULL) return;
974 
975 	str->len = strlen(name) + 1;
976 	fstrcpy(str->str, name);
977 }
978 
979 /*******************************************************************
980 reads or writes an RPC_ADDR_STR structure.
981 ********************************************************************/
smb_io_rpc_addr_str(BOOL io,RPC_ADDR_STR * str,char * q,char * base,int align,int depth)982 char* smb_io_rpc_addr_str(BOOL io, RPC_ADDR_STR *str, char *q, char *base, int align, int depth)
983 {
984 	if (str == NULL) return NULL;
985 
986 	DEBUG(5,("%s%04x smb_io_rpc_addr_str\n", tab_depth(depth), PTR_DIFF(q, base)));
987 	depth++;
988 
989 	q = align_offset(q, base, align);
990 
991 	DBG_RW_IVAL (      "len", depth, base, io, q, str->len); q += 2;
992 	DBG_RW_PCVAL(True, "str", depth, base, io, q, str->str, str->len); q += str->len;
993 
994 	return q;
995 }
996 
997 /*******************************************************************
998 creates an RPC_HDR_BBA structure.
999 ********************************************************************/
make_rpc_hdr_bba(RPC_HDR_BBA * bba,uint16 max_tsize,uint16 max_rsize,uint32 assoc_gid)1000 void make_rpc_hdr_bba(RPC_HDR_BBA *bba, uint16 max_tsize, uint16 max_rsize, uint32 assoc_gid)
1001 {
1002 	if (bba == NULL) return;
1003 
1004 	bba->max_tsize = max_tsize; /* maximum transmission fragment size (0x1630) */
1005 	bba->max_rsize = max_rsize; /* max receive fragment size (0x1630) */
1006 	bba->assoc_gid = assoc_gid; /* associated group id (0x0) */
1007 }
1008 
1009 /*******************************************************************
1010 reads or writes an RPC_HDR_BBA structure.
1011 ********************************************************************/
smb_io_rpc_hdr_bba(BOOL io,RPC_HDR_BBA * rpc,char * q,char * base,int align,int depth)1012 char* smb_io_rpc_hdr_bba(BOOL io, RPC_HDR_BBA *rpc, char *q, char *base, int align, int depth)
1013 {
1014 	if (rpc == NULL) return NULL;
1015 
1016 	DEBUG(5,("%s%04x smb_io_rpc_hdr_bba\n",  tab_depth(depth), PTR_DIFF(q, base)));
1017 	depth++;
1018 
1019 	DBG_RW_SVAL("max_tsize", depth, base, io, q, rpc->max_tsize); q += 2;
1020 	DBG_RW_SVAL("max_rsize", depth, base, io, q, rpc->max_rsize); q += 2;
1021 	DBG_RW_IVAL("assoc_gid", depth, base, io, q, rpc->assoc_gid); q += 4;
1022 
1023 	return q;
1024 }
1025 
1026 /*******************************************************************
1027 creates an RPC_HDR_RB structure.
1028 ********************************************************************/
make_rpc_hdr_rb(RPC_HDR_RB * rpc,uint16 max_tsize,uint16 max_rsize,uint32 assoc_gid,uint32 num_elements,uint16 context_id,uint8 num_syntaxes,RPC_IFACE * abstract,RPC_IFACE * transfer)1029 void make_rpc_hdr_rb(RPC_HDR_RB *rpc,
1030 				uint16 max_tsize, uint16 max_rsize, uint32 assoc_gid,
1031 				uint32 num_elements, uint16 context_id, uint8 num_syntaxes,
1032 				RPC_IFACE *abstract, RPC_IFACE *transfer)
1033 {
1034 	if (rpc == NULL) return;
1035 
1036 	make_rpc_hdr_bba(&(rpc->bba), max_tsize, max_rsize, assoc_gid);
1037 
1038 	rpc->num_elements = num_elements ; /* the number of elements (0x1) */
1039 	rpc->context_id   = context_id   ; /* presentation context identifier (0x0) */
1040 	rpc->num_syntaxes = num_syntaxes ; /* the number of syntaxes (has always been 1?)(0x1) */
1041 
1042 	/* num and vers. of interface client is using */
1043 	memcpy(&(rpc->abstract), abstract, sizeof(rpc->abstract));
1044 
1045 	/* num and vers. of interface to use for replies */
1046 	memcpy(&(rpc->transfer), transfer, sizeof(rpc->transfer));
1047 }
1048 
1049 /*******************************************************************
1050 reads or writes an RPC_HDR_RB structure.
1051 ********************************************************************/
smb_io_rpc_hdr_rb(BOOL io,RPC_HDR_RB * rpc,char * q,char * base,int align,int depth)1052 char* smb_io_rpc_hdr_rb(BOOL io, RPC_HDR_RB *rpc, char *q, char *base, int align, int depth)
1053 {
1054 	if (rpc == NULL) return NULL;
1055 
1056 	DEBUG(5,("%s%04x smb_io_rpc_hdr_bba\n", tab_depth(depth), PTR_DIFF(q, base)));
1057 	depth++;
1058 
1059 	q = smb_io_rpc_hdr_bba(io, &(rpc->bba), q, base, align, depth);
1060 
1061 	DBG_RW_IVAL("num_elements", depth, base, io, q, rpc->num_elements); q += 4;
1062 	DBG_RW_SVAL("context_id  ", depth, base, io, q, rpc->context_id  ); q += 2;
1063 	DBG_RW_CVAL("num_syntaxes", depth, base, io, q, rpc->num_syntaxes); q += 1;
1064 
1065 	q = smb_io_rpc_iface(io, &(rpc->abstract), q, base, align, depth);
1066 	q = smb_io_rpc_iface(io, &(rpc->transfer), q, base, align, depth);
1067 
1068 	return q;
1069 }
1070 
1071 /*******************************************************************
1072 creates an RPC_RESULTS structure.
1073 
1074 lkclXXXX only one reason at the moment!
1075 
1076 ********************************************************************/
make_rpc_results(RPC_RESULTS * res,uint8 num_results,uint16 result,uint16 reason)1077 void make_rpc_results(RPC_RESULTS *res,
1078 				uint8 num_results, uint16 result, uint16 reason)
1079 {
1080 	if (res == NULL) return;
1081 
1082 	res->num_results = num_results; /* the number of results (0x01) */
1083 	res->result      = result     ;  /* result (0x00 = accept) */
1084 	res->reason      = reason     ;  /* reason (0x00 = no reason specified) */
1085 }
1086 
1087 /*******************************************************************
1088 reads or writes an RPC_RESULTS structure.
1089 
1090 lkclXXXX only one reason at the moment!
1091 
1092 ********************************************************************/
smb_io_rpc_results(BOOL io,RPC_RESULTS * res,char * q,char * base,int align,int depth)1093 char* smb_io_rpc_results(BOOL io, RPC_RESULTS *res, char *q, char *base, int align, int depth)
1094 {
1095 	if (res == NULL) return NULL;
1096 
1097 	DEBUG(5,("%s%04x smb_io_rpc_results\n", tab_depth(depth), PTR_DIFF(q, base)));
1098 	depth++;
1099 
1100 	q = align_offset(q, base, align);
1101 
1102 	DBG_RW_CVAL("num_results", depth, base, io, q, res->num_results); q++;
1103 
1104 	q = align_offset(q, base, align);
1105 
1106 	DBG_RW_SVAL("result     ", depth, base, io, q, res->result     ); q += 2;
1107 	DBG_RW_SVAL("reason     ", depth, base, io, q, res->reason     ); q += 2;
1108 
1109 	return q;
1110 }
1111 
1112 /*******************************************************************
1113 creates an RPC_HDR_BA structure.
1114 
1115 lkclXXXX only one reason at the moment!
1116 
1117 ********************************************************************/
make_rpc_hdr_ba(RPC_HDR_BA * rpc,uint16 max_tsize,uint16 max_rsize,uint32 assoc_gid,char * pipe_addr,uint8 num_results,uint16 result,uint16 reason,RPC_IFACE * transfer)1118 void make_rpc_hdr_ba(RPC_HDR_BA *rpc,
1119 				uint16 max_tsize, uint16 max_rsize, uint32 assoc_gid,
1120 				char *pipe_addr,
1121 				uint8 num_results, uint16 result, uint16 reason,
1122 				RPC_IFACE *transfer)
1123 {
1124 	if (rpc == NULL || transfer == NULL || pipe_addr == NULL) return;
1125 
1126 	make_rpc_hdr_bba (&(rpc->bba ), max_tsize, max_rsize, assoc_gid);
1127 	make_rpc_addr_str(&(rpc->addr), pipe_addr);
1128 	make_rpc_results (&(rpc->res ), num_results, result, reason);
1129 
1130 	/* the transfer syntax from the request */
1131 	memcpy(&(rpc->transfer), transfer, sizeof(rpc->transfer));
1132 }
1133 
1134 /*******************************************************************
1135 reads or writes an RPC_HDR_BA structure.
1136 ********************************************************************/
smb_io_rpc_hdr_ba(BOOL io,RPC_HDR_BA * rpc,char * q,char * base,int align,int depth)1137 char* smb_io_rpc_hdr_ba(BOOL io, RPC_HDR_BA *rpc, char *q, char *base, int align, int depth)
1138 {
1139 	if (rpc == NULL) return NULL;
1140 
1141 	DEBUG(5,("%s%04x smb_io_rpc_hdr_ba\n", tab_depth(depth), PTR_DIFF(q, base)));
1142 	depth++;
1143 
1144 	q = smb_io_rpc_hdr_bba (io, &(rpc->bba)     , q, base, align, depth);
1145 	q = smb_io_rpc_addr_str(io, &(rpc->addr)    , q, base, align, depth);
1146 	q = smb_io_rpc_results (io, &(rpc->res)     , q, base, align, depth);
1147 	q = smb_io_rpc_iface   (io, &(rpc->transfer), q, base, align, depth);
1148 
1149 	return q;
1150 }
1151 
1152 /*******************************************************************
1153 makes an LSA_OBJ_ATTR structure.
1154 ********************************************************************/
make_obj_attr(LSA_OBJ_ATTR * attr,uint32 attributes,uint32 sec_qos)1155 void make_obj_attr(LSA_OBJ_ATTR *attr, uint32 attributes, uint32 sec_qos)
1156 {
1157 	if (attr == NULL) return;
1158 
1159 	DEBUG(5,("make_obj_attr\n"));
1160 
1161 	attr->len = 0x18; /* length of object attribute block, in bytes */
1162 	attr->ptr_root_dir = 0;
1163 	attr->ptr_obj_name = 0;
1164 	attr->attributes = attributes;
1165 	attr->ptr_sec_desc = 0;
1166 	attr->sec_qos = sec_qos;
1167 }
1168 
1169 /*******************************************************************
1170 reads or writes an LSA_OBJ_ATTR structure.
1171 ********************************************************************/
smb_io_obj_attr(BOOL io,LSA_OBJ_ATTR * attr,char * q,char * base,int align,int depth)1172 char* smb_io_obj_attr(BOOL io, LSA_OBJ_ATTR *attr, char *q, char *base, int align, int depth)
1173 {
1174 	char *start;
1175 
1176 	if (attr == NULL) return NULL;
1177 
1178 	DEBUG(5,("%s%04x smb_io_obj_attr\n",  tab_depth(depth), PTR_DIFF(q, base)));
1179 	depth++;
1180 
1181 	q = align_offset(q, base, align);
1182 
1183 	start = q;
1184 
1185 	/* these pointers had _better_ be zero, because we don't know
1186 	   what they point to!
1187 	 */
1188 	DBG_RW_IVAL("len"         , depth, base, io, q, attr->len         ); q += 4; /* 0x18 - length (in bytes) inc. the length field. */
1189 	DBG_RW_IVAL("ptr_root_dir", depth, base, io, q, attr->ptr_root_dir); q += 4; /* 0 - root directory (pointer) */
1190 	DBG_RW_IVAL("ptr_obj_name", depth, base, io, q, attr->ptr_obj_name); q += 4; /* 0 - object name (pointer) */
1191 	DBG_RW_IVAL("attributes"  , depth, base, io, q, attr->attributes  ); q += 4; /* 0 - attributes (undocumented) */
1192 	DBG_RW_IVAL("ptr_sec_desc", depth, base, io, q, attr->ptr_sec_desc); q += 4; /* 0 - security descriptior (pointer) */
1193 	DBG_RW_IVAL("sec_qos"     , depth, base, io, q, attr->sec_qos     ); q += 4; /* 0 - security quality of service */
1194 
1195 	if (attr->len != PTR_DIFF(q, start))
1196 	{
1197 		DEBUG(3,("smb_io_obj_attr: length %lx does not match size %lx\n",
1198 		         attr->len, PTR_DIFF(q, start)));
1199 	}
1200 
1201 	return q;
1202 }
1203 
1204 /*******************************************************************
1205 creates an RPC_HDR_RR structure.
1206 ********************************************************************/
make_rpc_hdr_rr(RPC_HDR_RR * hdr,enum RPC_PKT_TYPE pkt_type,uint32 call_id,int data_len,uint8 opnum)1207 void make_rpc_hdr_rr(RPC_HDR_RR *hdr, enum RPC_PKT_TYPE pkt_type,
1208 				uint32 call_id, int data_len, uint8 opnum)
1209 {
1210 	if (hdr == NULL) return;
1211 
1212 	/* frag is FIRST_FRAG | LAST_FRAG.  lkclXXXX must define these */
1213 	make_rpc_hdr(&(hdr->hdr), pkt_type, 0x03, call_id, data_len);
1214 
1215 	hdr->alloc_hint   = data_len - 0x18; /* allocation hint */
1216 	hdr->context_id   = 0;               /* presentation context identifier */
1217 	hdr->cancel_count = 0;               /* cancel count */
1218 	hdr->opnum        = opnum;           /* opnum */
1219 }
1220 
1221 /*******************************************************************
1222 reads or writes an RPC_HDR_RR structure.
1223 ********************************************************************/
smb_io_rpc_hdr_rr(BOOL io,RPC_HDR_RR * rpc,char * q,char * base,int align,int depth)1224 char* smb_io_rpc_hdr_rr(BOOL io, RPC_HDR_RR *rpc, char *q, char *base, int align, int depth)
1225 {
1226 	if (rpc == NULL) return NULL;
1227 
1228 	DEBUG(5,("%s%04x smb_io_rpc_hdr_rr\n",  tab_depth(depth), PTR_DIFF(q, base)));
1229 	depth++;
1230 
1231 	q = smb_io_rpc_hdr(io, &(rpc->hdr), q, base, align, depth);
1232 
1233 	DBG_RW_IVAL("alloc_hint", depth, base, io, q, rpc->alloc_hint); q += 4;
1234 	DBG_RW_CVAL("context_id", depth, base, io, q, rpc->context_id); q++;
1235 	DBG_RW_CVAL("cancel_ct ", depth, base, io, q, rpc->cancel_count); q++;
1236 	DBG_RW_CVAL("opnum     ", depth, base, io, q, rpc->opnum); q++;
1237 
1238 	return q;
1239 }
1240 /*******************************************************************
1241 reads or writes an LSA_POL_HND structure.
1242 ********************************************************************/
smb_io_pol_hnd(BOOL io,LSA_POL_HND * pol,char * q,char * base,int align,int depth)1243 char* smb_io_pol_hnd(BOOL io, LSA_POL_HND *pol, char *q, char *base, int align, int depth)
1244 {
1245 	if (pol == NULL) return NULL;
1246 
1247 	DEBUG(5,("%s%04x smb_io_pol_hnd\n",  tab_depth(depth), PTR_DIFF(q, base)));
1248 	depth++;
1249 
1250 	q = align_offset(q, base, align);
1251 
1252 	DBG_RW_PCVAL(False, "data", depth, base, io, q, pol->data, POL_HND_SIZE); q += POL_HND_SIZE;
1253 
1254 	return q;
1255 }
1256 
1257 /*******************************************************************
1258 reads or writes a dom query structure.
1259 ********************************************************************/
smb_io_dom_query_3(BOOL io,DOM_QUERY_3 * d_q,char * q,char * base,int align,int depth)1260 char* smb_io_dom_query_3(BOOL io, DOM_QUERY_3 *d_q, char *q, char *base, int align, int depth)
1261 {
1262 	return smb_io_dom_query(io, d_q, q, base, align, depth);
1263 }
1264 
1265 /*******************************************************************
1266 reads or writes a dom query structure.
1267 ********************************************************************/
smb_io_dom_query_5(BOOL io,DOM_QUERY_3 * d_q,char * q,char * base,int align,int depth)1268 char* smb_io_dom_query_5(BOOL io, DOM_QUERY_3 *d_q, char *q, char *base, int align, int depth)
1269 {
1270 	return smb_io_dom_query(io, d_q, q, base, align, depth);
1271 }
1272 
1273 /*******************************************************************
1274 reads or writes a dom query structure.
1275 ********************************************************************/
smb_io_dom_query(BOOL io,DOM_QUERY * d_q,char * q,char * base,int align,int depth)1276 char* smb_io_dom_query(BOOL io, DOM_QUERY *d_q, char *q, char *base, int align, int depth)
1277 {
1278 	if (d_q == NULL) return NULL;
1279 
1280 	DEBUG(5,("%s%04x smb_io_dom_query\n",  tab_depth(depth), PTR_DIFF(q, base)));
1281 	depth++;
1282 
1283 	q = align_offset(q, base, align);
1284 
1285 	DBG_RW_SVAL("uni_dom_max_len", depth, base, io, q, d_q->uni_dom_max_len); q += 2; /* domain name string length * 2 */
1286 	DBG_RW_SVAL("uni_dom_str_len", depth, base, io, q, d_q->uni_dom_str_len); q += 2; /* domain name string length * 2 */
1287 
1288 	DBG_RW_IVAL("buffer_dom_name", depth, base, io, q, d_q->buffer_dom_name); q += 4; /* undocumented domain name string buffer pointer */
1289 	DBG_RW_IVAL("buffer_dom_sid ", depth, base, io, q, d_q->buffer_dom_sid ); q += 4; /* undocumented domain SID string buffer pointer */
1290 
1291 	if (d_q->buffer_dom_name != 0)
1292 	{
1293 		q = smb_io_unistr2(io, &(d_q->uni_domain_name), q, base, align, depth); /* domain name (unicode string) */
1294 	}
1295 	if (d_q->buffer_dom_sid != 0)
1296 	{
1297 		q = smb_io_dom_sid(io, &(d_q->dom_sid), q, base, align, depth); /* domain SID */
1298 	}
1299 
1300 	return q;
1301 }
1302 
1303 /*******************************************************************
1304 reads or writes a DOM_R_REF structure.
1305 ********************************************************************/
smb_io_dom_r_ref(BOOL io,DOM_R_REF * r_r,char * q,char * base,int align,int depth)1306 char* smb_io_dom_r_ref(BOOL io, DOM_R_REF *r_r, char *q, char *base, int align, int depth)
1307 {
1308 	int i;
1309 
1310 	DEBUG(5,("%s%04x smb_io_dom_r_ref\n",  tab_depth(depth), PTR_DIFF(q, base)));
1311 	depth++;
1312 
1313 	if (r_r == NULL) return NULL;
1314 
1315 	q = align_offset(q, base, align);
1316 
1317 	DBG_RW_IVAL("undoc_buffer   ", depth, base, io, q, r_r->undoc_buffer); q += 4; /* undocumented buffer pointer. */
1318 	DBG_RW_IVAL("num_ref_doms_1 ", depth, base, io, q, r_r->num_ref_doms_1); q += 4; /* num referenced domains? */
1319 	DBG_RW_IVAL("buffer_dom_name", depth, base, io, q, r_r->buffer_dom_name); q += 4; /* undocumented domain name buffer pointer. */
1320 	DBG_RW_IVAL("max_entries    ", depth, base, io, q, r_r->max_entries); q += 4; /* 32 - max number of entries */
1321 	DBG_RW_IVAL("num_ref_doms_2 ", depth, base, io, q, r_r->num_ref_doms_2); q += 4; /* 4 - num referenced domains? */
1322 
1323 	q = smb_io_unihdr2(io, &(r_r->hdr_dom_name), q, base, align, depth); /* domain name unicode string header */
1324 
1325 	for (i = 0; i < r_r->num_ref_doms_1-1; i++)
1326 	{
1327 		q = smb_io_unihdr2(io, &(r_r->hdr_ref_dom[i]), q, base, align, depth);
1328 	}
1329 
1330 	q = smb_io_unistr(io, &(r_r->uni_dom_name), q, base, align, depth); /* domain name unicode string */
1331 
1332 	for (i = 0; i < r_r->num_ref_doms_2; i++)
1333 	{
1334 		q = smb_io_dom_sid(io, &(r_r->ref_dom[i]), q, base, align, depth); /* referenced domain SIDs */
1335 	}
1336 	return q;
1337 }
1338 
1339 /*******************************************************************
1340 reads or writes a DOM_NAME structure.
1341 ********************************************************************/
smb_io_dom_name(BOOL io,DOM_NAME * name,char * q,char * base,int align,int depth)1342 char* smb_io_dom_name(BOOL io, DOM_NAME *name, char *q, char *base, int align, int depth)
1343 {
1344 	if (name == NULL) return NULL;
1345 
1346 	DEBUG(5,("%s%04x smb_io_dom_name\n",  tab_depth(depth), PTR_DIFF(q, base)));
1347 	depth++;
1348 
1349 	q = align_offset(q, base, align);
1350 
1351 	DBG_RW_IVAL("uni_str_len", depth, base, io, q, name->uni_str_len); q += 4;
1352 
1353 	/* don't know if len is specified by uni_str_len member... */
1354 	/* assume unicode string is unicode-null-terminated, instead */
1355 
1356 	q = smb_io_unistr(io, &(name->str), q, base, align, depth);
1357 
1358 	return q;
1359 }
1360 
1361 
1362 /*******************************************************************
1363 reads or writes a structure.
1364 ********************************************************************/
smb_io_neg_flags(BOOL io,NEG_FLAGS * neg,char * q,char * base,int align,int depth)1365 char* smb_io_neg_flags(BOOL io, NEG_FLAGS *neg, char *q, char *base, int align, int depth)
1366 {
1367 	if (neg == NULL) return NULL;
1368 
1369 	DEBUG(5,("%s%04x smb_io_neg_flags\n",  tab_depth(depth), PTR_DIFF(q, base)));
1370 	depth++;
1371 
1372 	q = align_offset(q, base, align);
1373 
1374 	DBG_RW_IVAL("neg_flags", depth, base, io, q, neg->neg_flags); q += 4;
1375 
1376 	return q;
1377 }
1378 
1379 
1380 #if 0
1381 /*******************************************************************
1382 reads or writes a structure.
1383 ********************************************************************/
1384  char* smb_io_(BOOL io, *, char *q, char *base, int align, int depth)
1385 {
1386 	if (== NULL) return NULL;
1387 
1388 	q = align_offset(q, base, align);
1389 
1390 	DBG_RW_IVAL("", depth, base, io, q, ); q += 4;
1391 
1392 	return q;
1393 }
1394 #endif
1395 
1396 #endif
1397