pidl: Wireshark: Another C99 type conversion
[Samba.git] / source3 / nmbd / nmbd_packets.c
blob1da365762e651ace034cc5e2845491fa06805b1e
1 /*
2 Unix SMB/CIFS implementation.
3 NBT netbios routines and daemon - version 2
4 Copyright (C) Andrew Tridgell 1994-1998
5 Copyright (C) Luke Kenneth Casson Leighton 1994-1998
6 Copyright (C) Jeremy Allison 1994-2003
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 3 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, see <http://www.gnu.org/licenses/>.
22 #include "includes.h"
23 #include "nmbd/nmbd.h"
24 #include "../lib/util/select.h"
25 #include "system/select.h"
26 #include "libsmb/libsmb.h"
27 #include "libsmb/unexpected.h"
28 #include "lib/util/string_wrappers.h"
30 extern int ClientNMB;
31 extern int ClientDGRAM;
32 extern int global_nmb_port;
34 extern int num_response_packets;
36 bool rescan_listen_set = False;
38 static struct nb_packet_server *packet_server;
40 bool nmbd_init_packet_server(void)
42 NTSTATUS status;
44 status = nb_packet_server_create(
45 NULL, nmbd_event_context(),
46 global_nmbd_socket_dir(),
47 lp_parm_int(-1, "nmbd", "unexpected_clients", 200),
48 &packet_server);
49 if (!NT_STATUS_IS_OK(status)) {
50 DEBUG(0, ("ERROR: nb_packet_server_create failed: %s\n",
51 nt_errstr(status)));
52 return false;
54 return true;
58 /*******************************************************************
59 The global packet linked-list. Incoming entries are
60 added to the end of this list. It is supposed to remain fairly
61 short so we won't bother with an end pointer.
62 ******************************************************************/
64 static struct packet_struct *packet_queue = NULL;
66 /***************************************************************************
67 Utility function to find the specific fd to send a packet out on.
68 **************************************************************************/
70 static int find_subnet_fd_for_address( struct in_addr local_ip )
72 struct subnet_record *subrec;
74 for( subrec = FIRST_SUBNET; subrec; subrec = NEXT_SUBNET_EXCLUDING_UNICAST(subrec))
75 if(ip_equal_v4(local_ip, subrec->myip))
76 return subrec->nmb_sock;
78 return ClientNMB;
81 /***************************************************************************
82 Utility function to find the specific fd to send a mailslot packet out on.
83 **************************************************************************/
85 static int find_subnet_mailslot_fd_for_address( struct in_addr local_ip )
87 struct subnet_record *subrec;
89 for( subrec = FIRST_SUBNET; subrec; subrec = NEXT_SUBNET_EXCLUDING_UNICAST(subrec))
90 if(ip_equal_v4(local_ip, subrec->myip))
91 return subrec->dgram_sock;
93 return ClientDGRAM;
96 /***************************************************************************
97 Get/Set problematic nb_flags as network byte order 16 bit int.
98 **************************************************************************/
100 uint16_t get_nb_flags(char *buf)
102 return ((((uint16_t)*buf)&0xFFFF) & NB_FLGMSK);
105 void set_nb_flags(char *buf, uint16_t nb_flags)
107 *buf++ = ((nb_flags & NB_FLGMSK) & 0xFF);
108 *buf = '\0';
111 /***************************************************************************
112 Dumps out the browse packet data.
113 **************************************************************************/
115 static void debug_browse_data(const char *outbuf, int len)
117 int i,j;
119 DEBUG( 4, ( "debug_browse_data():\n" ) );
120 for (i = 0; i < len; i+= 16) {
121 DEBUGADD( 4, ( "%3x char ", i ) );
123 for (j = 0; j < 16; j++) {
124 unsigned char x;
125 if (i+j >= len)
126 break;
128 x = outbuf[i+j];
129 if (x < 32 || x > 127)
130 x = '.';
132 DEBUGADD( 4, ( "%c", x ) );
135 DEBUGADD( 4, ( "%*s hex", 16-j, "" ) );
137 for (j = 0; j < 16; j++) {
138 if (i+j >= len)
139 break;
140 DEBUGADD( 4, ( " %02x", (unsigned char)outbuf[i+j] ) );
143 DEBUGADD( 4, ("\n") );
147 /***************************************************************************
148 Generates the unique transaction identifier
149 **************************************************************************/
151 static uint16_t name_trn_id=0;
153 static uint16_t generate_name_trn_id(void)
155 if (!name_trn_id) {
156 name_trn_id = ((unsigned)time(NULL)%(unsigned)0x7FFF) + ((unsigned)getpid()%(unsigned)100);
158 name_trn_id = (name_trn_id+1) % (unsigned)0x7FFF;
159 return name_trn_id;
162 /***************************************************************************
163 Either loops back or sends out a completed NetBIOS packet.
164 **************************************************************************/
166 static bool send_netbios_packet(struct packet_struct *p)
168 bool loopback_this_packet = False;
170 /* Check if we are sending to or from ourselves as a WINS server. */
171 if(ismyip_v4(p->ip) && (p->port == global_nmb_port))
172 loopback_this_packet = True;
174 if(loopback_this_packet) {
175 struct packet_struct *lo_packet = NULL;
176 DEBUG(5,("send_netbios_packet: sending packet to ourselves.\n"));
177 if((lo_packet = copy_packet(p)) == NULL)
178 return False;
179 queue_packet(lo_packet);
180 } else if (!send_packet(p)) {
181 DEBUG(0,("send_netbios_packet: send_packet() to IP %s port %d failed\n",
182 inet_ntoa(p->ip),p->port));
183 return False;
186 return True;
189 /***************************************************************************
190 Sets up the common elements of an outgoing NetBIOS packet.
192 Note: do not attempt to rationalise whether rec_des should be set or not
193 in a particular situation. Just follow rfc_1002 or look at examples from WinXX.
194 It does NOT follow the rule that requests to the wins server always have
195 rec_des true. See for example name releases and refreshes
196 **************************************************************************/
198 static struct packet_struct *create_and_init_netbios_packet(struct nmb_name *nmbname,
199 bool bcast, bool rec_des,
200 struct in_addr to_ip)
202 struct packet_struct *packet = NULL;
203 struct nmb_packet *nmb = NULL;
205 /* Allocate the packet_struct we will return. */
206 if((packet = SMB_MALLOC_P(struct packet_struct)) == NULL) {
207 DEBUG(0,("create_and_init_netbios_packet: malloc fail (1) for packet struct.\n"));
208 return NULL;
211 memset((char *)packet,'\0',sizeof(*packet));
213 nmb = &packet->packet.nmb;
215 nmb->header.name_trn_id = generate_name_trn_id();
216 nmb->header.response = False;
217 nmb->header.nm_flags.recursion_desired = rec_des;
218 nmb->header.nm_flags.recursion_available = False;
219 nmb->header.nm_flags.trunc = False;
220 nmb->header.nm_flags.authoritative = False;
221 nmb->header.nm_flags.bcast = bcast;
223 nmb->header.rcode = 0;
224 nmb->header.qdcount = 1;
225 nmb->header.ancount = 0;
226 nmb->header.nscount = 0;
228 nmb->question.question_name = *nmbname;
229 nmb->question.question_type = QUESTION_TYPE_NB_QUERY;
230 nmb->question.question_class = QUESTION_CLASS_IN;
232 packet->ip = to_ip;
233 packet->port = NMB_PORT;
234 packet->recv_fd = -1;
235 packet->send_fd = ClientNMB;
236 packet->timestamp = time(NULL);
237 packet->packet_type = NMB_PACKET;
238 packet->locked = False;
240 return packet; /* Caller must free. */
243 /***************************************************************************
244 Sets up the common elements of register, refresh or release packet.
245 **************************************************************************/
247 static bool create_and_init_additional_record(struct packet_struct *packet,
248 uint16_t nb_flags,
249 const struct in_addr *register_ip)
251 struct nmb_packet *nmb = &packet->packet.nmb;
253 if((nmb->additional = SMB_MALLOC_P(struct res_rec)) == NULL) {
254 DEBUG(0,("create_and_init_additional_record: malloc fail for additional record.\n"));
255 return False;
258 memset((char *)nmb->additional,'\0',sizeof(struct res_rec));
260 nmb->additional->rr_name = nmb->question.question_name;
261 nmb->additional->rr_type = RR_TYPE_NB;
262 nmb->additional->rr_class = RR_CLASS_IN;
264 /* See RFC 1002, sections 5.1.1.1, 5.1.1.2 and 5.1.1.3 */
265 if (nmb->header.nm_flags.bcast)
266 nmb->additional->ttl = PERMANENT_TTL;
267 else
268 nmb->additional->ttl = lp_max_ttl();
270 nmb->additional->rdlength = 6;
272 set_nb_flags(nmb->additional->rdata,nb_flags);
274 /* Set the address for the name we are registering. */
275 putip(&nmb->additional->rdata[2], register_ip);
278 it turns out that Jeremys code was correct, we are supposed
279 to send registrations from the IP we are registering. The
280 trick is what to do on timeouts! When we send on a
281 non-routable IP then the reply will timeout, and we should
282 treat this as success, not failure. That means we go into
283 our standard refresh cycle for that name which copes nicely
284 with disconnected networks.
286 packet->recv_fd = -1;
287 packet->send_fd = find_subnet_fd_for_address(*register_ip);
289 return True;
292 /***************************************************************************
293 Sends out a name query.
294 **************************************************************************/
296 static bool initiate_name_query_packet( struct packet_struct *packet)
298 struct nmb_packet *nmb = NULL;
300 nmb = &packet->packet.nmb;
302 nmb->header.opcode = NMB_NAME_QUERY_OPCODE;
303 nmb->header.arcount = 0;
305 nmb->header.nm_flags.recursion_desired = True;
307 DEBUG(4,("initiate_name_query_packet: sending query for name %s (bcast=%s) to IP %s\n",
308 nmb_namestr(&nmb->question.question_name),
309 BOOLSTR(nmb->header.nm_flags.bcast), inet_ntoa(packet->ip)));
311 return send_netbios_packet( packet );
314 /***************************************************************************
315 Sends out a name query - from a WINS server.
316 **************************************************************************/
318 static bool initiate_name_query_packet_from_wins_server( struct packet_struct *packet)
320 struct nmb_packet *nmb = NULL;
322 nmb = &packet->packet.nmb;
324 nmb->header.opcode = NMB_NAME_QUERY_OPCODE;
325 nmb->header.arcount = 0;
327 nmb->header.nm_flags.recursion_desired = False;
329 DEBUG(4,("initiate_name_query_packet_from_wins_server: sending query for name %s (bcast=%s) to IP %s\n",
330 nmb_namestr(&nmb->question.question_name),
331 BOOLSTR(nmb->header.nm_flags.bcast), inet_ntoa(packet->ip)));
333 return send_netbios_packet( packet );
336 /***************************************************************************
337 Sends out a name register.
338 **************************************************************************/
340 static bool initiate_name_register_packet( struct packet_struct *packet,
341 uint16_t nb_flags, const struct in_addr *register_ip)
343 struct nmb_packet *nmb = &packet->packet.nmb;
345 nmb->header.opcode = NMB_NAME_REG_OPCODE;
346 nmb->header.arcount = 1;
348 nmb->header.nm_flags.recursion_desired = True;
350 if(create_and_init_additional_record(packet, nb_flags, register_ip) == False)
351 return False;
353 DEBUG(4,("initiate_name_register_packet: sending registration for name %s (bcast=%s) to IP %s\n",
354 nmb_namestr(&nmb->additional->rr_name),
355 BOOLSTR(nmb->header.nm_flags.bcast), inet_ntoa(packet->ip)));
357 return send_netbios_packet( packet );
360 /***************************************************************************
361 Sends out a multihomed name register.
362 **************************************************************************/
364 static bool initiate_multihomed_name_register_packet(struct packet_struct *packet,
365 uint16_t nb_flags, struct in_addr *register_ip)
367 struct nmb_packet *nmb = &packet->packet.nmb;
368 fstring second_ip_buf;
370 fstrcpy(second_ip_buf, inet_ntoa(packet->ip));
372 nmb->header.opcode = NMB_NAME_MULTIHOMED_REG_OPCODE;
373 nmb->header.arcount = 1;
375 nmb->header.nm_flags.recursion_desired = True;
377 if(create_and_init_additional_record(packet, nb_flags, register_ip) == False)
378 return False;
380 DEBUG(4,("initiate_multihomed_name_register_packet: sending registration \
381 for name %s IP %s (bcast=%s) to IP %s\n",
382 nmb_namestr(&nmb->additional->rr_name), inet_ntoa(*register_ip),
383 BOOLSTR(nmb->header.nm_flags.bcast), second_ip_buf ));
385 return send_netbios_packet( packet );
388 /***************************************************************************
389 Sends out a name refresh.
390 **************************************************************************/
392 static bool initiate_name_refresh_packet( struct packet_struct *packet,
393 uint16_t nb_flags, struct in_addr *refresh_ip)
395 struct nmb_packet *nmb = &packet->packet.nmb;
397 nmb->header.opcode = NMB_NAME_REFRESH_OPCODE_8;
398 nmb->header.arcount = 1;
400 nmb->header.nm_flags.recursion_desired = False;
402 if(create_and_init_additional_record(packet, nb_flags, refresh_ip) == False)
403 return False;
405 DEBUG(4,("initiate_name_refresh_packet: sending refresh for name %s (bcast=%s) to IP %s\n",
406 nmb_namestr(&nmb->additional->rr_name),
407 BOOLSTR(nmb->header.nm_flags.bcast), inet_ntoa(packet->ip)));
409 return send_netbios_packet( packet );
412 /***************************************************************************
413 Sends out a name release.
414 **************************************************************************/
416 static bool initiate_name_release_packet( struct packet_struct *packet,
417 uint16_t nb_flags, struct in_addr *release_ip)
419 struct nmb_packet *nmb = &packet->packet.nmb;
421 nmb->header.opcode = NMB_NAME_RELEASE_OPCODE;
422 nmb->header.arcount = 1;
424 nmb->header.nm_flags.recursion_desired = False;
426 if(create_and_init_additional_record(packet, nb_flags, release_ip) == False)
427 return False;
429 DEBUG(4,("initiate_name_release_packet: sending release for name %s (bcast=%s) to IP %s\n",
430 nmb_namestr(&nmb->additional->rr_name),
431 BOOLSTR(nmb->header.nm_flags.bcast), inet_ntoa(packet->ip)));
433 return send_netbios_packet( packet );
436 /***************************************************************************
437 Sends out a node status.
438 **************************************************************************/
440 static bool initiate_node_status_packet( struct packet_struct *packet )
442 struct nmb_packet *nmb = &packet->packet.nmb;
444 nmb->header.opcode = NMB_NAME_QUERY_OPCODE;
445 nmb->header.arcount = 0;
447 nmb->header.nm_flags.recursion_desired = False;
449 nmb->question.question_type = QUESTION_TYPE_NB_STATUS;
451 DEBUG(4,("initiate_node_status_packet: sending node status request for name %s to IP %s\n",
452 nmb_namestr(&nmb->question.question_name),
453 inet_ntoa(packet->ip)));
455 return send_netbios_packet( packet );
458 /****************************************************************************
459 Simplification functions for queuing standard packets.
460 These should be the only publicly callable functions for sending
461 out packets.
462 ****************************************************************************/
464 /****************************************************************************
465 Assertion - we should never be sending nmbd packets on the remote
466 broadcast subnet.
467 ****************************************************************************/
469 static bool assert_check_subnet(struct subnet_record *subrec)
471 if( subrec == remote_broadcast_subnet) {
472 DEBUG(0,("assert_check_subnet: Attempt to send packet on remote broadcast subnet. \
473 This is a bug.\n"));
474 return True;
476 return False;
479 /****************************************************************************
480 Queue a register name packet to the broadcast address of a subnet.
481 ****************************************************************************/
483 struct response_record *queue_register_name( struct subnet_record *subrec,
484 response_function resp_fn,
485 timeout_response_function timeout_fn,
486 register_name_success_function success_fn,
487 register_name_fail_function fail_fn,
488 struct userdata_struct *userdata,
489 struct nmb_name *nmbname,
490 uint16_t nb_flags)
492 struct packet_struct *p;
493 struct response_record *rrec;
494 struct sockaddr_storage ss;
495 const struct sockaddr_storage *pss = NULL;
496 if(assert_check_subnet(subrec))
497 return NULL;
499 /* note that all name registration requests have RD set (rfc1002 - section 4.2.2 */
500 if ((p = create_and_init_netbios_packet(nmbname, (subrec != unicast_subnet), True,
501 subrec->bcast_ip)) == NULL)
502 return NULL;
504 in_addr_to_sockaddr_storage(&ss, subrec->bcast_ip);
505 pss = iface_ip((struct sockaddr *)(void *)&ss);
506 if (!pss || pss->ss_family != AF_INET) {
507 p->locked = False;
508 free_packet(p);
509 return NULL;
512 if(initiate_name_register_packet(p, nb_flags,
513 &((const struct sockaddr_in *)pss)->sin_addr) == False) {
514 p->locked = False;
515 free_packet(p);
516 return NULL;
519 if((rrec = make_response_record(subrec, /* subnet record. */
520 p, /* packet we sent. */
521 resp_fn, /* function to call on response. */
522 timeout_fn, /* function to call on timeout. */
523 (success_function)success_fn, /* function to call on operation success. */
524 (fail_function)fail_fn, /* function to call on operation fail. */
525 userdata)) == NULL) {
526 p->locked = False;
527 free_packet(p);
528 return NULL;
531 return rrec;
534 /****************************************************************************
535 Queue a refresh name packet to the broadcast address of a subnet.
536 ****************************************************************************/
538 void queue_wins_refresh(struct nmb_name *nmbname,
539 response_function resp_fn,
540 timeout_response_function timeout_fn,
541 uint16_t nb_flags,
542 struct in_addr refresh_ip,
543 const char *tag)
545 struct packet_struct *p;
546 struct response_record *rrec;
547 struct in_addr wins_ip;
548 struct userdata_struct *userdata;
549 fstring ip_str;
551 wins_ip = wins_srv_ip_tag(tag, refresh_ip);
553 if ((p = create_and_init_netbios_packet(nmbname, False, False, wins_ip)) == NULL) {
554 return;
557 if (!initiate_name_refresh_packet(p, nb_flags, &refresh_ip)) {
558 p->locked = False;
559 free_packet(p);
560 return;
563 fstrcpy(ip_str, inet_ntoa(refresh_ip));
565 DEBUG(6,("Refreshing name %s IP %s with WINS server %s using tag '%s'\n",
566 nmb_namestr(nmbname), ip_str, inet_ntoa(wins_ip), tag));
568 userdata = (struct userdata_struct *)SMB_MALLOC(sizeof(*userdata) + strlen(tag) + 1);
569 if (!userdata) {
570 p->locked = False;
571 free_packet(p);
572 DEBUG(0,("Failed to allocate userdata structure!\n"));
573 return;
575 ZERO_STRUCTP(userdata);
576 userdata->userdata_len = strlen(tag) + 1;
577 strlcpy(userdata->data, tag, userdata->userdata_len);
579 if ((rrec = make_response_record(unicast_subnet,
581 resp_fn, timeout_fn,
582 NULL,
583 NULL,
584 userdata)) == NULL) {
585 p->locked = False;
586 free_packet(p);
587 return;
590 free(userdata);
592 /* we don't want to repeat refresh packets */
593 rrec->repeat_count = 0;
597 /****************************************************************************
598 Queue a multihomed register name packet to a given WINS server IP
599 ****************************************************************************/
601 struct response_record *queue_register_multihomed_name( struct subnet_record *subrec,
602 response_function resp_fn,
603 timeout_response_function timeout_fn,
604 register_name_success_function success_fn,
605 register_name_fail_function fail_fn,
606 struct userdata_struct *userdata,
607 struct nmb_name *nmbname,
608 uint16_t nb_flags,
609 struct in_addr register_ip,
610 struct in_addr wins_ip)
612 struct packet_struct *p;
613 struct response_record *rrec;
614 bool ret;
616 /* Sanity check. */
617 if(subrec != unicast_subnet) {
618 DEBUG(0,("queue_register_multihomed_name: should only be done on \
619 unicast subnet. subnet is %s\n.", subrec->subnet_name ));
620 return NULL;
623 if(assert_check_subnet(subrec))
624 return NULL;
626 if ((p = create_and_init_netbios_packet(nmbname, False, True, wins_ip)) == NULL)
627 return NULL;
629 if (nb_flags & NB_GROUP)
630 ret = initiate_name_register_packet( p, nb_flags, &register_ip);
631 else
632 ret = initiate_multihomed_name_register_packet(p, nb_flags, &register_ip);
634 if (ret == False) {
635 p->locked = False;
636 free_packet(p);
637 return NULL;
640 if ((rrec = make_response_record(subrec, /* subnet record. */
641 p, /* packet we sent. */
642 resp_fn, /* function to call on response. */
643 timeout_fn, /* function to call on timeout. */
644 (success_function)success_fn, /* function to call on operation success. */
645 (fail_function)fail_fn, /* function to call on operation fail. */
646 userdata)) == NULL) {
647 p->locked = False;
648 free_packet(p);
649 return NULL;
652 return rrec;
655 /****************************************************************************
656 Queue a release name packet to the broadcast address of a subnet.
657 ****************************************************************************/
659 struct response_record *queue_release_name( struct subnet_record *subrec,
660 response_function resp_fn,
661 timeout_response_function timeout_fn,
662 release_name_success_function success_fn,
663 release_name_fail_function fail_fn,
664 struct userdata_struct *userdata,
665 struct nmb_name *nmbname,
666 uint16_t nb_flags,
667 struct in_addr release_ip,
668 struct in_addr dest_ip)
670 struct packet_struct *p;
671 struct response_record *rrec;
673 if(assert_check_subnet(subrec))
674 return NULL;
676 if ((p = create_and_init_netbios_packet(nmbname, (subrec != unicast_subnet), False, dest_ip)) == NULL)
677 return NULL;
679 if(initiate_name_release_packet( p, nb_flags, &release_ip) == False) {
680 p->locked = False;
681 free_packet(p);
682 return NULL;
685 if((rrec = make_response_record(subrec, /* subnet record. */
686 p, /* packet we sent. */
687 resp_fn, /* function to call on response. */
688 timeout_fn, /* function to call on timeout. */
689 (success_function)success_fn, /* function to call on operation success. */
690 (fail_function)fail_fn, /* function to call on operation fail. */
691 userdata)) == NULL) {
692 p->locked = False;
693 free_packet(p);
694 return NULL;
698 * For a broadcast release packet, only send once.
699 * This will cause us to remove the name asap. JRA.
702 if (subrec != unicast_subnet) {
703 rrec->repeat_count = 0;
704 rrec->repeat_time = 0;
707 return rrec;
710 /****************************************************************************
711 Queue a query name packet to the broadcast address of a subnet.
712 ****************************************************************************/
714 struct response_record *queue_query_name( struct subnet_record *subrec,
715 response_function resp_fn,
716 timeout_response_function timeout_fn,
717 query_name_success_function success_fn,
718 query_name_fail_function fail_fn,
719 struct userdata_struct *userdata,
720 struct nmb_name *nmbname)
722 struct packet_struct *p;
723 struct response_record *rrec;
724 struct in_addr to_ip;
726 if(assert_check_subnet(subrec))
727 return NULL;
729 to_ip = subrec->bcast_ip;
731 /* queries to the WINS server turn up here as queries to IP 0.0.0.0
732 These need to be handled a bit differently */
733 if (subrec->type == UNICAST_SUBNET && is_zero_ip_v4(to_ip)) {
734 /* What we really need to do is loop over each of our wins
735 * servers and wins server tags here, but that just doesn't
736 * fit our architecture at the moment (userdata may already
737 * be used when we get here). For now we just query the first
738 * active wins server on the first tag.
740 char **tags = wins_srv_tags();
741 if (!tags) {
742 return NULL;
744 to_ip = wins_srv_ip_tag(tags[0], to_ip);
745 wins_srv_tags_free(tags);
748 if(( p = create_and_init_netbios_packet(nmbname,
749 (subrec != unicast_subnet),
750 (subrec == unicast_subnet),
751 to_ip)) == NULL)
752 return NULL;
754 if(lp_bind_interfaces_only()) {
755 int i;
757 DEBUG(10,("queue_query_name: bind_interfaces_only is set, looking for suitable source IP\n"));
758 for(i = 0; i < iface_count(); i++) {
759 const struct in_addr *ifip = iface_n_ip_v4(i);
761 if (ifip == NULL) {
762 DEBUG(0,("queue_query_name: interface %d has NULL IP address !\n", i));
763 continue;
766 if (is_loopback_ip_v4(*ifip)) {
767 DEBUG(5,("queue_query_name: ignoring loopback interface (%d)\n", i));
768 continue;
771 DEBUG(10,("queue_query_name: using source IP %s\n",inet_ntoa(*ifip)));
772 p->send_fd = find_subnet_fd_for_address( *ifip );
773 break;
777 if(initiate_name_query_packet( p ) == False) {
778 p->locked = False;
779 free_packet(p);
780 return NULL;
783 if((rrec = make_response_record(subrec, /* subnet record. */
784 p, /* packet we sent. */
785 resp_fn, /* function to call on response. */
786 timeout_fn, /* function to call on timeout. */
787 (success_function)success_fn, /* function to call on operation success. */
788 (fail_function)fail_fn, /* function to call on operation fail. */
789 userdata)) == NULL) {
790 p->locked = False;
791 free_packet(p);
792 return NULL;
795 return rrec;
798 /****************************************************************************
799 Queue a query name packet to a given address from the WINS subnet.
800 ****************************************************************************/
802 struct response_record *queue_query_name_from_wins_server( struct in_addr to_ip,
803 response_function resp_fn,
804 timeout_response_function timeout_fn,
805 query_name_success_function success_fn,
806 query_name_fail_function fail_fn,
807 struct userdata_struct *userdata,
808 struct nmb_name *nmbname)
810 struct packet_struct *p;
811 struct response_record *rrec;
813 if ((p = create_and_init_netbios_packet(nmbname, False, False, to_ip)) == NULL)
814 return NULL;
816 if(initiate_name_query_packet_from_wins_server( p ) == False) {
817 p->locked = False;
818 free_packet(p);
819 return NULL;
822 if((rrec = make_response_record(wins_server_subnet, /* subnet record. */
823 p, /* packet we sent. */
824 resp_fn, /* function to call on response. */
825 timeout_fn, /* function to call on timeout. */
826 (success_function)success_fn, /* function to call on operation success. */
827 (fail_function)fail_fn, /* function to call on operation fail. */
828 userdata)) == NULL) {
829 p->locked = False;
830 free_packet(p);
831 return NULL;
834 return rrec;
837 /****************************************************************************
838 Queue a node status packet to a given name and address.
839 ****************************************************************************/
841 struct response_record *queue_node_status( struct subnet_record *subrec,
842 response_function resp_fn,
843 timeout_response_function timeout_fn,
844 node_status_success_function success_fn,
845 node_status_fail_function fail_fn,
846 struct userdata_struct *userdata,
847 struct nmb_name *nmbname,
848 struct in_addr send_ip)
850 struct packet_struct *p;
851 struct response_record *rrec;
853 /* Sanity check. */
854 if(subrec != unicast_subnet) {
855 DEBUG(0,("queue_register_multihomed_name: should only be done on \
856 unicast subnet. subnet is %s\n.", subrec->subnet_name ));
857 return NULL;
860 if(assert_check_subnet(subrec))
861 return NULL;
863 if(( p = create_and_init_netbios_packet(nmbname, False, False, send_ip)) == NULL)
864 return NULL;
866 if(initiate_node_status_packet(p) == False) {
867 p->locked = False;
868 free_packet(p);
869 return NULL;
872 if((rrec = make_response_record(subrec, /* subnet record. */
873 p, /* packet we sent. */
874 resp_fn, /* function to call on response. */
875 timeout_fn, /* function to call on timeout. */
876 (success_function)success_fn, /* function to call on operation success. */
877 (fail_function)fail_fn, /* function to call on operation fail. */
878 userdata)) == NULL) {
879 p->locked = False;
880 free_packet(p);
881 return NULL;
884 return rrec;
887 /****************************************************************************
888 Reply to a netbios name packet. see rfc1002.txt
889 ****************************************************************************/
891 void reply_netbios_packet(struct packet_struct *orig_packet,
892 int rcode, enum netbios_reply_type_code rcv_code, int opcode,
893 int ttl, char *data,int len)
895 struct packet_struct packet;
896 struct nmb_packet *nmb = NULL;
897 struct res_rec answers;
898 struct nmb_packet *orig_nmb = &orig_packet->packet.nmb;
899 bool loopback_this_packet = False;
900 int rr_type = RR_TYPE_NB;
901 const char *packet_type = "unknown";
903 /* Check if we are sending to or from ourselves. */
904 if(ismyip_v4(orig_packet->ip) && (orig_packet->port == global_nmb_port))
905 loopback_this_packet = True;
907 nmb = &packet.packet.nmb;
909 /* Do a partial copy of the packet. We clear the locked flag and
910 the resource record pointers. */
911 packet = *orig_packet; /* Full structure copy. */
912 packet.locked = False;
913 nmb->answers = NULL;
914 nmb->nsrecs = NULL;
915 nmb->additional = NULL;
917 switch (rcv_code) {
918 case NMB_STATUS:
919 packet_type = "nmb_status";
920 nmb->header.nm_flags.recursion_desired = False;
921 nmb->header.nm_flags.recursion_available = False;
922 rr_type = RR_TYPE_NBSTAT;
923 break;
924 case NMB_QUERY:
925 packet_type = "nmb_query";
926 nmb->header.nm_flags.recursion_desired = True;
927 nmb->header.nm_flags.recursion_available = True;
928 if (rcode) {
929 rr_type = RR_TYPE_NULL;
931 break;
932 case NMB_REG:
933 case NMB_REG_REFRESH:
934 packet_type = "nmb_reg";
935 nmb->header.nm_flags.recursion_desired = True;
936 nmb->header.nm_flags.recursion_available = True;
937 break;
938 case NMB_REL:
939 packet_type = "nmb_rel";
940 nmb->header.nm_flags.recursion_desired = False;
941 nmb->header.nm_flags.recursion_available = False;
942 break;
943 case NMB_WAIT_ACK:
944 packet_type = "nmb_wack";
945 nmb->header.nm_flags.recursion_desired = False;
946 nmb->header.nm_flags.recursion_available = False;
947 rr_type = RR_TYPE_NULL;
948 break;
949 case WINS_REG:
950 packet_type = "wins_reg";
951 nmb->header.nm_flags.recursion_desired = True;
952 nmb->header.nm_flags.recursion_available = True;
953 break;
954 case WINS_QUERY:
955 packet_type = "wins_query";
956 nmb->header.nm_flags.recursion_desired = True;
957 nmb->header.nm_flags.recursion_available = True;
958 if (rcode) {
959 rr_type = RR_TYPE_NULL;
961 break;
962 default:
963 DEBUG(0,("reply_netbios_packet: Unknown packet type: %s %s to ip %s\n",
964 packet_type, nmb_namestr(&orig_nmb->question.question_name),
965 inet_ntoa(packet.ip)));
966 return;
969 DEBUG(4, ("reply_netbios_packet: sending a reply of packet type: %s "
970 "%s to ip %s for id %d\n", packet_type,
971 nmb_namestr(&orig_nmb->question.question_name),
972 inet_ntoa(packet.ip), orig_nmb->header.name_trn_id));
974 nmb->header.name_trn_id = orig_nmb->header.name_trn_id;
975 nmb->header.opcode = opcode;
976 nmb->header.response = True;
977 nmb->header.nm_flags.bcast = False;
978 nmb->header.nm_flags.trunc = False;
979 nmb->header.nm_flags.authoritative = True;
981 nmb->header.rcode = rcode;
982 nmb->header.qdcount = 0;
983 nmb->header.ancount = 1;
984 nmb->header.nscount = 0;
985 nmb->header.arcount = 0;
987 memset((char*)&nmb->question,'\0',sizeof(nmb->question));
989 nmb->answers = &answers;
990 memset((char*)nmb->answers,'\0',sizeof(*nmb->answers));
992 nmb->answers->rr_name = orig_nmb->question.question_name;
993 nmb->answers->rr_type = rr_type;
994 nmb->answers->rr_class = RR_CLASS_IN;
995 nmb->answers->ttl = ttl;
997 if (data && len) {
998 if (len < 0 || len > sizeof(nmb->answers->rdata)) {
999 DEBUG(5,("reply_netbios_packet: "
1000 "invalid packet len (%d)\n",
1001 len ));
1002 return;
1004 nmb->answers->rdlength = len;
1005 memcpy(nmb->answers->rdata, data, len);
1008 packet.packet_type = NMB_PACKET;
1009 packet.recv_fd = -1;
1010 /* Ensure we send out on the same fd that the original
1011 packet came in on to give the correct source IP address. */
1012 if (orig_packet->send_fd != -1) {
1013 packet.send_fd = orig_packet->send_fd;
1014 } else {
1015 packet.send_fd = orig_packet->recv_fd;
1017 packet.timestamp = time(NULL);
1019 debug_nmb_packet(&packet);
1021 if(loopback_this_packet) {
1022 struct packet_struct *lo_packet;
1023 DEBUG(5,("reply_netbios_packet: sending packet to ourselves.\n"));
1024 if((lo_packet = copy_packet(&packet)) == NULL)
1025 return;
1026 queue_packet(lo_packet);
1027 } else if (!send_packet(&packet)) {
1028 DEBUG(0,("reply_netbios_packet: send_packet to IP %s port %d failed\n",
1029 inet_ntoa(packet.ip),packet.port));
1033 /*******************************************************************
1034 Queue a packet into a packet queue
1035 ******************************************************************/
1037 void queue_packet(struct packet_struct *packet)
1039 DLIST_ADD_END(packet_queue, packet);
1042 /****************************************************************************
1043 Try and find a matching subnet record for a datagram port 138 packet.
1044 ****************************************************************************/
1046 static struct subnet_record *find_subnet_for_dgram_browse_packet(struct packet_struct *p)
1048 struct subnet_record *subrec;
1050 /* Go through all the broadcast subnets and see if the mask matches. */
1051 for (subrec = FIRST_SUBNET; subrec ; subrec = NEXT_SUBNET_EXCLUDING_UNICAST(subrec)) {
1052 if(same_net_v4(p->ip, subrec->bcast_ip, subrec->mask_ip))
1053 return subrec;
1056 /* If the subnet record is the remote announce broadcast subnet,
1057 hack it here to be the first subnet. This is really gross and
1058 is needed due to people turning on port 137/138 broadcast
1059 forwarding on their routers. May fire and brimstone rain
1060 down upon them...
1063 return FIRST_SUBNET;
1066 /****************************************************************************
1067 Dispatch a browse frame from port 138 to the correct processing function.
1068 ****************************************************************************/
1070 static void process_browse_packet(struct packet_struct *p, const char *buf,int len)
1072 struct dgram_packet *dgram = &p->packet.dgram;
1073 int command = CVAL(buf,0);
1074 struct subnet_record *subrec = find_subnet_for_dgram_browse_packet(p);
1075 char scope[64];
1076 unstring src_name;
1078 /* Drop the packet if it's a different NetBIOS scope, or the source is from one of our names. */
1079 pull_ascii(scope, dgram->dest_name.scope, 64, 64, STR_TERMINATE);
1080 if (!strequal(scope, lp_netbios_scope())) {
1081 DEBUG(7,("process_browse_packet: Discarding datagram from IP %s. Scope (%s) \
1082 mismatch with our scope (%s).\n", inet_ntoa(p->ip), scope, lp_netbios_scope()));
1083 return;
1086 pull_ascii_nstring(src_name, sizeof(src_name), dgram->source_name.name);
1087 if (is_myname(src_name)) {
1088 DEBUG(7,("process_browse_packet: Discarding datagram from IP %s. Source name \
1089 %s is one of our names !\n", inet_ntoa(p->ip), nmb_namestr(&dgram->source_name)));
1090 return;
1093 switch (command) {
1094 case ANN_HostAnnouncement:
1095 debug_browse_data(buf, len);
1096 process_host_announce(subrec, p, buf+1);
1097 break;
1098 case ANN_DomainAnnouncement:
1099 debug_browse_data(buf, len);
1100 process_workgroup_announce(subrec, p, buf+1);
1101 break;
1102 case ANN_LocalMasterAnnouncement:
1103 debug_browse_data(buf, len);
1104 process_local_master_announce(subrec, p, buf+1);
1105 break;
1106 case ANN_AnnouncementRequest:
1107 debug_browse_data(buf, len);
1108 process_announce_request(subrec, p, buf+1);
1109 break;
1110 case ANN_Election:
1111 debug_browse_data(buf, len);
1112 process_election(subrec, p, buf+1);
1113 break;
1114 case ANN_GetBackupListReq:
1115 debug_browse_data(buf, len);
1116 process_get_backup_list_request(subrec, p, buf+1);
1117 break;
1118 case ANN_GetBackupListResp:
1119 debug_browse_data(buf, len);
1120 /* We never send ANN_GetBackupListReq so we should never get these. */
1121 DEBUG(0,("process_browse_packet: Discarding GetBackupListResponse \
1122 packet from %s IP %s\n", nmb_namestr(&dgram->source_name), inet_ntoa(p->ip)));
1123 break;
1124 case ANN_ResetBrowserState:
1125 debug_browse_data(buf, len);
1126 process_reset_browser(subrec, p, buf+1);
1127 break;
1128 case ANN_MasterAnnouncement:
1129 /* Master browser datagrams must be processed on the unicast subnet. */
1130 subrec = unicast_subnet;
1132 debug_browse_data(buf, len);
1133 process_master_browser_announce(subrec, p, buf+1);
1134 break;
1135 case ANN_BecomeBackup:
1137 * We don't currently implement this. Log it just in case.
1139 debug_browse_data(buf, len);
1140 DEBUG(10,("process_browse_packet: On subnet %s ignoring browse packet \
1141 command ANN_BecomeBackup from %s IP %s to %s\n", subrec->subnet_name, nmb_namestr(&dgram->source_name),
1142 inet_ntoa(p->ip), nmb_namestr(&dgram->dest_name)));
1143 break;
1144 default:
1145 debug_browse_data(buf, len);
1146 DEBUG(0,("process_browse_packet: On subnet %s ignoring browse packet \
1147 command code %d from %s IP %s to %s\n", subrec->subnet_name, command, nmb_namestr(&dgram->source_name),
1148 inet_ntoa(p->ip), nmb_namestr(&dgram->dest_name)));
1149 break;
1153 /****************************************************************************
1154 Dispatch a LanMan browse frame from port 138 to the correct processing function.
1155 ****************************************************************************/
1157 static void process_lanman_packet(struct packet_struct *p, const char *buf,int len)
1159 struct dgram_packet *dgram = &p->packet.dgram;
1160 int command = SVAL(buf,0);
1161 struct subnet_record *subrec = find_subnet_for_dgram_browse_packet(p);
1162 char scope[64];
1163 unstring src_name;
1165 /* Drop the packet if it's a different NetBIOS scope, or the source is from one of our names. */
1167 pull_ascii(scope, dgram->dest_name.scope, 64, 64, STR_TERMINATE);
1168 if (!strequal(scope, lp_netbios_scope())) {
1169 DEBUG(7,("process_lanman_packet: Discarding datagram from IP %s. Scope (%s) \
1170 mismatch with our scope (%s).\n", inet_ntoa(p->ip), scope, lp_netbios_scope()));
1171 return;
1174 pull_ascii_nstring(src_name, sizeof(src_name), dgram->source_name.name);
1175 if (is_myname(src_name)) {
1176 DEBUG(0,("process_lanman_packet: Discarding datagram from IP %s. Source name \
1177 %s is one of our names !\n", inet_ntoa(p->ip), nmb_namestr(&dgram->source_name)));
1178 return;
1181 switch (command) {
1182 case ANN_HostAnnouncement:
1183 debug_browse_data(buf, len);
1184 process_lm_host_announce(subrec, p, buf+1, len > 1 ? len-1 : 0);
1185 break;
1186 case ANN_AnnouncementRequest:
1187 process_lm_announce_request(subrec, p, buf+1, len > 1 ? len-1 : 0);
1188 break;
1189 default:
1190 DEBUG(0,("process_lanman_packet: On subnet %s ignoring browse packet \
1191 command code %d from %s IP %s to %s\n", subrec->subnet_name, command, nmb_namestr(&dgram->source_name),
1192 inet_ntoa(p->ip), nmb_namestr(&dgram->dest_name)));
1193 break;
1197 /****************************************************************************
1198 Determine if a packet is for us on port 138. Note that to have any chance of
1199 being efficient we need to drop as many packets as possible at this
1200 stage as subsequent processing is expensive.
1201 ****************************************************************************/
1203 static bool listening(struct packet_struct *p,struct nmb_name *nbname)
1205 struct subnet_record *subrec = NULL;
1207 for (subrec = FIRST_SUBNET; subrec ; subrec = NEXT_SUBNET_EXCLUDING_UNICAST(subrec)) {
1208 if(same_net_v4(p->ip, subrec->bcast_ip, subrec->mask_ip))
1209 break;
1212 if(subrec == NULL)
1213 subrec = unicast_subnet;
1215 return (find_name_on_subnet(subrec, nbname, FIND_SELF_NAME) != NULL);
1218 /****************************************************************************
1219 Process udp 138 datagrams
1220 ****************************************************************************/
1222 static void process_dgram(struct packet_struct *p)
1224 const char *buf;
1225 const char *buf2;
1226 int len;
1227 struct dgram_packet *dgram = &p->packet.dgram;
1229 /* If we aren't listening to the destination name then ignore the packet */
1230 if (!listening(p,&dgram->dest_name)) {
1231 nb_packet_dispatch(packet_server, p);
1232 DEBUG(5,("process_dgram: ignoring dgram packet sent to name %s from %s\n",
1233 nmb_namestr(&dgram->dest_name), inet_ntoa(p->ip)));
1234 return;
1237 if (dgram->header.msg_type != 0x10 && dgram->header.msg_type != 0x11 && dgram->header.msg_type != 0x12) {
1238 nb_packet_dispatch(packet_server, p);
1239 /* Don't process error packets etc yet */
1240 DEBUG(5,("process_dgram: ignoring dgram packet sent to name %s from IP %s as it is \
1241 an error packet of type %x\n", nmb_namestr(&dgram->dest_name), inet_ntoa(p->ip), dgram->header.msg_type));
1242 return;
1245 /* Ensure we have a large enough packet before looking inside. */
1246 if (dgram->datasize < (smb_vwv12 - 2)) {
1247 /* That's the offset minus the 4 byte length + 2 bytes of offset. */
1248 DEBUG(0,("process_dgram: ignoring too short dgram packet (%u) sent to name %s from IP %s\n",
1249 (unsigned int)dgram->datasize,
1250 nmb_namestr(&dgram->dest_name),
1251 inet_ntoa(p->ip) ));
1252 return;
1255 buf = &dgram->data[0];
1256 buf -= 4; /* XXXX for the pseudo tcp length - someday I need to get rid of this */
1258 if (CVAL(buf,smb_com) != SMBtrans)
1259 return;
1261 len = SVAL(buf,smb_vwv11);
1262 buf2 = smb_base(buf) + SVAL(buf,smb_vwv12);
1264 if (len <= 0 || len > dgram->datasize) {
1265 DEBUG(0,("process_dgram: ignoring malformed1 (datasize = %d, len = %d) datagram \
1266 packet sent to name %s from IP %s\n",
1267 dgram->datasize,
1268 len,
1269 nmb_namestr(&dgram->dest_name),
1270 inet_ntoa(p->ip) ));
1271 return;
1274 if (buf2 < dgram->data || (buf2 >= dgram->data + dgram->datasize)) {
1275 DEBUG(0,("process_dgram: ignoring malformed2 (datasize = %d, len=%d, off=%d) datagram \
1276 packet sent to name %s from IP %s\n",
1277 dgram->datasize,
1278 len,
1279 (int)PTR_DIFF(buf2, dgram->data),
1280 nmb_namestr(&dgram->dest_name),
1281 inet_ntoa(p->ip) ));
1282 return;
1285 if ((buf2 + len < dgram->data) || (buf2 + len > dgram->data + dgram->datasize)) {
1286 DEBUG(0,("process_dgram: ignoring malformed3 (datasize = %d, len=%d, off=%d) datagram \
1287 packet sent to name %s from IP %s\n",
1288 dgram->datasize,
1289 len,
1290 (int)PTR_DIFF(buf2, dgram->data),
1291 nmb_namestr(&dgram->dest_name),
1292 inet_ntoa(p->ip) ));
1293 return;
1296 DEBUG(4,("process_dgram: datagram from %s to %s IP %s for %s of type %d len=%d\n",
1297 nmb_namestr(&dgram->source_name),nmb_namestr(&dgram->dest_name),
1298 inet_ntoa(p->ip), smb_buf_const(buf),CVAL(buf2,0),len));
1300 /* Datagram packet received for the browser mailslot */
1301 if (strequal(smb_buf_const(buf),BROWSE_MAILSLOT)) {
1302 process_browse_packet(p,buf2,len);
1303 return;
1306 /* Datagram packet received for the LAN Manager mailslot */
1307 if (strequal(smb_buf_const(buf),LANMAN_MAILSLOT)) {
1308 process_lanman_packet(p,buf2,len);
1309 return;
1312 /* Datagram packet received for the domain logon mailslot */
1313 if (strequal(smb_buf_const(buf),NET_LOGON_MAILSLOT)) {
1314 process_logon_packet(p,buf2,len,NET_LOGON_MAILSLOT);
1315 return;
1318 /* Datagram packet received for the NT domain logon mailslot */
1319 if (strequal(smb_buf_const(buf),NT_LOGON_MAILSLOT)) {
1320 process_logon_packet(p,buf2,len,NT_LOGON_MAILSLOT);
1321 return;
1324 nb_packet_dispatch(packet_server, p);
1327 /****************************************************************************
1328 Validate a response nmb packet.
1329 ****************************************************************************/
1331 static bool validate_nmb_response_packet( struct nmb_packet *nmb )
1333 bool ignore = False;
1335 switch (nmb->header.opcode) {
1336 case NMB_NAME_REG_OPCODE:
1337 case NMB_NAME_REFRESH_OPCODE_8: /* ambiguity in rfc1002 about which is correct. */
1338 case NMB_NAME_REFRESH_OPCODE_9: /* WinNT uses 8 by default. */
1339 if (nmb->header.ancount == 0) {
1340 DEBUG(0,("validate_nmb_response_packet: Bad REG/REFRESH Packet. "));
1341 ignore = True;
1343 break;
1345 case NMB_NAME_QUERY_OPCODE:
1346 if ((nmb->header.ancount != 0) && (nmb->header.ancount != 1)) {
1347 DEBUG(0,("validate_nmb_response_packet: Bad QUERY Packet. "));
1348 ignore = True;
1350 break;
1352 case NMB_NAME_RELEASE_OPCODE:
1353 if (nmb->header.ancount == 0) {
1354 DEBUG(0,("validate_nmb_response_packet: Bad RELEASE Packet. "));
1355 ignore = True;
1357 break;
1359 case NMB_WACK_OPCODE:
1360 /* Check WACK response here. */
1361 if (nmb->header.ancount != 1) {
1362 DEBUG(0,("validate_nmb_response_packet: Bad WACK Packet. "));
1363 ignore = True;
1365 break;
1366 default:
1367 DEBUG(0,("validate_nmb_response_packet: Ignoring packet with unknown opcode %d.\n",
1368 nmb->header.opcode));
1369 return True;
1372 if(ignore)
1373 DEBUG(0,("Ignoring response packet with opcode %d.\n", nmb->header.opcode));
1375 return ignore;
1378 /****************************************************************************
1379 Validate a request nmb packet.
1380 ****************************************************************************/
1382 static bool validate_nmb_packet( struct nmb_packet *nmb )
1384 bool ignore = False;
1386 switch (nmb->header.opcode) {
1387 case NMB_NAME_REG_OPCODE:
1388 case NMB_NAME_REFRESH_OPCODE_8: /* ambiguity in rfc1002 about which is correct. */
1389 case NMB_NAME_REFRESH_OPCODE_9: /* WinNT uses 8 by default. */
1390 case NMB_NAME_MULTIHOMED_REG_OPCODE:
1391 if (nmb->header.qdcount==0 || nmb->header.arcount==0) {
1392 DEBUG(0,("validate_nmb_packet: Bad REG/REFRESH Packet. "));
1393 ignore = True;
1395 break;
1397 case NMB_NAME_QUERY_OPCODE:
1398 if ((nmb->header.qdcount == 0) || ((nmb->question.question_type != QUESTION_TYPE_NB_QUERY) &&
1399 (nmb->question.question_type != QUESTION_TYPE_NB_STATUS))) {
1400 DEBUG(0,("validate_nmb_packet: Bad QUERY Packet. "));
1401 ignore = True;
1403 break;
1405 case NMB_NAME_RELEASE_OPCODE:
1406 if (nmb->header.qdcount==0 || nmb->header.arcount==0) {
1407 DEBUG(0,("validate_nmb_packet: Bad RELEASE Packet. "));
1408 ignore = True;
1410 break;
1411 default:
1412 DEBUG(0,("validate_nmb_packet: Ignoring packet with unknown opcode %d.\n",
1413 nmb->header.opcode));
1414 return True;
1417 if(ignore)
1418 DEBUG(0,("validate_nmb_packet: Ignoring request packet with opcode %d.\n", nmb->header.opcode));
1420 return ignore;
1423 /****************************************************************************
1424 Find a subnet (and potentially a response record) for a packet.
1425 ****************************************************************************/
1427 static struct subnet_record *find_subnet_for_nmb_packet( struct packet_struct *p,
1428 struct response_record **pprrec)
1430 struct nmb_packet *nmb = &p->packet.nmb;
1431 struct response_record *rrec = NULL;
1432 struct subnet_record *subrec = NULL;
1434 if(pprrec != NULL)
1435 *pprrec = NULL;
1437 if(nmb->header.response) {
1438 /* It's a response packet. Find a record for it or it's an error. */
1440 rrec = find_response_record( &subrec, nmb->header.name_trn_id);
1441 if(rrec == NULL) {
1442 DEBUG(3, ("find_subnet_for_nmb_packet: response "
1443 "record not found for response id %d\n",
1444 nmb->header.name_trn_id));
1445 nb_packet_dispatch(packet_server, p);
1446 return NULL;
1449 if(subrec == NULL) {
1450 DEBUG(0, ("find_subnet_for_nmb_packet: subnet record "
1451 "not found for response id %d\n",
1452 nmb->header.name_trn_id));
1453 return NULL;
1456 if(pprrec != NULL)
1457 *pprrec = rrec;
1458 return subrec;
1461 /* Try and see what subnet this packet belongs to. */
1463 /* WINS server ? */
1464 if(packet_is_for_wins_server(p))
1465 return wins_server_subnet;
1467 /* If it wasn't a broadcast packet then send to the UNICAST subnet. */
1468 if(nmb->header.nm_flags.bcast == False)
1469 return unicast_subnet;
1471 /* Go through all the broadcast subnets and see if the mask matches. */
1472 for (subrec = FIRST_SUBNET; subrec ; subrec = NEXT_SUBNET_EXCLUDING_UNICAST(subrec)) {
1473 if(same_net_v4(p->ip, subrec->bcast_ip, subrec->mask_ip))
1474 return subrec;
1477 /* If none match it must have been a directed broadcast - assign the remote_broadcast_subnet. */
1478 return remote_broadcast_subnet;
1481 /****************************************************************************
1482 Process a nmb request packet - validate the packet and route it.
1483 ****************************************************************************/
1485 static void process_nmb_request(struct packet_struct *p)
1487 struct nmb_packet *nmb = &p->packet.nmb;
1488 struct subnet_record *subrec = NULL;
1490 debug_nmb_packet(p);
1492 /* Ensure we have a good packet. */
1493 if(validate_nmb_packet(nmb))
1494 return;
1496 /* Allocate a subnet to this packet - if we cannot - fail. */
1497 if((subrec = find_subnet_for_nmb_packet(p, NULL))==NULL)
1498 return;
1500 switch (nmb->header.opcode) {
1501 case NMB_NAME_REG_OPCODE:
1502 if(subrec == wins_server_subnet)
1503 wins_process_name_registration_request(subrec, p);
1504 else
1505 process_name_registration_request(subrec, p);
1506 break;
1508 case NMB_NAME_REFRESH_OPCODE_8: /* ambiguity in rfc1002 about which is correct. */
1509 case NMB_NAME_REFRESH_OPCODE_9:
1510 if(subrec == wins_server_subnet)
1511 wins_process_name_refresh_request(subrec, p);
1512 else
1513 process_name_refresh_request(subrec, p);
1514 break;
1516 case NMB_NAME_MULTIHOMED_REG_OPCODE:
1517 if(subrec == wins_server_subnet) {
1518 wins_process_multihomed_name_registration_request(subrec, p);
1519 } else {
1520 DEBUG(0,("process_nmb_request: Multihomed registration request must be \
1521 directed at a WINS server.\n"));
1523 break;
1525 case NMB_NAME_QUERY_OPCODE:
1526 switch (nmb->question.question_type) {
1527 case QUESTION_TYPE_NB_QUERY:
1528 if(subrec == wins_server_subnet)
1529 wins_process_name_query_request(subrec, p);
1530 else
1531 process_name_query_request(subrec, p);
1532 break;
1533 case QUESTION_TYPE_NB_STATUS:
1534 if(subrec == wins_server_subnet) {
1535 DEBUG(0,("process_nmb_request: NB_STATUS request directed at WINS server is \
1536 not allowed.\n"));
1537 break;
1538 } else {
1539 process_node_status_request(subrec, p);
1541 break;
1543 break;
1545 case NMB_NAME_RELEASE_OPCODE:
1546 if(subrec == wins_server_subnet)
1547 wins_process_name_release_request(subrec, p);
1548 else
1549 process_name_release_request(subrec, p);
1550 break;
1554 /****************************************************************************
1555 Process a nmb response packet - validate the packet and route it.
1556 to either the WINS server or a normal response.
1557 ****************************************************************************/
1559 static void process_nmb_response(struct packet_struct *p)
1561 struct nmb_packet *nmb = &p->packet.nmb;
1562 struct subnet_record *subrec = NULL;
1563 struct response_record *rrec = NULL;
1565 debug_nmb_packet(p);
1567 if(validate_nmb_response_packet(nmb))
1568 return;
1570 if((subrec = find_subnet_for_nmb_packet(p, &rrec))==NULL)
1571 return;
1573 if(rrec == NULL) {
1574 DEBUG(0, ("process_nmb_response: response packet received but "
1575 "no response record found for id = %d. Ignoring "
1576 "packet.\n", nmb->header.name_trn_id));
1577 return;
1580 /* Increment the number of responses received for this record. */
1581 rrec->num_msgs++;
1582 /* Ensure we don't re-send the request. */
1583 rrec->repeat_count = 0;
1585 /* Call the response received function for this packet. */
1586 (*rrec->resp_fn)(subrec, rrec, p);
1589 /*******************************************************************
1590 Run elements off the packet queue till its empty
1591 ******************************************************************/
1593 void run_packet_queue(void)
1595 struct packet_struct *p;
1597 while ((p = packet_queue)) {
1598 DLIST_REMOVE(packet_queue, p);
1600 switch (p->packet_type) {
1601 case NMB_PACKET:
1602 if(p->packet.nmb.header.response)
1603 process_nmb_response(p);
1604 else
1605 process_nmb_request(p);
1606 break;
1608 case DGRAM_PACKET:
1609 process_dgram(p);
1610 break;
1612 free_packet(p);
1616 /*******************************************************************
1617 Retransmit or timeout elements from all the outgoing subnet response
1618 record queues. NOTE that this code must also check the WINS server
1619 subnet for response records to timeout as the WINS server code
1620 can send requests to check if a client still owns a name.
1621 (Patch from Andrey Alekseyev <fetch@muffin.arcadia.spb.ru>).
1622 ******************************************************************/
1624 void retransmit_or_expire_response_records(time_t t)
1626 struct subnet_record *subrec;
1628 for (subrec = FIRST_SUBNET; subrec; subrec = get_next_subnet_maybe_unicast_or_wins_server(subrec)) {
1629 struct response_record *rrec, *nextrrec;
1631 restart:
1633 for (rrec = subrec->responselist; rrec; rrec = nextrrec) {
1634 nextrrec = rrec->next;
1636 if (rrec->repeat_time <= t) {
1637 if (rrec->repeat_count > 0) {
1638 /* Resend while we have a non-zero repeat_count. */
1639 if(!send_packet(rrec->packet)) {
1640 DEBUG(0,("retransmit_or_expire_response_records: Failed to resend packet id %hu \
1641 to IP %s on subnet %s\n", rrec->response_id, inet_ntoa(rrec->packet->ip), subrec->subnet_name));
1643 rrec->repeat_time = t + rrec->repeat_interval;
1644 rrec->repeat_count--;
1645 } else {
1646 DEBUG(4,("retransmit_or_expire_response_records: timeout for packet id %hu to IP %s \
1647 on subnet %s\n", rrec->response_id, inet_ntoa(rrec->packet->ip), subrec->subnet_name));
1650 * Check the flag in this record to prevent recursion if we end
1651 * up in this function again via the timeout function call.
1654 if(!rrec->in_expiration_processing) {
1657 * Set the recursion protection flag in this record.
1660 rrec->in_expiration_processing = True;
1662 /* Call the timeout function. This will deal with removing the
1663 timed out packet. */
1664 if(rrec->timeout_fn) {
1665 (*rrec->timeout_fn)(subrec, rrec);
1666 } else {
1667 /* We must remove the record ourself if there is
1668 no timeout function. */
1669 remove_response_record(subrec, rrec);
1671 /* We have changed subrec->responselist,
1672 * restart from the beginning of this list. */
1673 goto restart;
1674 } /* !rrec->in_expitation_processing */
1675 } /* rrec->repeat_count > 0 */
1676 } /* rrec->repeat_time <= t */
1677 } /* end for rrec */
1678 } /* end for subnet */
1681 /****************************************************************************
1682 Create an fd_set containing all the sockets in the subnet structures,
1683 plus the broadcast sockets.
1684 ***************************************************************************/
1686 struct socket_attributes {
1687 enum packet_type type;
1688 bool broadcast;
1689 int fd;
1690 bool triggered;
1693 static bool create_listen_array(struct socket_attributes **pattrs,
1694 int *pnum_sockets)
1696 struct subnet_record *subrec = NULL;
1697 int count = 0;
1698 int num = 0;
1699 struct socket_attributes *attrs;
1701 /* The ClientNMB and ClientDGRAM sockets */
1702 count = 2;
1704 /* Check that we can add all the fd's we need. */
1705 for (subrec = FIRST_SUBNET;
1706 subrec != NULL;
1707 subrec = NEXT_SUBNET_EXCLUDING_UNICAST(subrec)) {
1708 if (subrec->nmb_sock != -1) {
1709 count += 1;
1711 if (subrec->dgram_sock != -1) {
1712 count += 1;
1714 if (subrec->nmb_bcast != -1) {
1715 count += 1;
1717 if (subrec->dgram_bcast != -1) {
1718 count += 1;
1722 attrs = talloc_zero_array(NULL, struct socket_attributes, count);
1723 if (attrs == NULL) {
1724 DEBUG(1, ("talloc fail for attrs. "
1725 "size %d\n", count));
1726 return true;
1729 num = 0;
1731 attrs[num].fd = ClientNMB;
1732 attrs[num].type = NMB_PACKET;
1733 attrs[num].broadcast = false;
1734 num += 1;
1736 attrs[num].fd = ClientDGRAM;
1737 attrs[num].type = DGRAM_PACKET;
1738 attrs[num].broadcast = false;
1739 num += 1;
1741 for (subrec = FIRST_SUBNET; subrec; subrec = NEXT_SUBNET_EXCLUDING_UNICAST(subrec)) {
1743 if (subrec->nmb_sock != -1) {
1744 attrs[num].fd = subrec->nmb_sock;
1745 attrs[num].type = NMB_PACKET;
1746 attrs[num].broadcast = false;
1747 num += 1;
1750 if (subrec->nmb_bcast != -1) {
1751 attrs[num].fd = subrec->nmb_bcast;
1752 attrs[num].type = NMB_PACKET;
1753 attrs[num].broadcast = true;
1754 num += 1;
1757 if (subrec->dgram_sock != -1) {
1758 attrs[num].fd = subrec->dgram_sock;
1759 attrs[num].type = DGRAM_PACKET;
1760 attrs[num].broadcast = false;
1761 num += 1;
1764 if (subrec->dgram_bcast != -1) {
1765 attrs[num].fd = subrec->dgram_bcast;
1766 attrs[num].type = DGRAM_PACKET;
1767 attrs[num].broadcast = true;
1768 num += 1;
1772 TALLOC_FREE(*pattrs);
1773 *pattrs = attrs;
1775 *pnum_sockets = count;
1777 return False;
1780 /****************************************************************************
1781 List of packets we're processing this select.
1782 ***************************************************************************/
1784 struct processed_packet {
1785 struct processed_packet *next;
1786 struct processed_packet *prev;
1787 enum packet_type packet_type;
1788 struct in_addr ip;
1789 int packet_id;
1792 /****************************************************************************
1793 Have we seen this before ?
1794 ***************************************************************************/
1796 static bool is_processed_packet(struct processed_packet *processed_packet_list,
1797 struct packet_struct *packet)
1799 struct processed_packet *p = NULL;
1801 for (p = processed_packet_list; p; p = p->next) {
1802 if (ip_equal_v4(p->ip, packet->ip) && p->packet_type == packet->packet_type) {
1803 if ((p->packet_type == NMB_PACKET) &&
1804 (p->packet_id ==
1805 packet->packet.nmb.header.name_trn_id)) {
1806 return true;
1807 } else if ((p->packet_type == DGRAM_PACKET) &&
1808 (p->packet_id ==
1809 packet->packet.dgram.header.dgm_id)) {
1810 return true;
1814 return false;
1817 /****************************************************************************
1818 Keep a list of what we've seen before.
1819 ***************************************************************************/
1821 static bool store_processed_packet(struct processed_packet **pp_processed_packet_list,
1822 struct packet_struct *packet)
1824 struct processed_packet *p = SMB_MALLOC_P(struct processed_packet);
1825 if (!p) {
1826 return false;
1828 p->packet_type = packet->packet_type;
1829 p->ip = packet->ip;
1830 if (packet->packet_type == NMB_PACKET) {
1831 p->packet_id = packet->packet.nmb.header.name_trn_id;
1832 } else if (packet->packet_type == DGRAM_PACKET) {
1833 p->packet_id = packet->packet.dgram.header.dgm_id;
1834 } else {
1835 SAFE_FREE(p);
1836 return false;
1839 DLIST_ADD(*pp_processed_packet_list, p);
1840 return true;
1843 /****************************************************************************
1844 Throw away what we've seen before.
1845 ***************************************************************************/
1847 static void free_processed_packet_list(struct processed_packet **pp_processed_packet_list)
1849 struct processed_packet *p = NULL, *next = NULL;
1851 for (p = *pp_processed_packet_list; p; p = next) {
1852 next = p->next;
1853 DLIST_REMOVE(*pp_processed_packet_list, p);
1854 SAFE_FREE(p);
1858 /****************************************************************************
1859 Timeout callback - just notice we timed out.
1860 ***************************************************************************/
1862 static void nmbd_timeout_handler(struct tevent_context *ev,
1863 struct tevent_timer *te,
1864 struct timeval current_time,
1865 void *private_data)
1867 bool *got_timeout = private_data;
1868 *got_timeout = true;
1871 /****************************************************************************
1872 fd callback - remember the fd that triggered.
1873 ***************************************************************************/
1875 static void nmbd_fd_handler(struct tevent_context *ev,
1876 struct tevent_fd *fde,
1877 uint16_t flags,
1878 void *private_data)
1880 struct socket_attributes *attr = private_data;
1881 attr->triggered = true;
1884 /****************************************************************************
1885 Read from a socket.
1886 ****************************************************************************/
1888 static ssize_t read_udp_v4_socket(
1889 int fd,
1890 char *buf,
1891 size_t len,
1892 struct sockaddr_storage *psa)
1894 ssize_t ret;
1895 socklen_t socklen = sizeof(*psa);
1896 struct sockaddr_in *si = (struct sockaddr_in *)psa;
1898 memset((char *)psa,'\0',socklen);
1900 ret = (ssize_t)sys_recvfrom(fd,buf,len,0,
1901 (struct sockaddr *)psa,&socklen);
1902 if (ret <= 0) {
1903 /* Don't print a low debug error for a non-blocking socket. */
1904 if (errno == EAGAIN) {
1905 DEBUG(10,("read_udp_v4_socket: returned EAGAIN\n"));
1906 } else {
1907 DEBUG(2,("read_udp_v4_socket: failed. errno=%s\n",
1908 strerror(errno)));
1910 return 0;
1913 if (psa->ss_family != AF_INET) {
1914 DEBUG(2,("read_udp_v4_socket: invalid address family %d "
1915 "(not IPv4)\n", (int)psa->ss_family));
1916 return 0;
1919 DEBUG(10,("read_udp_v4_socket: ip %s port %d read: %lu\n",
1920 inet_ntoa(si->sin_addr),
1921 si->sin_port,
1922 (unsigned long)ret));
1924 return ret;
1927 /*******************************************************************
1928 Read a packet from a socket and parse it, returning a packet ready
1929 to be used or put on the queue. This assumes a UDP socket.
1930 ******************************************************************/
1932 static struct packet_struct *read_packet(int fd,enum packet_type packet_type)
1934 struct packet_struct *packet;
1935 struct sockaddr_storage sa;
1936 struct sockaddr_in *si = (struct sockaddr_in *)&sa;
1937 char buf[MAX_DGRAM_SIZE];
1938 int length;
1940 length = read_udp_v4_socket(fd,buf,sizeof(buf),&sa);
1941 if (length < MIN_DGRAM_SIZE || sa.ss_family != AF_INET) {
1942 return NULL;
1945 packet = parse_packet(buf,
1946 length,
1947 packet_type,
1948 si->sin_addr,
1949 ntohs(si->sin_port));
1950 if (!packet)
1951 return NULL;
1953 packet->recv_fd = fd;
1954 packet->send_fd = -1;
1956 DEBUG(5,("Received a packet of len %d from (%s) port %d\n",
1957 length, inet_ntoa(packet->ip), packet->port ) );
1959 return(packet);
1962 /****************************************************************************
1963 Listens for NMB or DGRAM packets, and queues them.
1964 return True if the socket is dead
1965 ***************************************************************************/
1967 bool listen_for_packets(struct messaging_context *msg, bool run_election)
1969 static struct socket_attributes *attrs = NULL;
1970 static int listen_number = 0;
1971 int num_sockets;
1972 int i;
1973 int loop_rtn;
1974 int timeout_secs;
1976 #ifndef SYNC_DNS
1977 int dns_fd;
1978 int dns_pollidx = -1;
1979 #endif
1980 struct processed_packet *processed_packet_list = NULL;
1981 struct tevent_timer *te = NULL;
1982 bool got_timeout = false;
1983 TALLOC_CTX *frame = talloc_stackframe();
1985 if ((attrs == NULL) || rescan_listen_set) {
1986 if (create_listen_array(&attrs, &listen_number)) {
1987 DEBUG(0,("listen_for_packets: Fatal error. unable to create listen set. Exiting.\n"));
1988 TALLOC_FREE(frame);
1989 return True;
1991 rescan_listen_set = False;
1994 num_sockets = listen_number;
1996 #ifndef SYNC_DNS
1997 dns_fd = asyncdns_fd();
1998 if (dns_fd != -1) {
1999 attrs = talloc_realloc(NULL,
2000 attrs,
2001 struct socket_attributes,
2002 num_sockets + 1);
2003 if (attrs == NULL) {
2004 TALLOC_FREE(frame);
2005 return true;
2007 dns_pollidx = num_sockets;
2008 attrs[dns_pollidx].fd = dns_fd;
2010 * dummy values, we only need
2011 * fd and triggered.
2013 attrs[dns_pollidx].type = NMB_PACKET;
2014 attrs[dns_pollidx].broadcast = false;
2015 num_sockets += 1;
2017 #endif
2019 for (i=0; i<num_sockets; i++) {
2020 struct tevent_fd *tfd = tevent_add_fd(nmbd_event_context(),
2021 frame,
2022 attrs[i].fd,
2023 TEVENT_FD_READ,
2024 nmbd_fd_handler,
2025 &attrs[i]);
2026 if (tfd == NULL) {
2027 TALLOC_FREE(frame);
2028 return true;
2030 attrs[i].triggered = false;
2034 * During elections and when expecting a netbios response packet we
2035 * need to send election packets at tighter intervals.
2036 * Ideally it needs to be the interval (in ms) between time now and
2037 * the time we are expecting the next netbios packet.
2040 if (run_election||num_response_packets) {
2041 timeout_secs = 1;
2042 } else {
2043 timeout_secs = NMBD_SELECT_LOOP;
2046 te = tevent_add_timer(nmbd_event_context(),
2047 frame,
2048 tevent_timeval_current_ofs(timeout_secs, 0),
2049 nmbd_timeout_handler,
2050 &got_timeout);
2051 if (te == NULL) {
2052 TALLOC_FREE(frame);
2053 return true;
2056 loop_rtn = tevent_loop_once(nmbd_event_context());
2058 if (loop_rtn == -1) {
2059 TALLOC_FREE(frame);
2060 return true;
2063 if (got_timeout) {
2064 TALLOC_FREE(frame);
2065 return false;
2068 #ifndef SYNC_DNS
2069 if ((dns_fd != -1) && (dns_pollidx != -1) &&
2070 attrs[dns_pollidx].triggered){
2071 run_dns_queue(msg);
2072 TALLOC_FREE(frame);
2073 return false;
2075 #endif
2077 for(i = 0; i < listen_number; i++) {
2078 enum packet_type packet_type;
2079 struct packet_struct *packet;
2080 const char *packet_name;
2081 int client_fd;
2082 int client_port;
2084 if (!attrs[i].triggered) {
2085 continue;
2088 if (attrs[i].type == NMB_PACKET) {
2089 /* Port 137 */
2090 packet_type = NMB_PACKET;
2091 packet_name = "nmb";
2092 client_fd = ClientNMB;
2093 client_port = global_nmb_port;
2094 } else {
2095 /* Port 138 */
2096 packet_type = DGRAM_PACKET;
2097 packet_name = "dgram";
2098 client_fd = ClientDGRAM;
2099 client_port = DGRAM_PORT;
2102 packet = read_packet(attrs[i].fd, packet_type);
2103 if (!packet) {
2104 continue;
2108 * If we got a packet on the broadcast socket and interfaces
2109 * only is set then check it came from one of our local nets.
2111 if (lp_bind_interfaces_only() &&
2112 (attrs[i].fd == client_fd) &&
2113 (!is_local_net_v4(packet->ip))) {
2114 DEBUG(7,("discarding %s packet sent to broadcast socket from %s:%d\n",
2115 packet_name, inet_ntoa(packet->ip), packet->port));
2116 free_packet(packet);
2117 continue;
2120 if (!IS_DC) {
2121 if ((is_loopback_ip_v4(packet->ip) || ismyip_v4(packet->ip)) &&
2122 packet->port == client_port)
2124 if (client_port == DGRAM_PORT) {
2125 DEBUG(7,("discarding own dgram packet from %s:%d\n",
2126 inet_ntoa(packet->ip),packet->port));
2127 free_packet(packet);
2128 continue;
2131 if (packet->packet.nmb.header.nm_flags.bcast) {
2132 DEBUG(7,("discarding own nmb bcast packet from %s:%d\n",
2133 inet_ntoa(packet->ip),packet->port));
2134 free_packet(packet);
2135 continue;
2140 if (is_processed_packet(processed_packet_list, packet)) {
2141 DEBUG(7,("discarding duplicate packet from %s:%d\n",
2142 inet_ntoa(packet->ip),packet->port));
2143 free_packet(packet);
2144 continue;
2147 store_processed_packet(&processed_packet_list, packet);
2149 if (attrs[i].broadcast) {
2150 /* this is a broadcast socket */
2151 packet->send_fd = attrs[i-1].fd;
2152 } else {
2153 /* this is already a unicast socket */
2154 packet->send_fd = attrs[i].fd;
2157 queue_packet(packet);
2160 free_processed_packet_list(&processed_packet_list);
2161 TALLOC_FREE(frame);
2162 return False;
2165 /****************************************************************************
2166 Construct and send a netbios DGRAM.
2167 **************************************************************************/
2169 bool send_mailslot(bool unique, const char *mailslot,char *buf, size_t len,
2170 const char *srcname, int src_type,
2171 const char *dstname, int dest_type,
2172 struct in_addr dest_ip,struct in_addr src_ip,
2173 int dest_port)
2175 bool loopback_this_packet = False;
2176 struct packet_struct p;
2177 struct dgram_packet *dgram = &p.packet.dgram;
2178 char *ptr,*p2;
2179 char tmp[4];
2181 memset((char *)&p,'\0',sizeof(p));
2183 if(ismyip_v4(dest_ip) && (dest_port == DGRAM_PORT)) /* Only if to DGRAM_PORT */
2184 loopback_this_packet = True;
2186 /* generate_name_trn_id(); */ /* Not used, so gone, RJS */
2188 /* DIRECT GROUP or UNIQUE datagram. */
2189 dgram->header.msg_type = unique ? 0x10 : 0x11;
2190 dgram->header.flags.node_type = M_NODE;
2191 dgram->header.flags.first = True;
2192 dgram->header.flags.more = False;
2193 dgram->header.dgm_id = generate_name_trn_id();
2194 dgram->header.source_ip = src_ip;
2195 dgram->header.source_port = DGRAM_PORT;
2196 dgram->header.dgm_length = 0; /* Let build_dgram() handle this. */
2197 dgram->header.packet_offset = 0;
2199 make_nmb_name(&dgram->source_name,srcname,src_type);
2200 make_nmb_name(&dgram->dest_name,dstname,dest_type);
2202 ptr = &dgram->data[0];
2204 /* Setup the smb part. */
2205 ptr -= 4; /* XXX Ugliness because of handling of tcp SMB length. */
2206 memcpy(tmp,ptr,4);
2208 if (smb_size + 17*2 + strlen(mailslot) + 1 + len > MAX_DGRAM_SIZE) {
2209 DEBUG(0, ("send_mailslot: Cannot write beyond end of packet\n"));
2210 return false;
2213 cli_set_message(ptr,17,strlen(mailslot) + 1 + len,True);
2214 memcpy(ptr,tmp,4);
2216 SCVAL(ptr,smb_com,SMBtrans);
2217 SSVAL(ptr,smb_vwv1,len);
2218 SSVAL(ptr,smb_vwv11,len);
2219 SSVAL(ptr,smb_vwv12,70 + strlen(mailslot));
2220 SSVAL(ptr,smb_vwv13,3);
2221 SSVAL(ptr,smb_vwv14,1);
2222 SSVAL(ptr,smb_vwv15,1);
2223 SSVAL(ptr,smb_vwv16,2);
2224 p2 = smb_buf(ptr);
2225 strlcpy_base(p2, mailslot, dgram->data, sizeof(dgram->data));
2226 p2 = skip_string(ptr,MAX_DGRAM_SIZE,p2);
2228 if (((p2+len) > dgram->data+sizeof(dgram->data)) || ((p2+len) < p2)) {
2229 DEBUG(0, ("send_mailslot: Cannot write beyond end of packet\n"));
2230 return False;
2231 } else {
2232 if (len) {
2233 memcpy(p2,buf,len);
2235 p2 += len;
2238 dgram->datasize = PTR_DIFF(p2,ptr+4); /* +4 for tcp length. */
2240 p.ip = dest_ip;
2241 p.port = dest_port;
2242 p.recv_fd = -1;
2243 p.send_fd = find_subnet_mailslot_fd_for_address( src_ip );
2244 p.timestamp = time(NULL);
2245 p.packet_type = DGRAM_PACKET;
2247 DEBUG(4,("send_mailslot: Sending to mailslot %s from %s IP %s ", mailslot,
2248 nmb_namestr(&dgram->source_name), inet_ntoa(src_ip)));
2249 DEBUG(4,("to %s IP %s\n", nmb_namestr(&dgram->dest_name), inet_ntoa(dest_ip)));
2251 debug_browse_data(buf, len);
2253 if(loopback_this_packet) {
2254 struct packet_struct *lo_packet = NULL;
2255 DEBUG(5,("send_mailslot: sending packet to ourselves.\n"));
2256 if((lo_packet = copy_packet(&p)) == NULL)
2257 return False;
2258 queue_packet(lo_packet);
2259 return True;
2260 } else {
2261 return(send_packet(&p));