merge from APP_HEAD
[Samba.git] / source / rpc_parse / parse_misc.c
blob01d76981736f5bb9e7c610b3b35b2a21de99c29a
1 /*
2 * Unix SMB/CIFS implementation.
3 * RPC Pipe client / server routines
4 * Copyright (C) Andrew Tridgell 1992-1997,
5 * Copyright (C) Luke Kenneth Casson Leighton 1996-1997,
6 * Copyright (C) Paul Ashton 1997.
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, write to the Free Software
20 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 #include "includes.h"
25 #undef DBGC_CLASS
26 #define DBGC_CLASS DBGC_RPC_PARSE
28 /****************************************************************************
29 A temporary TALLOC context for things like unistrs, that is valid for
30 the life of a complete RPC call.
31 ****************************************************************************/
33 static TALLOC_CTX *current_rpc_talloc = NULL;
35 TALLOC_CTX *get_current_rpc_talloc(void)
37 return current_rpc_talloc;
40 void set_current_rpc_talloc( TALLOC_CTX *ctx)
42 current_rpc_talloc = ctx;
45 static TALLOC_CTX *main_loop_talloc = NULL;
47 /*******************************************************************
48 free up temporary memory - called from the main loop
49 ********************************************************************/
51 void main_loop_talloc_free(void)
53 if (!main_loop_talloc)
54 return;
55 talloc_destroy(main_loop_talloc);
56 main_loop_talloc = NULL;
59 /*******************************************************************
60 Get a talloc context that is freed in the main loop...
61 ********************************************************************/
63 TALLOC_CTX *main_loop_talloc_get(void)
65 if (!main_loop_talloc) {
66 main_loop_talloc = talloc_init_named("main loop talloc (mainly parse_misc)");
67 if (!main_loop_talloc)
68 smb_panic("main_loop_talloc: malloc fail\n");
71 return main_loop_talloc;
74 /*******************************************************************
75 Try and get a talloc context. Get the rpc one if possible, else
76 get the main loop one. The main loop one is more dangerous as it
77 goes away between packets, the rpc one will stay around for as long
78 as a current RPC lasts.
79 ********************************************************************/
81 TALLOC_CTX *get_talloc_ctx(void)
83 TALLOC_CTX *tc = get_current_rpc_talloc();
85 if (tc)
86 return tc;
87 return main_loop_talloc_get();
90 /*******************************************************************
91 Reads or writes a UTIME type.
92 ********************************************************************/
94 static BOOL smb_io_utime(char *desc, UTIME *t, prs_struct *ps, int depth)
96 if (t == NULL)
97 return False;
99 prs_debug(ps, depth, desc, "smb_io_utime");
100 depth++;
102 if(!prs_align(ps))
103 return False;
105 if(!prs_uint32 ("time", ps, depth, &t->time))
106 return False;
108 return True;
111 /*******************************************************************
112 Reads or writes an NTTIME structure.
113 ********************************************************************/
115 BOOL smb_io_time(char *desc, NTTIME *nttime, prs_struct *ps, int depth)
117 if (nttime == NULL)
118 return False;
120 prs_debug(ps, depth, desc, "smb_io_time");
121 depth++;
123 if(!prs_align(ps))
124 return False;
126 if(!prs_uint32("low ", ps, depth, &nttime->low)) /* low part */
127 return False;
128 if(!prs_uint32("high", ps, depth, &nttime->high)) /* high part */
129 return False;
131 return True;
134 /*******************************************************************
135 Reads or writes a LOOKUP_LEVEL structure.
136 ********************************************************************/
138 BOOL smb_io_lookup_level(char *desc, LOOKUP_LEVEL *level, prs_struct *ps, int depth)
140 if (level == NULL)
141 return False;
143 prs_debug(ps, depth, desc, "smb_io_lookup_level");
144 depth++;
146 if(!prs_align(ps))
147 return False;
148 if(!prs_uint16("value", ps, depth, &level->value))
149 return False;
150 if(!prs_align(ps))
151 return False;
153 return True;
156 /*******************************************************************
157 Gets an enumeration handle from an ENUM_HND structure.
158 ********************************************************************/
160 uint32 get_enum_hnd(ENUM_HND *enh)
162 return (enh && enh->ptr_hnd != 0) ? enh->handle : 0;
165 /*******************************************************************
166 Inits an ENUM_HND structure.
167 ********************************************************************/
169 void init_enum_hnd(ENUM_HND *enh, uint32 hnd)
171 DEBUG(5,("smb_io_enum_hnd\n"));
173 enh->ptr_hnd = (hnd != 0) ? 1 : 0;
174 enh->handle = hnd;
177 /*******************************************************************
178 Reads or writes an ENUM_HND structure.
179 ********************************************************************/
181 BOOL smb_io_enum_hnd(char *desc, ENUM_HND *hnd, prs_struct *ps, int depth)
183 if (hnd == NULL)
184 return False;
186 prs_debug(ps, depth, desc, "smb_io_enum_hnd");
187 depth++;
189 if(!prs_align(ps))
190 return False;
192 if(!prs_uint32("ptr_hnd", ps, depth, &hnd->ptr_hnd)) /* pointer */
193 return False;
195 if (hnd->ptr_hnd != 0) {
196 if(!prs_uint32("handle ", ps, depth, &hnd->handle )) /* enum handle */
197 return False;
200 return True;
203 /*******************************************************************
204 Reads or writes a DOM_SID structure.
205 ********************************************************************/
207 BOOL smb_io_dom_sid(char *desc, DOM_SID *sid, prs_struct *ps, int depth)
209 int i;
211 if (sid == NULL)
212 return False;
214 prs_debug(ps, depth, desc, "smb_io_dom_sid");
215 depth++;
217 if(!prs_uint8 ("sid_rev_num", ps, depth, &sid->sid_rev_num))
218 return False;
219 if(!prs_uint8 ("num_auths ", ps, depth, &sid->num_auths))
220 return False;
222 for (i = 0; i < 6; i++)
224 fstring tmp;
225 slprintf(tmp, sizeof(tmp) - 1, "id_auth[%d] ", i);
226 if(!prs_uint8 (tmp, ps, depth, &sid->id_auth[i]))
227 return False;
230 /* oops! XXXX should really issue a warning here... */
231 if (sid->num_auths > MAXSUBAUTHS)
232 sid->num_auths = MAXSUBAUTHS;
234 if(!prs_uint32s(False, "sub_auths ", ps, depth, sid->sub_auths, sid->num_auths))
235 return False;
237 return True;
240 /*******************************************************************
241 Inits a DOM_SID structure.
243 BIG NOTE: this function only does SIDS where the identauth is not >= 2^32
244 identauth >= 2^32 can be detected because it will be specified in hex
245 ********************************************************************/
247 void init_dom_sid(DOM_SID *sid, char *str_sid)
249 pstring domsid;
250 int identauth;
251 char *p;
253 if (str_sid == NULL)
255 DEBUG(4,("netlogon domain SID: none\n"));
256 sid->sid_rev_num = 0;
257 sid->num_auths = 0;
258 return;
261 pstrcpy(domsid, str_sid);
263 DEBUG(4,("init_dom_sid %d SID: %s\n", __LINE__, domsid));
265 /* assume, but should check, that domsid starts "S-" */
266 p = strtok(domsid+2,"-");
267 sid->sid_rev_num = atoi(p);
269 /* identauth in decimal should be < 2^32 */
270 /* identauth in hex should be >= 2^32 */
271 identauth = atoi(strtok(0,"-"));
273 DEBUG(4,("netlogon rev %d\n", sid->sid_rev_num));
274 DEBUG(4,("netlogon %s ia %d\n", p, identauth));
276 sid->id_auth[0] = 0;
277 sid->id_auth[1] = 0;
278 sid->id_auth[2] = (identauth & 0xff000000) >> 24;
279 sid->id_auth[3] = (identauth & 0x00ff0000) >> 16;
280 sid->id_auth[4] = (identauth & 0x0000ff00) >> 8;
281 sid->id_auth[5] = (identauth & 0x000000ff);
283 sid->num_auths = 0;
285 while ((p = strtok(0, "-")) != NULL && sid->num_auths < MAXSUBAUTHS)
286 sid->sub_auths[sid->num_auths++] = atoi(p);
288 DEBUG(4,("init_dom_sid: %d SID: %s\n", __LINE__, domsid));
291 /*******************************************************************
292 Inits a DOM_SID2 structure.
293 ********************************************************************/
295 void init_dom_sid2(DOM_SID2 *sid2, const DOM_SID *sid)
297 sid2->sid = *sid;
298 sid2->num_auths = sid2->sid.num_auths;
301 /*******************************************************************
302 Reads or writes a DOM_SID2 structure.
303 ********************************************************************/
305 BOOL smb_io_dom_sid2(char *desc, DOM_SID2 *sid, prs_struct *ps, int depth)
307 if (sid == NULL)
308 return False;
310 prs_debug(ps, depth, desc, "smb_io_dom_sid2");
311 depth++;
313 if(!prs_align(ps))
314 return False;
316 if(!prs_uint32("num_auths", ps, depth, &sid->num_auths))
317 return False;
319 if(!smb_io_dom_sid("sid", &sid->sid, ps, depth))
320 return False;
322 return True;
325 /*******************************************************************
326 creates a STRHDR structure.
327 ********************************************************************/
329 void init_str_hdr(STRHDR *hdr, int max_len, int len, uint32 buffer)
331 hdr->str_max_len = max_len;
332 hdr->str_str_len = len;
333 hdr->buffer = buffer;
336 /*******************************************************************
337 Reads or writes a STRHDR structure.
338 ********************************************************************/
340 BOOL smb_io_strhdr(char *desc, STRHDR *hdr, prs_struct *ps, int depth)
342 if (hdr == NULL)
343 return False;
345 prs_debug(ps, depth, desc, "smb_io_strhdr");
346 depth++;
348 prs_align(ps);
350 if(!prs_uint16("str_str_len", ps, depth, &hdr->str_str_len))
351 return False;
352 if(!prs_uint16("str_max_len", ps, depth, &hdr->str_max_len))
353 return False;
354 if(!prs_uint32("buffer ", ps, depth, &hdr->buffer))
355 return False;
357 return True;
360 /*******************************************************************
361 Inits a UNIHDR structure.
362 ********************************************************************/
364 void init_uni_hdr(UNIHDR *hdr, int len)
366 hdr->uni_str_len = 2 * len;
367 hdr->uni_max_len = 2 * len;
368 hdr->buffer = len != 0 ? 1 : 0;
371 /*******************************************************************
372 Reads or writes a UNIHDR structure.
373 ********************************************************************/
375 BOOL smb_io_unihdr(char *desc, UNIHDR *hdr, prs_struct *ps, int depth)
377 if (hdr == NULL)
378 return False;
380 prs_debug(ps, depth, desc, "smb_io_unihdr");
381 depth++;
383 if(!prs_align(ps))
384 return False;
386 if(!prs_uint16("uni_str_len", ps, depth, &hdr->uni_str_len))
387 return False;
388 if(!prs_uint16("uni_max_len", ps, depth, &hdr->uni_max_len))
389 return False;
390 if(!prs_uint32("buffer ", ps, depth, &hdr->buffer))
391 return False;
393 return True;
396 /*******************************************************************
397 Inits a BUFHDR structure.
398 ********************************************************************/
400 void init_buf_hdr(BUFHDR *hdr, int max_len, int len)
402 hdr->buf_max_len = max_len;
403 hdr->buf_len = len;
406 /*******************************************************************
407 prs_uint16 wrapper. Call this and it sets up a pointer to where the
408 uint16 should be stored, or gets the size if reading.
409 ********************************************************************/
411 BOOL smb_io_hdrbuf_pre(char *desc, BUFHDR *hdr, prs_struct *ps, int depth, uint32 *offset)
413 (*offset) = prs_offset(ps);
414 if (ps->io) {
416 /* reading. */
418 if(!smb_io_hdrbuf(desc, hdr, ps, depth))
419 return False;
421 } else {
423 /* writing. */
425 if(!prs_set_offset(ps, prs_offset(ps) + (sizeof(uint32) * 2)))
426 return False;
429 return True;
432 /*******************************************************************
433 smb_io_hdrbuf wrapper. Call this and it retrospectively stores the size.
434 Does nothing on reading, as that is already handled by ...._pre()
435 ********************************************************************/
437 BOOL smb_io_hdrbuf_post(char *desc, BUFHDR *hdr, prs_struct *ps, int depth,
438 uint32 ptr_hdrbuf, uint32 max_len, uint32 len)
440 if (!ps->io) {
441 /* writing: go back and do a retrospective job. i hate this */
443 uint32 old_offset = prs_offset(ps);
445 init_buf_hdr(hdr, max_len, len);
446 if(!prs_set_offset(ps, ptr_hdrbuf))
447 return False;
448 if(!smb_io_hdrbuf(desc, hdr, ps, depth))
449 return False;
451 if(!prs_set_offset(ps, old_offset))
452 return False;
455 return True;
458 /*******************************************************************
459 Reads or writes a BUFHDR structure.
460 ********************************************************************/
462 BOOL smb_io_hdrbuf(char *desc, BUFHDR *hdr, prs_struct *ps, int depth)
464 if (hdr == NULL)
465 return False;
467 prs_debug(ps, depth, desc, "smb_io_hdrbuf");
468 depth++;
470 if(!prs_align(ps))
471 return False;
473 if(!prs_uint32("buf_max_len", ps, depth, &hdr->buf_max_len))
474 return False;
475 if(!prs_uint32("buf_len ", ps, depth, &hdr->buf_len))
476 return False;
478 return True;
481 /*******************************************************************
482 creates a UNIHDR2 structure.
483 ********************************************************************/
485 void init_uni_hdr2(UNIHDR2 *hdr, int len)
487 init_uni_hdr(&hdr->unihdr, len);
488 hdr->buffer = (len > 0) ? 1 : 0;
491 /*******************************************************************
492 Reads or writes a UNIHDR2 structure.
493 ********************************************************************/
495 BOOL smb_io_unihdr2(char *desc, UNIHDR2 *hdr2, prs_struct *ps, int depth)
497 if (hdr2 == NULL)
498 return False;
500 prs_debug(ps, depth, desc, "smb_io_unihdr2");
501 depth++;
503 if(!prs_align(ps))
504 return False;
506 if(!smb_io_unihdr("hdr", &hdr2->unihdr, ps, depth))
507 return False;
508 if(!prs_uint32("buffer", ps, depth, &hdr2->buffer))
509 return False;
511 return True;
514 /*******************************************************************
515 Inits a UNISTR structure.
516 ********************************************************************/
518 void init_unistr(UNISTR *str, const char *buf)
520 size_t len;
522 if (buf == NULL) {
523 str->buffer = NULL;
524 return;
528 len = strlen(buf) + 1;
530 if (len < MAX_UNISTRLEN)
531 len = MAX_UNISTRLEN;
532 len *= sizeof(uint16);
534 str->buffer = (uint16 *)talloc_zero(get_talloc_ctx(), len);
535 if (str->buffer == NULL)
536 smb_panic("init_unistr: malloc fail\n");
538 rpcstr_push(str->buffer, buf, len, STR_TERMINATE);
541 /*******************************************************************
542 reads or writes a UNISTR structure.
543 XXXX NOTE: UNISTR structures NEED to be null-terminated.
544 ********************************************************************/
546 BOOL smb_io_unistr(char *desc, UNISTR *uni, prs_struct *ps, int depth)
548 if (uni == NULL)
549 return False;
551 prs_debug(ps, depth, desc, "smb_io_unistr");
552 depth++;
554 if(!prs_unistr("unistr", ps, depth, uni))
555 return False;
557 return True;
560 /*******************************************************************
561 Allocate the BUFFER3 memory.
562 ********************************************************************/
564 static void create_buffer3(BUFFER3 *str, size_t len)
566 if (len < MAX_BUFFERLEN)
567 len = MAX_BUFFERLEN;
569 str->buffer = talloc_zero(get_talloc_ctx(), len);
570 if (str->buffer == NULL)
571 smb_panic("create_buffer3: talloc fail\n");
575 /*******************************************************************
576 Inits a BUFFER3 structure from a uint32
577 ********************************************************************/
579 void init_buffer3_uint32(BUFFER3 *str, uint32 val)
581 ZERO_STRUCTP(str);
583 /* set up string lengths. */
584 str->buf_max_len = sizeof(uint32);
585 str->buf_len = sizeof(uint32);
587 create_buffer3(str, sizeof(uint32));
588 SIVAL(str->buffer, 0, val);
591 /*******************************************************************
592 Inits a BUFFER3 structure.
593 ********************************************************************/
595 void init_buffer3_str(BUFFER3 *str, char *buf, int len)
597 ZERO_STRUCTP(str);
599 /* set up string lengths. */
600 str->buf_max_len = len * 2;
601 str->buf_len = len * 2;
603 create_buffer3(str, str->buf_max_len);
605 rpcstr_push(str->buffer, buf, str->buf_max_len, STR_TERMINATE);
609 /*******************************************************************
610 Inits a BUFFER3 structure from a hex string.
611 ********************************************************************/
613 void init_buffer3_hex(BUFFER3 *str, char *buf)
615 ZERO_STRUCTP(str);
616 create_buffer3(str, strlen(buf));
617 str->buf_max_len = str->buf_len = strhex_to_str((char *)str->buffer, sizeof(str->buffer), buf);
620 /*******************************************************************
621 Inits a BUFFER3 structure.
622 ********************************************************************/
624 void init_buffer3_bytes(BUFFER3 *str, uint8 *buf, int len)
626 ZERO_STRUCTP(str);
628 /* max buffer size (allocated size) */
629 str->buf_max_len = len;
630 if (buf != NULL) {
631 create_buffer3(str, len);
632 memcpy(str->buffer, buf, len);
634 str->buf_len = buf != NULL ? len : 0;
637 /*******************************************************************
638 Reads or writes a BUFFER3 structure.
639 the uni_max_len member tells you how large the buffer is.
640 the uni_str_len member tells you how much of the buffer is really used.
641 ********************************************************************/
643 BOOL smb_io_buffer3(char *desc, BUFFER3 *buf3, prs_struct *ps, int depth)
645 if (buf3 == NULL)
646 return False;
648 prs_debug(ps, depth, desc, "smb_io_buffer3");
649 depth++;
651 if(!prs_align(ps))
652 return False;
654 if(!prs_uint32("uni_max_len", ps, depth, &buf3->buf_max_len))
655 return False;
657 if (UNMARSHALLING(ps)) {
658 buf3->buffer = (unsigned char *)prs_alloc_mem(ps, buf3->buf_max_len);
659 if (buf3->buffer == NULL)
660 return False;
663 if(!prs_uint8s(True, "buffer ", ps, depth, buf3->buffer, buf3->buf_max_len))
664 return False;
666 if(!prs_uint32("buf_len ", ps, depth, &buf3->buf_len))
667 return False;
669 return True;
672 /*******************************************************************
673 reads or writes a BUFFER5 structure.
674 the buf_len member tells you how large the buffer is.
675 ********************************************************************/
676 BOOL smb_io_buffer5(char *desc, BUFFER5 *buf5, prs_struct *ps, int depth)
678 prs_debug(ps, depth, desc, "smb_io_buffer5");
679 depth++;
681 if (buf5 == NULL) return False;
683 if(!prs_align(ps))
684 return False;
685 if(!prs_uint32("buf_len", ps, depth, &buf5->buf_len))
686 return False;
689 if(!prs_buffer5(True, "buffer" , ps, depth, buf5))
690 return False;
692 return True;
695 /*******************************************************************
696 Inits a BUFFER2 structure.
697 ********************************************************************/
699 void init_buffer2(BUFFER2 *str, uint8 *buf, int len)
701 ZERO_STRUCTP(str);
703 /* max buffer size (allocated size) */
704 str->buf_max_len = len;
705 str->undoc = 0;
706 str->buf_len = buf != NULL ? len : 0;
708 if (buf != NULL) {
709 if (len < MAX_BUFFERLEN)
710 len = MAX_BUFFERLEN;
711 str->buffer = talloc_zero(get_talloc_ctx(), len);
712 if (str->buffer == NULL)
713 smb_panic("init_buffer2: talloc fail\n");
714 memcpy(str->buffer, buf, MIN(str->buf_len, len));
718 /*******************************************************************
719 Reads or writes a BUFFER2 structure.
720 the uni_max_len member tells you how large the buffer is.
721 the uni_str_len member tells you how much of the buffer is really used.
722 ********************************************************************/
724 BOOL smb_io_buffer2(char *desc, BUFFER2 *buf2, uint32 buffer, prs_struct *ps, int depth)
726 if (buf2 == NULL)
727 return False;
729 if (buffer) {
731 prs_debug(ps, depth, desc, "smb_io_buffer2");
732 depth++;
734 if(!prs_align(ps))
735 return False;
737 if(!prs_uint32("uni_max_len", ps, depth, &buf2->buf_max_len))
738 return False;
739 if(!prs_uint32("undoc ", ps, depth, &buf2->undoc))
740 return False;
741 if(!prs_uint32("buf_len ", ps, depth, &buf2->buf_len))
742 return False;
744 /* buffer advanced by indicated length of string
745 NOT by searching for null-termination */
747 if(!prs_buffer2(True, "buffer ", ps, depth, buf2))
748 return False;
750 } else {
752 prs_debug(ps, depth, desc, "smb_io_buffer2 - NULL");
753 depth++;
754 memset((char *)buf2, '\0', sizeof(*buf2));
757 return True;
760 /*******************************************************************
761 creates a UNISTR2 structure: sets up the buffer, too
762 ********************************************************************/
764 void init_buf_unistr2(UNISTR2 *str, uint32 *ptr, const char *buf)
766 if (buf != NULL) {
768 *ptr = 1;
769 init_unistr2(str, buf, strlen(buf)+1);
771 } else {
773 *ptr = 0;
774 init_unistr2(str, "", 0);
779 /*******************************************************************
780 Copies a UNISTR2 structure.
781 ********************************************************************/
783 void copy_unistr2(UNISTR2 *str, const UNISTR2 *from)
786 /* set up string lengths. add one if string is not null-terminated */
787 str->uni_max_len = from->uni_max_len;
788 str->undoc = from->undoc;
789 str->uni_str_len = from->uni_str_len;
791 if (from->buffer == NULL)
792 return;
794 /* the string buffer is allocated to the maximum size
795 (the the length of the source string) to prevent
796 reallocation of memory. */
797 if (str->buffer == NULL) {
798 size_t len = from->uni_max_len * sizeof(uint16);
800 if (len < MAX_UNISTRLEN)
801 len = MAX_UNISTRLEN;
802 len *= sizeof(uint16);
804 str->buffer = (uint16 *)talloc_zero(get_talloc_ctx(), len);
805 if ((str->buffer == NULL) && (len > 0 ))
807 smb_panic("copy_unistr2: talloc fail\n");
808 return;
812 /* copy the string */
813 memcpy(str->buffer, from->buffer, from->uni_max_len*sizeof(uint16));
816 /*******************************************************************
817 Creates a STRING2 structure.
818 ********************************************************************/
820 void init_string2(STRING2 *str, const char *buf, int max_len, int str_len)
822 int alloc_len = 0;
824 /* set up string lengths. */
825 str->str_max_len = max_len;
826 str->undoc = 0;
827 str->str_str_len = str_len;
829 /* store the string */
830 if(str_len != 0) {
831 if (str_len < MAX_STRINGLEN)
832 alloc_len = MAX_STRINGLEN;
833 str->buffer = talloc_zero(get_talloc_ctx(), alloc_len);
834 if (str->buffer == NULL)
835 smb_panic("init_string2: malloc fail\n");
836 memcpy(str->buffer, buf, str_len);
840 /*******************************************************************
841 Reads or writes a STRING2 structure.
842 XXXX NOTE: STRING2 structures need NOT be null-terminated.
843 the str_str_len member tells you how long the string is;
844 the str_max_len member tells you how large the buffer is.
845 ********************************************************************/
847 BOOL smb_io_string2(char *desc, STRING2 *str2, uint32 buffer, prs_struct *ps, int depth)
849 if (str2 == NULL)
850 return False;
852 if (buffer) {
854 prs_debug(ps, depth, desc, "smb_io_string2");
855 depth++;
857 if(!prs_align(ps))
858 return False;
860 if(!prs_uint32("str_max_len", ps, depth, &str2->str_max_len))
861 return False;
862 if(!prs_uint32("undoc ", ps, depth, &str2->undoc))
863 return False;
864 if(!prs_uint32("str_str_len", ps, depth, &str2->str_str_len))
865 return False;
867 /* buffer advanced by indicated length of string
868 NOT by searching for null-termination */
869 if(!prs_string2(True, "buffer ", ps, depth, str2))
870 return False;
872 } else {
874 prs_debug(ps, depth, desc, "smb_io_string2 - NULL");
875 depth++;
876 memset((char *)str2, '\0', sizeof(*str2));
880 return True;
883 /*******************************************************************
884 Inits a UNISTR2 structure.
885 ********************************************************************/
887 void init_unistr2(UNISTR2 *str, const char *buf, size_t len)
889 ZERO_STRUCTP(str);
891 /* set up string lengths. */
892 str->uni_max_len = (uint32)len;
893 str->undoc = 0;
894 str->uni_str_len = (uint32)len;
896 if (len < MAX_UNISTRLEN)
897 len = MAX_UNISTRLEN;
898 len *= sizeof(uint16);
900 str->buffer = (uint16 *)talloc_zero(get_talloc_ctx(), len);
901 if ((str->buffer == NULL) && (len > 0))
903 smb_panic("init_unistr2: malloc fail\n");
904 return;
908 * don't move this test above ! The UNISTR2 must be initialized !!!
909 * jfm, 7/7/2001.
911 if (buf==NULL)
912 return;
914 rpcstr_push((char *)str->buffer, buf, len, STR_TERMINATE);
917 /**
918 * Inits a UNISTR2 structure.
919 * @param ctx talloc context to allocate string on
920 * @param str pointer to string to create
921 * @param buf UCS2 null-terminated buffer to init from
924 void init_unistr2_w(TALLOC_CTX *ctx, UNISTR2 *str, const smb_ucs2_t *buf)
926 uint32 len = strlen_w(buf);
927 uint32 max_len = len;
928 uint32 alloc_len;
930 ZERO_STRUCTP(str);
932 /* set up string lengths. */
933 str->uni_max_len = len;
934 str->undoc = 0;
935 str->uni_str_len = len;
937 if (max_len < MAX_UNISTRLEN)
938 max_len = MAX_UNISTRLEN;
940 alloc_len = (max_len + 1) * sizeof(uint16);
942 str->buffer = (uint16 *)talloc_zero(ctx, alloc_len);
943 if ((str->buffer == NULL) && (alloc_len > 0))
945 smb_panic("init_unistr2_w: malloc fail\n");
946 return;
950 * don't move this test above ! The UNISTR2 must be initialized !!!
951 * jfm, 7/7/2001.
953 if (buf==NULL)
954 return;
956 /* Yes, this is a strncpy( foo, bar, strlen(bar)) - but as
957 long as the buffer above is talloc()ed correctly then this
958 is the correct thing to do */
959 strncpy_w(str->buffer, buf, len + 1);
962 /*******************************************************************
963 Inits a UNISTR2 structure from a UNISTR
964 ********************************************************************/
965 void init_unistr2_from_unistr (UNISTR2 *to, UNISTR *from)
968 uint32 i;
970 /* the destination UNISTR2 should never be NULL.
971 if it is it is a programming error */
973 /* if the source UNISTR is NULL, then zero out
974 the destination string and return */
975 ZERO_STRUCTP (to);
976 if ((from == NULL) || (from->buffer == NULL))
977 return;
979 /* get the length; UNISTR must be NULL terminated */
980 i = 0;
981 while ((from->buffer)[i]!='\0')
982 i++;
983 i++; /* one more to catch the terminating NULL */
984 /* is this necessary -- jerry? I need to think */
986 /* set up string lengths; uni_max_len is set to i+1
987 because we need to account for the final NULL termination */
988 to->uni_max_len = i;
989 to->undoc = 0;
990 to->uni_str_len = i;
992 /* allocate the space and copy the string buffer */
993 to->buffer = (uint16 *)talloc_zero(get_talloc_ctx(), sizeof(uint16)*(to->uni_str_len));
994 if (to->buffer == NULL)
995 smb_panic("init_unistr2_from_unistr: malloc fail\n");
996 memcpy(to->buffer, from->buffer, to->uni_max_len*sizeof(uint16));
998 return;
1002 /*******************************************************************
1003 Reads or writes a UNISTR2 structure.
1004 XXXX NOTE: UNISTR2 structures need NOT be null-terminated.
1005 the uni_str_len member tells you how long the string is;
1006 the uni_max_len member tells you how large the buffer is.
1007 ********************************************************************/
1009 BOOL smb_io_unistr2(char *desc, UNISTR2 *uni2, uint32 buffer, prs_struct *ps, int depth)
1011 if (uni2 == NULL)
1012 return False;
1014 if (buffer) {
1016 prs_debug(ps, depth, desc, "smb_io_unistr2");
1017 depth++;
1019 if(!prs_align(ps))
1020 return False;
1022 if(!prs_uint32("uni_max_len", ps, depth, &uni2->uni_max_len))
1023 return False;
1024 if(!prs_uint32("undoc ", ps, depth, &uni2->undoc))
1025 return False;
1026 if(!prs_uint32("uni_str_len", ps, depth, &uni2->uni_str_len))
1027 return False;
1029 /* buffer advanced by indicated length of string
1030 NOT by searching for null-termination */
1031 if(!prs_unistr2(True, "buffer ", ps, depth, uni2))
1032 return False;
1034 } else {
1036 prs_debug(ps, depth, desc, "smb_io_unistr2 - NULL");
1037 depth++;
1038 memset((char *)uni2, '\0', sizeof(*uni2));
1042 return True;
1045 /*******************************************************************
1046 Inits a DOM_RID2 structure.
1047 ********************************************************************/
1049 void init_dom_rid2(DOM_RID2 *rid2, uint32 rid, uint8 type, uint32 idx)
1051 rid2->type = type;
1052 rid2->rid = rid;
1053 rid2->rid_idx = idx;
1056 /*******************************************************************
1057 Reads or writes a DOM_RID2 structure.
1058 ********************************************************************/
1060 BOOL smb_io_dom_rid2(char *desc, DOM_RID2 *rid2, prs_struct *ps, int depth)
1062 if (rid2 == NULL)
1063 return False;
1065 prs_debug(ps, depth, desc, "smb_io_dom_rid2");
1066 depth++;
1068 if(!prs_align(ps))
1069 return False;
1071 if(!prs_uint8("type ", ps, depth, &rid2->type))
1072 return False;
1073 if(!prs_align(ps))
1074 return False;
1075 if(!prs_uint32("rid ", ps, depth, &rid2->rid))
1076 return False;
1077 if(!prs_uint32("rid_idx", ps, depth, &rid2->rid_idx))
1078 return False;
1080 return True;
1083 /*******************************************************************
1084 creates a DOM_RID3 structure.
1085 ********************************************************************/
1087 void init_dom_rid3(DOM_RID3 *rid3, uint32 rid, uint8 type)
1089 rid3->rid = rid;
1090 rid3->type1 = type;
1091 rid3->ptr_type = 0x1; /* non-zero, basically. */
1092 rid3->type2 = 0x1;
1093 rid3->unk = type;
1096 /*******************************************************************
1097 reads or writes a DOM_RID3 structure.
1098 ********************************************************************/
1100 BOOL smb_io_dom_rid3(char *desc, DOM_RID3 *rid3, prs_struct *ps, int depth)
1102 if (rid3 == NULL)
1103 return False;
1105 prs_debug(ps, depth, desc, "smb_io_dom_rid3");
1106 depth++;
1108 if(!prs_align(ps))
1109 return False;
1111 if(!prs_uint32("rid ", ps, depth, &rid3->rid))
1112 return False;
1113 if(!prs_uint32("type1 ", ps, depth, &rid3->type1))
1114 return False;
1115 if(!prs_uint32("ptr_type", ps, depth, &rid3->ptr_type))
1116 return False;
1117 if(!prs_uint32("type2 ", ps, depth, &rid3->type2))
1118 return False;
1119 if(!prs_uint32("unk ", ps, depth, &rid3->unk))
1120 return False;
1122 return True;
1125 /*******************************************************************
1126 Inits a DOM_RID4 structure.
1127 ********************************************************************/
1129 void init_dom_rid4(DOM_RID4 *rid4, uint16 unknown, uint16 attr, uint32 rid)
1131 rid4->unknown = unknown;
1132 rid4->attr = attr;
1133 rid4->rid = rid;
1136 /*******************************************************************
1137 Inits a DOM_CLNT_SRV structure.
1138 ********************************************************************/
1140 static void init_clnt_srv(DOM_CLNT_SRV *log, char *logon_srv, char *comp_name)
1142 DEBUG(5,("init_clnt_srv: %d\n", __LINE__));
1144 if (logon_srv != NULL) {
1145 log->undoc_buffer = 1;
1146 init_unistr2(&log->uni_logon_srv, logon_srv, strlen(logon_srv)+1);
1147 } else {
1148 log->undoc_buffer = 0;
1151 if (comp_name != NULL) {
1152 log->undoc_buffer2 = 1;
1153 init_unistr2(&log->uni_comp_name, comp_name, strlen(comp_name)+1);
1154 } else {
1155 log->undoc_buffer2 = 0;
1159 /*******************************************************************
1160 Inits or writes a DOM_CLNT_SRV structure.
1161 ********************************************************************/
1163 static BOOL smb_io_clnt_srv(char *desc, DOM_CLNT_SRV *log, prs_struct *ps, int depth)
1165 if (log == NULL)
1166 return False;
1168 prs_debug(ps, depth, desc, "smb_io_clnt_srv");
1169 depth++;
1171 if(!prs_align(ps))
1172 return False;
1174 if(!prs_uint32("undoc_buffer ", ps, depth, &log->undoc_buffer))
1175 return False;
1177 if (log->undoc_buffer != 0) {
1178 if(!smb_io_unistr2("unistr2", &log->uni_logon_srv, log->undoc_buffer, ps, depth))
1179 return False;
1182 if(!prs_align(ps))
1183 return False;
1185 if(!prs_uint32("undoc_buffer2", ps, depth, &log->undoc_buffer2))
1186 return False;
1188 if (log->undoc_buffer2 != 0) {
1189 if(!smb_io_unistr2("unistr2", &log->uni_comp_name, log->undoc_buffer2, ps, depth))
1190 return False;
1193 return True;
1196 /*******************************************************************
1197 Inits a DOM_LOG_INFO structure.
1198 ********************************************************************/
1200 void init_log_info(DOM_LOG_INFO *log, const char *logon_srv, const char *acct_name,
1201 uint16 sec_chan, const char *comp_name)
1203 DEBUG(5,("make_log_info %d\n", __LINE__));
1205 log->undoc_buffer = 1;
1207 init_unistr2(&log->uni_logon_srv, logon_srv, strlen(logon_srv)+1);
1208 init_unistr2(&log->uni_acct_name, acct_name, strlen(acct_name)+1);
1210 log->sec_chan = sec_chan;
1212 init_unistr2(&log->uni_comp_name, comp_name, strlen(comp_name)+1);
1215 /*******************************************************************
1216 Reads or writes a DOM_LOG_INFO structure.
1217 ********************************************************************/
1219 BOOL smb_io_log_info(char *desc, DOM_LOG_INFO *log, prs_struct *ps, int depth)
1221 if (log == NULL)
1222 return False;
1224 prs_debug(ps, depth, desc, "smb_io_log_info");
1225 depth++;
1227 if(!prs_align(ps))
1228 return False;
1230 if(!prs_uint32("undoc_buffer", ps, depth, &log->undoc_buffer))
1231 return False;
1233 if(!smb_io_unistr2("unistr2", &log->uni_logon_srv, True, ps, depth))
1234 return False;
1235 if(!smb_io_unistr2("unistr2", &log->uni_acct_name, True, ps, depth))
1236 return False;
1238 if(!prs_uint16("sec_chan", ps, depth, &log->sec_chan))
1239 return False;
1241 if(!smb_io_unistr2("unistr2", &log->uni_comp_name, True, ps, depth))
1242 return False;
1244 return True;
1247 /*******************************************************************
1248 Reads or writes a DOM_CHAL structure.
1249 ********************************************************************/
1251 BOOL smb_io_chal(char *desc, DOM_CHAL *chal, prs_struct *ps, int depth)
1253 if (chal == NULL)
1254 return False;
1256 prs_debug(ps, depth, desc, "smb_io_chal");
1257 depth++;
1259 if(!prs_align(ps))
1260 return False;
1262 if(!prs_uint8s (False, "data", ps, depth, chal->data, 8))
1263 return False;
1265 return True;
1268 /*******************************************************************
1269 Reads or writes a DOM_CRED structure.
1270 ********************************************************************/
1272 BOOL smb_io_cred(char *desc, DOM_CRED *cred, prs_struct *ps, int depth)
1274 if (cred == NULL)
1275 return False;
1277 prs_debug(ps, depth, desc, "smb_io_cred");
1278 depth++;
1280 if(!prs_align(ps))
1281 return False;
1283 if(!smb_io_chal ("", &cred->challenge, ps, depth))
1284 return False;
1286 if(!smb_io_utime("", &cred->timestamp, ps, depth))
1287 return False;
1289 return True;
1292 /*******************************************************************
1293 Inits a DOM_CLNT_INFO2 structure.
1294 ********************************************************************/
1296 void init_clnt_info2(DOM_CLNT_INFO2 *clnt,
1297 char *logon_srv, char *comp_name,
1298 DOM_CRED *clnt_cred)
1300 DEBUG(5,("make_clnt_info: %d\n", __LINE__));
1302 init_clnt_srv(&(clnt->login), logon_srv, comp_name);
1304 if (clnt_cred != NULL) {
1305 clnt->ptr_cred = 1;
1306 memcpy(&(clnt->cred), clnt_cred, sizeof(clnt->cred));
1307 } else {
1308 clnt->ptr_cred = 0;
1312 /*******************************************************************
1313 Reads or writes a DOM_CLNT_INFO2 structure.
1314 ********************************************************************/
1316 BOOL smb_io_clnt_info2(char *desc, DOM_CLNT_INFO2 *clnt, prs_struct *ps, int depth)
1318 if (clnt == NULL)
1319 return False;
1321 prs_debug(ps, depth, desc, "smb_io_clnt_info2");
1322 depth++;
1324 if(!prs_align(ps))
1325 return False;
1327 if(!smb_io_clnt_srv("", &clnt->login, ps, depth))
1328 return False;
1330 if(!prs_align(ps))
1331 return False;
1333 if(!prs_uint32("ptr_cred", ps, depth, &clnt->ptr_cred))
1334 return False;
1335 if(!smb_io_cred("", &clnt->cred, ps, depth))
1336 return False;
1338 return True;
1341 /*******************************************************************
1342 Inits a DOM_CLNT_INFO structure.
1343 ********************************************************************/
1345 void init_clnt_info(DOM_CLNT_INFO *clnt,
1346 char *logon_srv, char *acct_name,
1347 uint16 sec_chan, char *comp_name,
1348 DOM_CRED *cred)
1350 DEBUG(5,("make_clnt_info\n"));
1352 init_log_info(&clnt->login, logon_srv, acct_name, sec_chan, comp_name);
1353 memcpy(&clnt->cred, cred, sizeof(clnt->cred));
1356 /*******************************************************************
1357 Reads or writes a DOM_CLNT_INFO structure.
1358 ********************************************************************/
1360 BOOL smb_io_clnt_info(char *desc, DOM_CLNT_INFO *clnt, prs_struct *ps, int depth)
1362 if (clnt == NULL)
1363 return False;
1365 prs_debug(ps, depth, desc, "smb_io_clnt_info");
1366 depth++;
1368 if(!prs_align(ps))
1369 return False;
1371 if(!smb_io_log_info("", &clnt->login, ps, depth))
1372 return False;
1373 if(!smb_io_cred("", &clnt->cred, ps, depth))
1374 return False;
1376 return True;
1379 /*******************************************************************
1380 Inits a DOM_LOGON_ID structure.
1381 ********************************************************************/
1383 void init_logon_id(DOM_LOGON_ID *log, uint32 log_id_low, uint32 log_id_high)
1385 DEBUG(5,("make_logon_id: %d\n", __LINE__));
1387 log->low = log_id_low;
1388 log->high = log_id_high;
1391 /*******************************************************************
1392 Reads or writes a DOM_LOGON_ID structure.
1393 ********************************************************************/
1395 BOOL smb_io_logon_id(char *desc, DOM_LOGON_ID *log, prs_struct *ps, int depth)
1397 if (log == NULL)
1398 return False;
1400 prs_debug(ps, depth, desc, "smb_io_logon_id");
1401 depth++;
1403 if(!prs_align(ps))
1404 return False;
1406 if(!prs_uint32("low ", ps, depth, &log->low ))
1407 return False;
1408 if(!prs_uint32("high", ps, depth, &log->high))
1409 return False;
1411 return True;
1414 /*******************************************************************
1415 Inits an OWF_INFO structure.
1416 ********************************************************************/
1418 void init_owf_info(OWF_INFO *hash, uint8 data[16])
1420 DEBUG(5,("init_owf_info: %d\n", __LINE__));
1422 if (data != NULL)
1423 memcpy(hash->data, data, sizeof(hash->data));
1424 else
1425 memset((char *)hash->data, '\0', sizeof(hash->data));
1428 /*******************************************************************
1429 Reads or writes an OWF_INFO structure.
1430 ********************************************************************/
1432 BOOL smb_io_owf_info(char *desc, OWF_INFO *hash, prs_struct *ps, int depth)
1434 if (hash == NULL)
1435 return False;
1437 prs_debug(ps, depth, desc, "smb_io_owf_info");
1438 depth++;
1440 if(!prs_align(ps))
1441 return False;
1443 if(!prs_uint8s (False, "data", ps, depth, hash->data, 16))
1444 return False;
1446 return True;
1449 /*******************************************************************
1450 Reads or writes a DOM_GID structure.
1451 ********************************************************************/
1453 BOOL smb_io_gid(char *desc, DOM_GID *gid, prs_struct *ps, int depth)
1455 if (gid == NULL)
1456 return False;
1458 prs_debug(ps, depth, desc, "smb_io_gid");
1459 depth++;
1461 if(!prs_align(ps))
1462 return False;
1464 if(!prs_uint32("g_rid", ps, depth, &gid->g_rid))
1465 return False;
1466 if(!prs_uint32("attr ", ps, depth, &gid->attr))
1467 return False;
1469 return True;
1472 /*******************************************************************
1473 Reads or writes an POLICY_HND structure.
1474 ********************************************************************/
1476 BOOL smb_io_pol_hnd(char *desc, POLICY_HND *pol, prs_struct *ps, int depth)
1478 if (pol == NULL)
1479 return False;
1481 prs_debug(ps, depth, desc, "smb_io_pol_hnd");
1482 depth++;
1484 if(!prs_align(ps))
1485 return False;
1487 if(UNMARSHALLING(ps))
1488 ZERO_STRUCTP(pol);
1490 if (!prs_uint32("data1", ps, depth, &pol->data1))
1491 return False;
1492 if (!prs_uint32("data2", ps, depth, &pol->data2))
1493 return False;
1494 if (!prs_uint16("data3", ps, depth, &pol->data3))
1495 return False;
1496 if (!prs_uint16("data4", ps, depth, &pol->data4))
1497 return False;
1498 if(!prs_uint8s (False, "data5", ps, depth, pol->data5, sizeof(pol->data5)))
1499 return False;
1501 return True;
1504 /*******************************************************************
1505 Create a UNISTR3.
1506 ********************************************************************/
1508 void init_unistr3(UNISTR3 *str, const char *buf)
1510 size_t len;
1512 if (buf == NULL) {
1513 str->uni_str_len=0;
1514 str->str.buffer = NULL;
1515 return;
1518 len = strlen(buf) + 1;
1520 str->uni_str_len=len;
1522 if (len < MAX_UNISTRLEN)
1523 len = MAX_UNISTRLEN;
1525 len *= sizeof(uint16);
1527 str->str.buffer = (uint16 *)talloc_zero(get_talloc_ctx(), len);
1528 if (str->str.buffer == NULL)
1529 smb_panic("init_unistr3: malloc fail\n");
1531 rpcstr_push((char *)str->str.buffer, buf, len, STR_TERMINATE);
1534 /*******************************************************************
1535 Reads or writes a UNISTR3 structure.
1536 ********************************************************************/
1538 BOOL smb_io_unistr3(char *desc, UNISTR3 *name, prs_struct *ps, int depth)
1540 if (name == NULL)
1541 return False;
1543 prs_debug(ps, depth, desc, "smb_io_unistr3");
1544 depth++;
1546 if(!prs_align(ps))
1547 return False;
1549 if(!prs_uint32("uni_str_len", ps, depth, &name->uni_str_len))
1550 return False;
1552 /* don't know if len is specified by uni_str_len member... */
1553 /* assume unicode string is unicode-null-terminated, instead */
1555 if(!prs_unistr3(True, "unistr", name, ps, depth))
1556 return False;
1558 return True;
1562 /*******************************************************************
1563 Stream a uint64_struct
1564 ********************************************************************/
1565 BOOL prs_uint64(char *name, prs_struct *ps, int depth, UINT64_S *data64)
1567 return prs_uint32(name, ps, depth+1, &data64->low) &&
1568 prs_uint32(name, ps, depth+1, &data64->high);
1571 /*******************************************************************
1572 reads or writes a BUFHDR2 structure.
1573 ********************************************************************/
1574 BOOL smb_io_bufhdr2(char *desc, BUFHDR2 *hdr, prs_struct *ps, int depth)
1576 prs_debug(ps, depth, desc, "smb_io_bufhdr2");
1577 depth++;
1579 prs_align(ps);
1580 prs_uint32("info_level", ps, depth, &(hdr->info_level));
1581 prs_uint32("length ", ps, depth, &(hdr->length ));
1582 prs_uint32("buffer ", ps, depth, &(hdr->buffer ));
1584 return True;
1587 /*******************************************************************
1588 reads or writes a BUFFER4 structure.
1589 ********************************************************************/
1590 BOOL smb_io_buffer4(char *desc, BUFFER4 *buf4, uint32 buffer, prs_struct *ps, int depth)
1592 prs_debug(ps, depth, desc, "smb_io_buffer4");
1593 depth++;
1595 prs_align(ps);
1596 prs_uint32("buf_len", ps, depth, &(buf4->buf_len));
1598 if (buf4->buf_len > MAX_BUFFERLEN)
1600 buf4->buf_len = MAX_BUFFERLEN;
1603 prs_uint8s(True, "buffer", ps, depth, buf4->buffer, buf4->buf_len);
1605 return True;
1608 /*******************************************************************
1609 creates a UNIHDR structure.
1610 ********************************************************************/
1612 BOOL make_uni_hdr(UNIHDR *hdr, int len)
1614 if (hdr == NULL)
1616 return False;
1618 hdr->uni_str_len = 2 * len;
1619 hdr->uni_max_len = 2 * len;
1620 hdr->buffer = len != 0 ? 1 : 0;
1622 return True;
1625 /*******************************************************************
1626 creates a BUFHDR2 structure.
1627 ********************************************************************/
1628 BOOL make_bufhdr2(BUFHDR2 *hdr, uint32 info_level, uint32 length, uint32 buffer)
1630 hdr->info_level = info_level;
1631 hdr->length = length;
1632 hdr->buffer = buffer;
1634 return True;