• Home
  • History
  • Annotate
  • Line#
  • Navigate
  • Raw
  • Download
  • only in /asuswrt-rt-n18u-9.0.0.4.380.2695/release/src-rt-6.x.4708/router/samba-3.5.8/source3/libsmb/
1/*
2   Unix SMB/CIFS implementation.
3   NBT netbios library routines
4   Copyright (C) Andrew Tridgell 1994-1998
5   Copyright (C) Jeremy Allison 2007
6
7   This program is free software; you can redistribute it and/or modify
8   it under the terms of the GNU General Public License as published by
9   the Free Software Foundation; either version 3 of the License, or
10   (at your option) any later version.
11
12   This program is distributed in the hope that it will be useful,
13   but WITHOUT ANY WARRANTY; without even the implied warranty of
14   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15   GNU General Public License for more details.
16
17   You should have received a copy of the GNU General Public License
18   along with this program.  If not, see <http://www.gnu.org/licenses/>.
19
20*/
21
22#include "includes.h"
23
24static const struct opcode_names {
25	const char *nmb_opcode_name;
26	int opcode;
27} nmb_header_opcode_names[] = {
28	{"Query",           0 },
29	{"Registration",      5 },
30	{"Release",           6 },
31	{"WACK",              7 },
32	{"Refresh",           8 },
33	{"Refresh(altcode)",  9 },
34	{"Multi-homed Registration", 15 },
35	{0, -1 }
36};
37
38/****************************************************************************
39 Lookup a nmb opcode name.
40****************************************************************************/
41
42static const char *lookup_opcode_name( int opcode )
43{
44	const struct opcode_names *op_namep;
45	int i;
46
47	for(i = 0; nmb_header_opcode_names[i].nmb_opcode_name != 0; i++) {
48		op_namep = &nmb_header_opcode_names[i];
49		if(opcode == op_namep->opcode)
50			return op_namep->nmb_opcode_name;
51	}
52	return "<unknown opcode>";
53}
54
55/****************************************************************************
56 Print out a res_rec structure.
57****************************************************************************/
58
59static void debug_nmb_res_rec(struct res_rec *res, const char *hdr)
60{
61	int i, j;
62
63	DEBUGADD( 4, ( "    %s: nmb_name=%s rr_type=%d rr_class=%d ttl=%d\n",
64		hdr,
65		nmb_namestr(&res->rr_name),
66		res->rr_type,
67		res->rr_class,
68		res->ttl ) );
69
70	if( res->rdlength == 0 || res->rdata == NULL )
71		return;
72
73	for (i = 0; i < res->rdlength; i+= MAX_NETBIOSNAME_LEN) {
74		DEBUGADD(4, ("    %s %3x char ", hdr, i));
75
76		for (j = 0; j < MAX_NETBIOSNAME_LEN; j++) {
77			unsigned char x = res->rdata[i+j];
78			if (x < 32 || x > 127)
79				x = '.';
80
81			if (i+j >= res->rdlength)
82				break;
83			DEBUGADD(4, ("%c", x));
84		}
85
86		DEBUGADD(4, ("   hex "));
87
88		for (j = 0; j < MAX_NETBIOSNAME_LEN; j++) {
89			if (i+j >= res->rdlength)
90				break;
91			DEBUGADD(4, ("%02X", (unsigned char)res->rdata[i+j]));
92		}
93
94		DEBUGADD(4, ("\n"));
95	}
96}
97
98/****************************************************************************
99 Process a nmb packet.
100****************************************************************************/
101
102void debug_nmb_packet(struct packet_struct *p)
103{
104	struct nmb_packet *nmb = &p->packet.nmb;
105
106	if( DEBUGLVL( 4 ) ) {
107		dbgtext( "nmb packet from %s(%d) header: id=%d "
108				"opcode=%s(%d) response=%s\n",
109			inet_ntoa(p->ip), p->port,
110			nmb->header.name_trn_id,
111			lookup_opcode_name(nmb->header.opcode),
112			nmb->header.opcode,
113			BOOLSTR(nmb->header.response) );
114		dbgtext( "    header: flags: bcast=%s rec_avail=%s "
115				"rec_des=%s trunc=%s auth=%s\n",
116			BOOLSTR(nmb->header.nm_flags.bcast),
117			BOOLSTR(nmb->header.nm_flags.recursion_available),
118			BOOLSTR(nmb->header.nm_flags.recursion_desired),
119			BOOLSTR(nmb->header.nm_flags.trunc),
120			BOOLSTR(nmb->header.nm_flags.authoritative) );
121		dbgtext( "    header: rcode=%d qdcount=%d ancount=%d "
122				"nscount=%d arcount=%d\n",
123			nmb->header.rcode,
124			nmb->header.qdcount,
125			nmb->header.ancount,
126			nmb->header.nscount,
127			nmb->header.arcount );
128	}
129
130	if (nmb->header.qdcount) {
131		DEBUGADD( 4, ( "    question: q_name=%s q_type=%d q_class=%d\n",
132			nmb_namestr(&nmb->question.question_name),
133			nmb->question.question_type,
134			nmb->question.question_class) );
135	}
136
137	if (nmb->answers && nmb->header.ancount) {
138		debug_nmb_res_rec(nmb->answers,"answers");
139	}
140	if (nmb->nsrecs && nmb->header.nscount) {
141		debug_nmb_res_rec(nmb->nsrecs,"nsrecs");
142	}
143	if (nmb->additional && nmb->header.arcount) {
144		debug_nmb_res_rec(nmb->additional,"additional");
145	}
146}
147
148/*******************************************************************
149 Handle "compressed" name pointers.
150******************************************************************/
151
152static bool handle_name_ptrs(unsigned char *ubuf,int *offset,int length,
153			     bool *got_pointer,int *ret)
154{
155	int loop_count=0;
156
157	while ((ubuf[*offset] & 0xC0) == 0xC0) {
158		if (!*got_pointer)
159			(*ret) += 2;
160		(*got_pointer)=True;
161		(*offset) = ((ubuf[*offset] & ~0xC0)<<8) | ubuf[(*offset)+1];
162		if (loop_count++ == 10 ||
163				(*offset) < 0 || (*offset)>(length-2)) {
164			return False;
165		}
166	}
167	return True;
168}
169
170/*******************************************************************
171 Parse a nmb name from "compressed" format to something readable
172 return the space taken by the name, or 0 if the name is invalid
173******************************************************************/
174
175static int parse_nmb_name(char *inbuf,int ofs,int length, struct nmb_name *name)
176{
177	int m,n=0;
178	unsigned char *ubuf = (unsigned char *)inbuf;
179	int ret = 0;
180	bool got_pointer=False;
181	int loop_count=0;
182	int offset = ofs;
183
184	if (length - offset < 2)
185		return(0);
186
187	/* handle initial name pointers */
188	if (!handle_name_ptrs(ubuf,&offset,length,&got_pointer,&ret))
189		return(0);
190
191	m = ubuf[offset];
192
193	if (!m)
194		return(0);
195	if ((m & 0xC0) || offset+m+2 > length)
196		return(0);
197
198	memset((char *)name,'\0',sizeof(*name));
199
200	/* the "compressed" part */
201	if (!got_pointer)
202		ret += m + 2;
203	offset++;
204	while (m > 0) {
205		unsigned char c1,c2;
206		c1 = ubuf[offset++]-'A';
207		c2 = ubuf[offset++]-'A';
208		if ((c1 & 0xF0) || (c2 & 0xF0) || (n > sizeof(name->name)-1))
209			return(0);
210		name->name[n++] = (c1<<4) | c2;
211		m -= 2;
212	}
213	name->name[n] = 0;
214
215	if (n==MAX_NETBIOSNAME_LEN) {
216		/* parse out the name type, its always
217		 * in the 16th byte of the name */
218		name->name_type = ((unsigned char)name->name[15]) & 0xff;
219
220		/* remove trailing spaces */
221		name->name[15] = 0;
222		n = 14;
223		while (n && name->name[n]==' ')
224			name->name[n--] = 0;
225	}
226
227	/* now the domain parts (if any) */
228	n = 0;
229	while (ubuf[offset]) {
230		/* we can have pointers within the domain part as well */
231		if (!handle_name_ptrs(ubuf,&offset,length,&got_pointer,&ret))
232			return(0);
233
234		m = ubuf[offset];
235		/*
236		 * Don't allow null domain parts.
237		 */
238		if (!m)
239			return(0);
240		if (!got_pointer)
241			ret += m+1;
242		if (n)
243			name->scope[n++] = '.';
244		if (m+2+offset>length || n+m+1>sizeof(name->scope))
245			return(0);
246		offset++;
247		while (m--)
248			name->scope[n++] = (char)ubuf[offset++];
249
250		/*
251		 * Watch for malicious loops.
252		 */
253		if (loop_count++ == 10)
254			return 0;
255	}
256	name->scope[n++] = 0;
257
258	return(ret);
259}
260
261/****************************************************************************
262 Put a netbios name, padding(s) and a name type into a 16 character buffer.
263 name is already in DOS charset.
264 [15 bytes name + padding][1 byte name type].
265****************************************************************************/
266
267void put_name(char *dest, const char *name, int pad, unsigned int name_type)
268{
269	size_t len = strlen(name);
270
271	memcpy(dest, name, (len < MAX_NETBIOSNAME_LEN) ?
272			len : MAX_NETBIOSNAME_LEN - 1);
273	if (len < MAX_NETBIOSNAME_LEN - 1) {
274		memset(dest + len, pad, MAX_NETBIOSNAME_LEN - 1 - len);
275	}
276	dest[MAX_NETBIOSNAME_LEN - 1] = name_type;
277}
278
279/*******************************************************************
280 Put a compressed nmb name into a buffer. Return the length of the
281 compressed name.
282
283 Compressed names are really weird. The "compression" doubles the
284 size. The idea is that it also means that compressed names conform
285 to the doman name system. See RFC1002.
286
287 If buf == NULL this is a length calculation.
288******************************************************************/
289
290static int put_nmb_name(char *buf,int offset,struct nmb_name *name)
291{
292	int ret,m;
293	nstring buf1;
294	char *p;
295
296	if (strcmp(name->name,"*") == 0) {
297		/* special case for wildcard name */
298		put_name(buf1, "*", '\0', name->name_type);
299	} else {
300		put_name(buf1, name->name, ' ', name->name_type);
301	}
302
303	if (buf) {
304		buf[offset] = 0x20;
305	}
306
307	ret = 34;
308
309	for (m=0;m<MAX_NETBIOSNAME_LEN;m++) {
310		if (buf) {
311			buf[offset+1+2*m] = 'A' + ((buf1[m]>>4)&0xF);
312			buf[offset+2+2*m] = 'A' + (buf1[m]&0xF);
313		}
314	}
315	offset += 33;
316
317	if (buf) {
318		buf[offset] = 0;
319	}
320
321	if (name->scope[0]) {
322		/* XXXX this scope handling needs testing */
323		ret += strlen(name->scope) + 1;
324		if (buf) {
325			safe_strcpy(&buf[offset+1],name->scope,
326					sizeof(name->scope));
327
328			p = &buf[offset+1];
329			while ((p = strchr_m(p,'.'))) {
330				buf[offset] = PTR_DIFF(p,&buf[offset+1]);
331				offset += (buf[offset] + 1);
332				p = &buf[offset+1];
333			}
334			buf[offset] = strlen(&buf[offset+1]);
335		}
336	}
337
338	return ret;
339}
340
341/*******************************************************************
342 Useful for debugging messages.
343******************************************************************/
344
345char *nmb_namestr(const struct nmb_name *n)
346{
347	fstring name;
348	char *result;
349
350	pull_ascii_fstring(name, n->name);
351	if (!n->scope[0])
352		result = talloc_asprintf(talloc_tos(), "%s<%02x>", name,
353					 n->name_type);
354	else
355		result = talloc_asprintf(talloc_tos(), "%s<%02x>.%s", name,
356					 n->name_type, n->scope);
357
358	SMB_ASSERT(result != NULL);
359	return result;
360}
361
362/*******************************************************************
363 Allocate and parse some resource records.
364******************************************************************/
365
366static bool parse_alloc_res_rec(char *inbuf,int *offset,int length,
367				struct res_rec **recs, int count)
368{
369	int i;
370
371	*recs = SMB_MALLOC_ARRAY(struct res_rec, count);
372	if (!*recs)
373		return(False);
374
375	memset((char *)*recs,'\0',sizeof(**recs)*count);
376
377	for (i=0;i<count;i++) {
378		int l = parse_nmb_name(inbuf,*offset,length,
379				&(*recs)[i].rr_name);
380		(*offset) += l;
381		if (!l || (*offset)+10 > length) {
382			SAFE_FREE(*recs);
383			return(False);
384		}
385		(*recs)[i].rr_type = RSVAL(inbuf,(*offset));
386		(*recs)[i].rr_class = RSVAL(inbuf,(*offset)+2);
387		(*recs)[i].ttl = RIVAL(inbuf,(*offset)+4);
388		(*recs)[i].rdlength = RSVAL(inbuf,(*offset)+8);
389		(*offset) += 10;
390		if ((*recs)[i].rdlength>sizeof((*recs)[i].rdata) ||
391				(*offset)+(*recs)[i].rdlength > length) {
392			SAFE_FREE(*recs);
393			return(False);
394		}
395		memcpy((*recs)[i].rdata,inbuf+(*offset),(*recs)[i].rdlength);
396		(*offset) += (*recs)[i].rdlength;
397	}
398	return(True);
399}
400
401/*******************************************************************
402 Put a resource record into a packet.
403 If buf == NULL this is a length calculation.
404******************************************************************/
405
406static int put_res_rec(char *buf,int offset,struct res_rec *recs,int count)
407{
408	int ret=0;
409	int i;
410
411	for (i=0;i<count;i++) {
412		int l = put_nmb_name(buf,offset,&recs[i].rr_name);
413		offset += l;
414		ret += l;
415		if (buf) {
416			RSSVAL(buf,offset,recs[i].rr_type);
417			RSSVAL(buf,offset+2,recs[i].rr_class);
418			RSIVAL(buf,offset+4,recs[i].ttl);
419			RSSVAL(buf,offset+8,recs[i].rdlength);
420			memcpy(buf+offset+10,recs[i].rdata,recs[i].rdlength);
421		}
422		offset += 10+recs[i].rdlength;
423		ret += 10+recs[i].rdlength;
424	}
425
426	return ret;
427}
428
429/*******************************************************************
430 Put a compressed name pointer record into a packet.
431 If buf == NULL this is a length calculation.
432******************************************************************/
433
434static int put_compressed_name_ptr(unsigned char *buf,
435				int offset,
436				struct res_rec *rec,
437				int ptr_offset)
438{
439	int ret=0;
440	if (buf) {
441		buf[offset] = (0xC0 | ((ptr_offset >> 8) & 0xFF));
442		buf[offset+1] = (ptr_offset & 0xFF);
443	}
444	offset += 2;
445	ret += 2;
446	if (buf) {
447		RSSVAL(buf,offset,rec->rr_type);
448		RSSVAL(buf,offset+2,rec->rr_class);
449		RSIVAL(buf,offset+4,rec->ttl);
450		RSSVAL(buf,offset+8,rec->rdlength);
451		memcpy(buf+offset+10,rec->rdata,rec->rdlength);
452	}
453	offset += 10+rec->rdlength;
454	ret += 10+rec->rdlength;
455
456	return ret;
457}
458
459/*******************************************************************
460 Parse a dgram packet. Return False if the packet can't be parsed
461 or is invalid for some reason, True otherwise.
462
463 This is documented in section 4.4.1 of RFC1002.
464******************************************************************/
465
466static bool parse_dgram(char *inbuf,int length,struct dgram_packet *dgram)
467{
468	int offset;
469	int flags;
470
471	memset((char *)dgram,'\0',sizeof(*dgram));
472
473	if (length < 14)
474		return(False);
475
476	dgram->header.msg_type = CVAL(inbuf,0);
477	flags = CVAL(inbuf,1);
478	dgram->header.flags.node_type = (enum node_type)((flags>>2)&3);
479	if (flags & 1)
480		dgram->header.flags.more = True;
481	if (flags & 2)
482		dgram->header.flags.first = True;
483	dgram->header.dgm_id = RSVAL(inbuf,2);
484	putip((char *)&dgram->header.source_ip,inbuf+4);
485	dgram->header.source_port = RSVAL(inbuf,8);
486	dgram->header.dgm_length = RSVAL(inbuf,10);
487	dgram->header.packet_offset = RSVAL(inbuf,12);
488
489	offset = 14;
490
491	if (dgram->header.msg_type == 0x10 ||
492			dgram->header.msg_type == 0x11 ||
493			dgram->header.msg_type == 0x12) {
494		offset += parse_nmb_name(inbuf,offset,length,
495				&dgram->source_name);
496		offset += parse_nmb_name(inbuf,offset,length,
497				&dgram->dest_name);
498	}
499
500	if (offset >= length || (length-offset > sizeof(dgram->data)))
501		return(False);
502
503	dgram->datasize = length-offset;
504	memcpy(dgram->data,inbuf+offset,dgram->datasize);
505
506	/* Paranioa. Ensure the last 2 bytes in the dgram buffer are
507	   zero. This should be true anyway, just enforce it for
508	   paranioa sake. JRA. */
509	SMB_ASSERT(dgram->datasize <= (sizeof(dgram->data)-2));
510	memset(&dgram->data[sizeof(dgram->data)-2], '\0', 2);
511
512	return(True);
513}
514
515/*******************************************************************
516 Parse a nmb packet. Return False if the packet can't be parsed
517 or is invalid for some reason, True otherwise.
518******************************************************************/
519
520static bool parse_nmb(char *inbuf,int length,struct nmb_packet *nmb)
521{
522	int nm_flags,offset;
523
524	memset((char *)nmb,'\0',sizeof(*nmb));
525
526	if (length < 12)
527		return(False);
528
529	/* parse the header */
530	nmb->header.name_trn_id = RSVAL(inbuf,0);
531
532	DEBUG(10,("parse_nmb: packet id = %d\n", nmb->header.name_trn_id));
533
534	nmb->header.opcode = (CVAL(inbuf,2) >> 3) & 0xF;
535	nmb->header.response = ((CVAL(inbuf,2)>>7)&1)?True:False;
536	nm_flags = ((CVAL(inbuf,2) & 0x7) << 4) + (CVAL(inbuf,3)>>4);
537	nmb->header.nm_flags.bcast = (nm_flags&1)?True:False;
538	nmb->header.nm_flags.recursion_available = (nm_flags&8)?True:False;
539	nmb->header.nm_flags.recursion_desired = (nm_flags&0x10)?True:False;
540	nmb->header.nm_flags.trunc = (nm_flags&0x20)?True:False;
541	nmb->header.nm_flags.authoritative = (nm_flags&0x40)?True:False;
542	nmb->header.rcode = CVAL(inbuf,3) & 0xF;
543	nmb->header.qdcount = RSVAL(inbuf,4);
544	nmb->header.ancount = RSVAL(inbuf,6);
545	nmb->header.nscount = RSVAL(inbuf,8);
546	nmb->header.arcount = RSVAL(inbuf,10);
547
548	if (nmb->header.qdcount) {
549		offset = parse_nmb_name(inbuf,12,length,
550				&nmb->question.question_name);
551		if (!offset)
552			return(False);
553
554		if (length - (12+offset) < 4)
555			return(False);
556		nmb->question.question_type = RSVAL(inbuf,12+offset);
557		nmb->question.question_class = RSVAL(inbuf,12+offset+2);
558
559		offset += 12+4;
560	} else {
561		offset = 12;
562	}
563
564	/* and any resource records */
565	if (nmb->header.ancount &&
566			!parse_alloc_res_rec(inbuf,&offset,length,&nmb->answers,
567					nmb->header.ancount))
568		return(False);
569
570	if (nmb->header.nscount &&
571			!parse_alloc_res_rec(inbuf,&offset,length,&nmb->nsrecs,
572					nmb->header.nscount))
573		return(False);
574
575	if (nmb->header.arcount &&
576			!parse_alloc_res_rec(inbuf,&offset,length,
577				&nmb->additional, nmb->header.arcount))
578		return(False);
579
580	return(True);
581}
582
583/*******************************************************************
584 'Copy constructor' for an nmb packet.
585******************************************************************/
586
587static struct packet_struct *copy_nmb_packet(struct packet_struct *packet)
588{
589	struct nmb_packet *nmb;
590	struct nmb_packet *copy_nmb;
591	struct packet_struct *pkt_copy;
592
593	if(( pkt_copy = SMB_MALLOC_P(struct packet_struct)) == NULL) {
594		DEBUG(0,("copy_nmb_packet: malloc fail.\n"));
595		return NULL;
596	}
597
598	/* Structure copy of entire thing. */
599
600	*pkt_copy = *packet;
601
602	/* Ensure this copy is not locked. */
603	pkt_copy->locked = False;
604	pkt_copy->recv_fd = -1;
605	pkt_copy->send_fd = -1;
606
607	/* Ensure this copy has no resource records. */
608	nmb = &packet->packet.nmb;
609	copy_nmb = &pkt_copy->packet.nmb;
610
611	copy_nmb->answers = NULL;
612	copy_nmb->nsrecs = NULL;
613	copy_nmb->additional = NULL;
614
615	/* Now copy any resource records. */
616
617	if (nmb->answers) {
618		if((copy_nmb->answers = SMB_MALLOC_ARRAY(
619				struct res_rec,nmb->header.ancount)) == NULL)
620			goto free_and_exit;
621		memcpy((char *)copy_nmb->answers, (char *)nmb->answers,
622				nmb->header.ancount * sizeof(struct res_rec));
623	}
624	if (nmb->nsrecs) {
625		if((copy_nmb->nsrecs = SMB_MALLOC_ARRAY(
626				struct res_rec, nmb->header.nscount)) == NULL)
627			goto free_and_exit;
628		memcpy((char *)copy_nmb->nsrecs, (char *)nmb->nsrecs,
629				nmb->header.nscount * sizeof(struct res_rec));
630	}
631	if (nmb->additional) {
632		if((copy_nmb->additional = SMB_MALLOC_ARRAY(
633				struct res_rec, nmb->header.arcount)) == NULL)
634			goto free_and_exit;
635		memcpy((char *)copy_nmb->additional, (char *)nmb->additional,
636				nmb->header.arcount * sizeof(struct res_rec));
637	}
638
639	return pkt_copy;
640
641 free_and_exit:
642
643	SAFE_FREE(copy_nmb->answers);
644	SAFE_FREE(copy_nmb->nsrecs);
645	SAFE_FREE(copy_nmb->additional);
646	SAFE_FREE(pkt_copy);
647
648	DEBUG(0,("copy_nmb_packet: malloc fail in resource records.\n"));
649	return NULL;
650}
651
652/*******************************************************************
653  'Copy constructor' for a dgram packet.
654******************************************************************/
655
656static struct packet_struct *copy_dgram_packet(struct packet_struct *packet)
657{
658	struct packet_struct *pkt_copy;
659
660	if(( pkt_copy = SMB_MALLOC_P(struct packet_struct)) == NULL) {
661		DEBUG(0,("copy_dgram_packet: malloc fail.\n"));
662		return NULL;
663	}
664
665	/* Structure copy of entire thing. */
666
667	*pkt_copy = *packet;
668
669	/* Ensure this copy is not locked. */
670	pkt_copy->locked = False;
671	pkt_copy->recv_fd = -1;
672	pkt_copy->send_fd = -1;
673
674	/* There are no additional pointers in a dgram packet,
675		we are finished. */
676	return pkt_copy;
677}
678
679/*******************************************************************
680 'Copy constructor' for a generic packet.
681******************************************************************/
682
683struct packet_struct *copy_packet(struct packet_struct *packet)
684{
685	if(packet->packet_type == NMB_PACKET)
686		return copy_nmb_packet(packet);
687	else if (packet->packet_type == DGRAM_PACKET)
688		return copy_dgram_packet(packet);
689	return NULL;
690}
691
692/*******************************************************************
693 Free up any resources associated with an nmb packet.
694******************************************************************/
695
696static void free_nmb_packet(struct nmb_packet *nmb)
697{
698	SAFE_FREE(nmb->answers);
699	SAFE_FREE(nmb->nsrecs);
700	SAFE_FREE(nmb->additional);
701}
702
703/*******************************************************************
704 Free up any resources associated with a dgram packet.
705******************************************************************/
706
707static void free_dgram_packet(struct dgram_packet *nmb)
708{
709	/* We have nothing to do for a dgram packet. */
710}
711
712/*******************************************************************
713 Free up any resources associated with a packet.
714******************************************************************/
715
716void free_packet(struct packet_struct *packet)
717{
718	if (packet->locked)
719		return;
720	if (packet->packet_type == NMB_PACKET)
721		free_nmb_packet(&packet->packet.nmb);
722	else if (packet->packet_type == DGRAM_PACKET)
723		free_dgram_packet(&packet->packet.dgram);
724	ZERO_STRUCTPN(packet);
725	SAFE_FREE(packet);
726}
727
728/*******************************************************************
729 Parse a packet buffer into a packet structure.
730******************************************************************/
731
732struct packet_struct *parse_packet(char *buf,int length,
733				   enum packet_type packet_type,
734				   struct in_addr ip,
735				   int port)
736{
737	struct packet_struct *p;
738	bool ok=False;
739
740	p = SMB_MALLOC_P(struct packet_struct);
741	if (!p)
742		return(NULL);
743
744	ZERO_STRUCTP(p);	/* initialize for possible padding */
745
746	p->next = NULL;
747	p->prev = NULL;
748	p->ip = ip;
749	p->port = port;
750	p->locked = False;
751	p->timestamp = time(NULL);
752	p->packet_type = packet_type;
753
754	switch (packet_type) {
755	case NMB_PACKET:
756		ok = parse_nmb(buf,length,&p->packet.nmb);
757		break;
758
759	case DGRAM_PACKET:
760		ok = parse_dgram(buf,length,&p->packet.dgram);
761		break;
762	}
763
764	if (!ok) {
765		free_packet(p);
766		return NULL;
767	}
768
769	return p;
770}
771
772/*******************************************************************
773 Read a packet from a socket and parse it, returning a packet ready
774 to be used or put on the queue. This assumes a UDP socket.
775******************************************************************/
776
777struct packet_struct *read_packet(int fd,enum packet_type packet_type)
778{
779	struct packet_struct *packet;
780	struct sockaddr_storage sa;
781	struct sockaddr_in *si = (struct sockaddr_in *)&sa;
782	char buf[MAX_DGRAM_SIZE];
783	int length;
784
785	length = read_udp_v4_socket(fd,buf,sizeof(buf),&sa);
786	if (length < MIN_DGRAM_SIZE || sa.ss_family != AF_INET) {
787		return NULL;
788	}
789
790	packet = parse_packet(buf,
791			length,
792			packet_type,
793			si->sin_addr,
794			ntohs(si->sin_port));
795	if (!packet)
796		return NULL;
797
798	packet->recv_fd = fd;
799	packet->send_fd = -1;
800
801	DEBUG(5,("Received a packet of len %d from (%s) port %d\n",
802		 length, inet_ntoa(packet->ip), packet->port ) );
803
804	return(packet);
805}
806
807/*******************************************************************
808 Send a udp packet on a already open socket.
809******************************************************************/
810
811static bool send_udp(int fd,char *buf,int len,struct in_addr ip,int port)
812{
813	bool ret = False;
814	int i;
815	struct sockaddr_in sock_out;
816
817	/* set the address and port */
818	memset((char *)&sock_out,'\0',sizeof(sock_out));
819	putip((char *)&sock_out.sin_addr,(char *)&ip);
820	sock_out.sin_port = htons( port );
821	sock_out.sin_family = AF_INET;
822
823	DEBUG( 5, ( "Sending a packet of len %d to (%s) on port %d\n",
824			len, inet_ntoa(ip), port ) );
825
826	/*
827	 * Patch to fix asynch error notifications from Linux kernel.
828	 */
829
830	for (i = 0; i < 5; i++) {
831		ret = (sendto(fd,buf,len,0,(struct sockaddr *)&sock_out,
832					sizeof(sock_out)) >= 0);
833		if (ret || errno != ECONNREFUSED)
834			break;
835	}
836
837	if (!ret)
838		DEBUG(0,("Packet send failed to %s(%d) ERRNO=%s\n",
839			inet_ntoa(ip),port,strerror(errno)));
840
841	return(ret);
842}
843
844/*******************************************************************
845 Build a dgram packet ready for sending.
846 If buf == NULL this is a length calculation.
847******************************************************************/
848
849static int build_dgram(char *buf, size_t len, struct dgram_packet *dgram)
850{
851	unsigned char *ubuf = (unsigned char *)buf;
852	int offset=0;
853
854	/* put in the header */
855	if (buf) {
856		ubuf[0] = dgram->header.msg_type;
857		ubuf[1] = (((int)dgram->header.flags.node_type)<<2);
858		if (dgram->header.flags.more)
859			ubuf[1] |= 1;
860		if (dgram->header.flags.first)
861			ubuf[1] |= 2;
862		RSSVAL(ubuf,2,dgram->header.dgm_id);
863		putip(ubuf+4,(char *)&dgram->header.source_ip);
864		RSSVAL(ubuf,8,dgram->header.source_port);
865		RSSVAL(ubuf,12,dgram->header.packet_offset);
866	}
867
868	offset = 14;
869
870	if (dgram->header.msg_type == 0x10 ||
871			dgram->header.msg_type == 0x11 ||
872			dgram->header.msg_type == 0x12) {
873		offset += put_nmb_name((char *)ubuf,offset,&dgram->source_name);
874		offset += put_nmb_name((char *)ubuf,offset,&dgram->dest_name);
875	}
876
877	if (buf) {
878		memcpy(ubuf+offset,dgram->data,dgram->datasize);
879	}
880	offset += dgram->datasize;
881
882	/* automatically set the dgm_length
883	 * NOTE: RFC1002 says the dgm_length does *not*
884	 *       include the fourteen-byte header. crh
885	 */
886	dgram->header.dgm_length = (offset - 14);
887	if (buf) {
888		RSSVAL(ubuf,10,dgram->header.dgm_length);
889	}
890
891	return offset;
892}
893
894/*******************************************************************
895 Build a nmb name
896*******************************************************************/
897
898void make_nmb_name( struct nmb_name *n, const char *name, int type)
899{
900	fstring unix_name;
901	memset( (char *)n, '\0', sizeof(struct nmb_name) );
902	fstrcpy(unix_name, name);
903	strupper_m(unix_name);
904	push_ascii(n->name, unix_name, sizeof(n->name), STR_TERMINATE);
905	n->name_type = (unsigned int)type & 0xFF;
906	push_ascii(n->scope,  global_scope(), 64, STR_TERMINATE);
907}
908
909/*******************************************************************
910  Compare two nmb names
911******************************************************************/
912
913bool nmb_name_equal(struct nmb_name *n1, struct nmb_name *n2)
914{
915	return ((n1->name_type == n2->name_type) &&
916		strequal(n1->name ,n2->name ) &&
917		strequal(n1->scope,n2->scope));
918}
919
920/*******************************************************************
921 Build a nmb packet ready for sending.
922 If buf == NULL this is a length calculation.
923******************************************************************/
924
925static int build_nmb(char *buf, size_t len, struct nmb_packet *nmb)
926{
927	unsigned char *ubuf = (unsigned char *)buf;
928	int offset=0;
929
930	if (len && len < 12) {
931		return 0;
932	}
933
934	/* put in the header */
935	if (buf) {
936		RSSVAL(ubuf,offset,nmb->header.name_trn_id);
937		ubuf[offset+2] = (nmb->header.opcode & 0xF) << 3;
938		if (nmb->header.response)
939			ubuf[offset+2] |= (1<<7);
940		if (nmb->header.nm_flags.authoritative &&
941				nmb->header.response)
942			ubuf[offset+2] |= 0x4;
943		if (nmb->header.nm_flags.trunc)
944			ubuf[offset+2] |= 0x2;
945		if (nmb->header.nm_flags.recursion_desired)
946			ubuf[offset+2] |= 0x1;
947		if (nmb->header.nm_flags.recursion_available &&
948				nmb->header.response)
949			ubuf[offset+3] |= 0x80;
950		if (nmb->header.nm_flags.bcast)
951			ubuf[offset+3] |= 0x10;
952		ubuf[offset+3] |= (nmb->header.rcode & 0xF);
953
954		RSSVAL(ubuf,offset+4,nmb->header.qdcount);
955		RSSVAL(ubuf,offset+6,nmb->header.ancount);
956		RSSVAL(ubuf,offset+8,nmb->header.nscount);
957		RSSVAL(ubuf,offset+10,nmb->header.arcount);
958	}
959
960	offset += 12;
961	if (nmb->header.qdcount) {
962		/* XXXX this doesn't handle a qdcount of > 1 */
963		if (len) {
964			/* Length check. */
965			int extra = put_nmb_name(NULL,offset,
966					&nmb->question.question_name);
967			if (offset + extra > len) {
968				return 0;
969			}
970		}
971		offset += put_nmb_name((char *)ubuf,offset,
972				&nmb->question.question_name);
973		if (buf) {
974			RSSVAL(ubuf,offset,nmb->question.question_type);
975			RSSVAL(ubuf,offset+2,nmb->question.question_class);
976		}
977		offset += 4;
978	}
979
980	if (nmb->header.ancount) {
981		if (len) {
982			/* Length check. */
983			int extra = put_res_rec(NULL,offset,nmb->answers,
984					nmb->header.ancount);
985			if (offset + extra > len) {
986				return 0;
987			}
988		}
989		offset += put_res_rec((char *)ubuf,offset,nmb->answers,
990				nmb->header.ancount);
991	}
992
993	if (nmb->header.nscount) {
994		if (len) {
995			/* Length check. */
996			int extra = put_res_rec(NULL,offset,nmb->nsrecs,
997				nmb->header.nscount);
998			if (offset + extra > len) {
999				return 0;
1000			}
1001		}
1002		offset += put_res_rec((char *)ubuf,offset,nmb->nsrecs,
1003				nmb->header.nscount);
1004	}
1005
1006	/*
1007	 * The spec says we must put compressed name pointers
1008	 * in the following outgoing packets :
1009	 * NAME_REGISTRATION_REQUEST, NAME_REFRESH_REQUEST,
1010	 * NAME_RELEASE_REQUEST.
1011	 */
1012
1013	if((nmb->header.response == False) &&
1014		((nmb->header.opcode == NMB_NAME_REG_OPCODE) ||
1015		(nmb->header.opcode == NMB_NAME_RELEASE_OPCODE) ||
1016		(nmb->header.opcode == NMB_NAME_REFRESH_OPCODE_8) ||
1017		(nmb->header.opcode == NMB_NAME_REFRESH_OPCODE_9) ||
1018		(nmb->header.opcode == NMB_NAME_MULTIHOMED_REG_OPCODE)) &&
1019		(nmb->header.arcount == 1)) {
1020
1021		if (len) {
1022			/* Length check. */
1023			int extra = put_compressed_name_ptr(NULL,offset,
1024					nmb->additional,12);
1025			if (offset + extra > len) {
1026				return 0;
1027			}
1028		}
1029		offset += put_compressed_name_ptr(ubuf,offset,
1030				nmb->additional,12);
1031	} else if (nmb->header.arcount) {
1032		if (len) {
1033			/* Length check. */
1034			int extra = put_res_rec(NULL,offset,nmb->additional,
1035				nmb->header.arcount);
1036			if (offset + extra > len) {
1037				return 0;
1038			}
1039		}
1040		offset += put_res_rec((char *)ubuf,offset,nmb->additional,
1041			nmb->header.arcount);
1042	}
1043	return offset;
1044}
1045
1046/*******************************************************************
1047 Linearise a packet.
1048******************************************************************/
1049
1050int build_packet(char *buf, size_t buflen, struct packet_struct *p)
1051{
1052	int len = 0;
1053
1054	switch (p->packet_type) {
1055	case NMB_PACKET:
1056		len = build_nmb(buf,buflen,&p->packet.nmb);
1057		break;
1058
1059	case DGRAM_PACKET:
1060		len = build_dgram(buf,buflen,&p->packet.dgram);
1061		break;
1062	}
1063
1064	return len;
1065}
1066
1067/*******************************************************************
1068 Send a packet_struct.
1069******************************************************************/
1070
1071bool send_packet(struct packet_struct *p)
1072{
1073	char buf[1024];
1074	int len=0;
1075
1076	memset(buf,'\0',sizeof(buf));
1077
1078	len = build_packet(buf, sizeof(buf), p);
1079
1080	if (!len)
1081		return(False);
1082
1083	return(send_udp(p->send_fd,buf,len,p->ip,p->port));
1084}
1085
1086/****************************************************************************
1087 Receive a packet with timeout on a open UDP filedescriptor.
1088 The timeout is in milliseconds
1089***************************************************************************/
1090
1091struct packet_struct *receive_packet(int fd,enum packet_type type,int t)
1092{
1093	fd_set fds;
1094	struct timeval timeout;
1095	int ret;
1096
1097	if (fd < 0 || fd >= FD_SETSIZE) {
1098		errno = EBADF;
1099		return NULL;
1100	}
1101
1102	FD_ZERO(&fds);
1103	FD_SET(fd,&fds);
1104	timeout.tv_sec = t/1000;
1105	timeout.tv_usec = 1000*(t%1000);
1106
1107	if ((ret = sys_select_intr(fd+1,&fds,NULL,NULL,&timeout)) == -1) {
1108		/* errno should be EBADF or EINVAL. */
1109		DEBUG(0,("select returned -1, errno = %s (%d)\n",
1110					strerror(errno), errno));
1111		return NULL;
1112	}
1113
1114	if (ret == 0) /* timeout */
1115		return NULL;
1116
1117	if (FD_ISSET(fd,&fds))
1118		return(read_packet(fd,type));
1119
1120	return(NULL);
1121}
1122
1123/****************************************************************************
1124 Receive a UDP/137 packet either via UDP or from the unexpected packet
1125 queue. The packet must be a reply packet and have the specified trn_id.
1126 The timeout is in milliseconds.
1127***************************************************************************/
1128
1129struct packet_struct *receive_nmb_packet(int fd, int t, int trn_id)
1130{
1131	struct packet_struct *p;
1132
1133	p = receive_packet(fd, NMB_PACKET, t);
1134
1135	if (p && p->packet.nmb.header.response &&
1136			p->packet.nmb.header.name_trn_id == trn_id) {
1137		return p;
1138	}
1139	if (p)
1140		free_packet(p);
1141
1142	/* try the unexpected packet queue */
1143	return receive_unexpected(NMB_PACKET, trn_id, NULL);
1144}
1145
1146/****************************************************************************
1147 Receive a UDP/138 packet either via UDP or from the unexpected packet
1148 queue. The packet must be a reply packet and have the specified mailslot name
1149 The timeout is in milliseconds.
1150***************************************************************************/
1151
1152struct packet_struct *receive_dgram_packet(int fd, int t,
1153		const char *mailslot_name)
1154{
1155	struct packet_struct *p;
1156
1157	p = receive_packet(fd, DGRAM_PACKET, t);
1158
1159	if (p && match_mailslot_name(p, mailslot_name)) {
1160		return p;
1161	}
1162	if (p)
1163		free_packet(p);
1164
1165	/* try the unexpected packet queue */
1166	return receive_unexpected(DGRAM_PACKET, 0, mailslot_name);
1167}
1168
1169/****************************************************************************
1170 See if a datagram has the right mailslot name.
1171***************************************************************************/
1172
1173bool match_mailslot_name(struct packet_struct *p, const char *mailslot_name)
1174{
1175	struct dgram_packet *dgram = &p->packet.dgram;
1176	char *buf;
1177
1178	buf = &dgram->data[0];
1179	buf -= 4;
1180
1181	buf = smb_buf(buf);
1182
1183	if (memcmp(buf, mailslot_name, strlen(mailslot_name)+1) == 0) {
1184		return True;
1185	}
1186
1187	return False;
1188}
1189
1190/****************************************************************************
1191 Return the number of bits that match between two len character buffers
1192***************************************************************************/
1193
1194int matching_len_bits(unsigned char *p1, unsigned char *p2, size_t len)
1195{
1196	size_t i, j;
1197	int ret = 0;
1198	for (i=0; i<len; i++) {
1199		if (p1[i] != p2[i])
1200			break;
1201		ret += 8;
1202	}
1203
1204	if (i==len)
1205		return ret;
1206
1207	for (j=0; j<8; j++) {
1208		if ((p1[i] & (1<<(7-j))) != (p2[i] & (1<<(7-j))))
1209			break;
1210		ret++;
1211	}
1212
1213	return ret;
1214}
1215
1216static unsigned char sort_ip[4];
1217
1218/****************************************************************************
1219 Compare two query reply records.
1220***************************************************************************/
1221
1222static int name_query_comp(unsigned char *p1, unsigned char *p2)
1223{
1224	return matching_len_bits(p2+2, sort_ip, 4) -
1225		matching_len_bits(p1+2, sort_ip, 4);
1226}
1227
1228/****************************************************************************
1229 Sort a set of 6 byte name query response records so that the IPs that
1230 have the most leading bits in common with the specified address come first.
1231***************************************************************************/
1232
1233void sort_query_replies(char *data, int n, struct in_addr ip)
1234{
1235	if (n <= 1)
1236		return;
1237
1238	putip(sort_ip, (char *)&ip);
1239
1240	qsort(data, n, 6, QSORT_CAST name_query_comp);
1241}
1242
1243/****************************************************************************
1244 Interpret the weird netbios "name" into a unix fstring. Return the name type.
1245 Returns -1 on error.
1246****************************************************************************/
1247
1248static int name_interpret(unsigned char *buf, size_t buf_len,
1249		unsigned char *in, fstring name)
1250{
1251	unsigned char *end_ptr = buf + buf_len;
1252	int ret;
1253	unsigned int len;
1254	fstring out_string;
1255	unsigned char *out = (unsigned char *)out_string;
1256
1257	*out=0;
1258
1259	if (in >= end_ptr) {
1260		return -1;
1261	}
1262	len = (*in++) / 2;
1263
1264	if (len<1) {
1265		return -1;
1266	}
1267
1268	while (len--) {
1269		if (&in[1] >= end_ptr) {
1270			return -1;
1271		}
1272		if (in[0] < 'A' || in[0] > 'P' || in[1] < 'A' || in[1] > 'P') {
1273			*out = 0;
1274			return(0);
1275		}
1276		*out = ((in[0]-'A')<<4) + (in[1]-'A');
1277		in += 2;
1278		out++;
1279		if (PTR_DIFF(out,out_string) >= sizeof(fstring)) {
1280			return -1;
1281		}
1282	}
1283	ret = out[-1];
1284	out[-1] = 0;
1285
1286	pull_ascii_fstring(name, out_string);
1287
1288	return(ret);
1289}
1290
1291/****************************************************************************
1292 Mangle a name into netbios format.
1293 Note:  <Out> must be (33 + strlen(scope) + 2) bytes long, at minimum.
1294****************************************************************************/
1295
1296char *name_mangle(TALLOC_CTX *mem_ctx, const char *In, char name_type)
1297{
1298	int   i;
1299	int   len;
1300	nstring buf;
1301	char *result;
1302	char *p;
1303
1304	result = talloc_array(mem_ctx, char, 33 + strlen(global_scope()) + 2);
1305	if (result == NULL) {
1306		return NULL;
1307	}
1308	p = result;
1309
1310	/* Safely copy the input string, In, into buf[]. */
1311	if (strcmp(In,"*") == 0)
1312		put_name(buf, "*", '\0', 0x00);
1313	else {
1314		/* We use an fstring here as mb dos names can expend x3 when
1315		   going to utf8. */
1316		fstring buf_unix;
1317		nstring buf_dos;
1318
1319		pull_ascii_fstring(buf_unix, In);
1320		strupper_m(buf_unix);
1321
1322		push_ascii_nstring(buf_dos, buf_unix);
1323		put_name(buf, buf_dos, ' ', name_type);
1324	}
1325
1326	/* Place the length of the first field into the output buffer. */
1327	p[0] = 32;
1328	p++;
1329
1330	/* Now convert the name to the rfc1001/1002 format. */
1331	for( i = 0; i < MAX_NETBIOSNAME_LEN; i++ ) {
1332		p[i*2]     = ( (buf[i] >> 4) & 0x000F ) + 'A';
1333		p[(i*2)+1] = (buf[i] & 0x000F) + 'A';
1334	}
1335	p += 32;
1336	p[0] = '\0';
1337
1338	/* Add the scope string. */
1339	for( i = 0, len = 0; *(global_scope()) != '\0'; i++, len++ ) {
1340		switch( (global_scope())[i] ) {
1341			case '\0':
1342				p[0] = len;
1343				if( len > 0 )
1344					p[len+1] = 0;
1345				return result;
1346			case '.':
1347				p[0] = len;
1348				p   += (len + 1);
1349				len  = -1;
1350				break;
1351			default:
1352				p[len+1] = (global_scope())[i];
1353				break;
1354		}
1355	}
1356
1357	return result;
1358}
1359
1360/****************************************************************************
1361 Find a pointer to a netbios name.
1362****************************************************************************/
1363
1364static unsigned char *name_ptr(unsigned char *buf, size_t buf_len, unsigned int ofs)
1365{
1366	unsigned char c = 0;
1367
1368	if (ofs > buf_len || buf_len < 1) {
1369		return NULL;
1370	}
1371
1372	c = *(unsigned char *)(buf+ofs);
1373	if ((c & 0xC0) == 0xC0) {
1374		uint16 l = 0;
1375
1376		if (ofs > buf_len - 1) {
1377			return NULL;
1378		}
1379		l = RSVAL(buf, ofs) & 0x3FFF;
1380		if (l > buf_len) {
1381			return NULL;
1382		}
1383		DEBUG(5,("name ptr to pos %d from %d is %s\n",l,ofs,buf+l));
1384		return(buf + l);
1385	} else {
1386		return(buf+ofs);
1387	}
1388}
1389
1390/****************************************************************************
1391 Extract a netbios name from a buf (into a unix string) return name type.
1392 Returns -1 on error.
1393****************************************************************************/
1394
1395int name_extract(unsigned char *buf, size_t buf_len, unsigned int ofs, fstring name)
1396{
1397	unsigned char *p = name_ptr(buf,buf_len,ofs);
1398
1399	name[0] = '\0';
1400	if (p == NULL) {
1401		return -1;
1402	}
1403	return(name_interpret(buf,buf_len,p,name));
1404}
1405
1406/****************************************************************************
1407 Return the total storage length of a mangled name.
1408 Returns -1 on error.
1409****************************************************************************/
1410
1411int name_len(unsigned char *s1, size_t buf_len)
1412{
1413	/* NOTE: this argument _must_ be unsigned */
1414	unsigned char *s = (unsigned char *)s1;
1415	int len = 0;
1416
1417	if (buf_len < 1) {
1418		return -1;
1419	}
1420	/* If the two high bits of the byte are set, return 2. */
1421	if (0xC0 == (*s & 0xC0)) {
1422		if (buf_len < 2) {
1423			return -1;
1424		}
1425		return(2);
1426	}
1427
1428	/* Add up the length bytes. */
1429	for (len = 1; (*s); s += (*s) + 1) {
1430		len += *s + 1;
1431		if (len > buf_len) {
1432			return -1;
1433		}
1434	}
1435
1436	return(len);
1437}
1438