4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
22 * Copyright 2010 Sun Microsystems, Inc. All rights reserved.
23 * Use is subject to license terms.
24 * Copyright (c) 2016 by Delphix. All rights reserved.
28 * NetBIOS name resolution node types.
30 * A B-node (broadcast node) uses broadcasts for name registration
31 * and resolution. Routers typically do not forward broadcasts and
32 * only computers on the local subnet will respond.
34 * A P-node (peer-to-peer node) uses a NetBIOS name server (WINS)
35 * to resolve NetBIOS names, which allows it to work across routers.
36 * In order to function in a P-node environment, all computers must
37 * be configured to use the NetBIOS name server because P-nodes do
38 * not broadcast on the network.
40 * A mixed node (M-node) behaves as a B-node by default. If it cannot
41 * resolve the name via broadcast then it tries a NetBIOS name server
44 * A hybrid node (H-node) behaves as a P-node by default. If it cannot
45 * resolve the name using a NetBIOS name server then it resorts to
46 * broadcasts (B-node).
48 * NetBIOS Name Service Protocols
50 * A REQUEST packet is always sent to the well known UDP port 137.
51 * The destination address is normally either the IP broadcast address or
52 * the address of the NAME - the address of the NAME server it set up at
53 * initialization time. In rare cases, a request packet will be sent to
54 * an end node, e.g. a NAME QUERY REQUEST sent to "challenge" a node.
56 * A RESPONSE packet is always sent to the source UDP port and source IP
57 * address of the request packet.
59 * A DEMAND packet must always be sent to the well known UDP port 137.
60 * There is no restriction on the target IP address.
62 * A transaction ID is a value composed from the requestor's IP address and
63 * a unique 16 bit value generated by the originator of the transaction.
72 #include <sys/socket.h>
73 #include <sys/sockio.h>
74 #include <arpa/inet.h>
75 #include <net/if_arp.h>
77 #include <smbsrv/libsmbns.h>
78 #include <smbns_netbios.h>
81 * RFC 1002 4.2.1.1. HEADER
83 #define QUESTION_TYPE_NETBIOS_GENERAL 0x20
84 #define QUESTION_TYPE_NETBIOS_STATUS 0x21
86 #define QUESTION_CLASS_INTERNET 0x0001
89 * RFC 1002 4.2.1.3. RESOURCE RECORD
91 #define RR_TYPE_IP_ADDRESS_RESOURCE 0x0001
92 #define RR_TYPE_NAME_SERVER_RESOURCE 0x0002
93 #define RR_TYPE_NULL_RESOURCE 0x000A
94 #define RR_TYPE_NETBIOS_RESOURCE 0x0020
95 #define RR_TYPE_NETBIOS_STATUS 0x0021
99 * RESOURCE RECORD RR_CLASS field definitions
101 #define RR_CLASS_INTERNET_CLASS 0x0001
104 * NB_FLAGS field of the RESOURCE RECORD RDATA field for RR_TYPE of NB.
106 #define RR_FLAGS_NB_ONT_MASK 0x6000
107 #define RR_FLAGS_NB_ONT_B_NODE 0x0000
108 #define RR_FLAGS_NB_ONT_P_NODE 0x2000
109 #define RR_FLAGS_NB_ONT_M_NODE 0x4000
110 #define RR_FLAGS_NB_ONT_RESERVED 0x6000
111 #define RR_FLAGS_NB_GROUP_NAME 0x8000
113 #define NAME_FLAGS_PERMANENT_NAME 0x0200
114 #define NAME_FLAGS_ACTIVE_NAME 0x0400
115 #define NAME_FLAGS_CONFLICT 0x0800
116 #define NAME_FLAGS_DEREGISTER 0x1000
117 #define NAME_FLAGS_ONT_MASK 0x6000
118 #define NAME_FLAGS_ONT_B_NODE 0x0000
119 #define NAME_FLAGS_ONT_P_NODE 0x2000
120 #define NAME_FLAGS_ONT_M_NODE 0x4000
121 #define NAME_FLAGS_ONT_RESERVED 0x6000
122 #define NAME_FLAGS_GROUP_NAME 0x8000
124 #define MAX_NETBIOS_REPLY_DATA_SIZE 500
126 #define NAME_HEADER_SIZE 12
128 typedef struct nbt_name_reply
{
129 struct nbt_name_reply
*forw
;
130 struct nbt_name_reply
*back
;
131 struct name_packet
*packet
;
133 uint16_t name_trn_id
;
134 boolean_t reply_ready
;
137 static nbt_name_reply_t reply_queue
;
138 static mutex_t rq_mtx
;
141 static mutex_t nbt_name_config_mtx
;
143 static name_queue_t delete_queue
;
144 static name_queue_t refresh_queue
;
146 static int name_sock
= 0;
148 static int bcast_num
= 0;
149 static int nbns_num
= 0;
150 static addr_entry_t smb_bcast_list
[SMB_PI_MAX_NETWORKS
];
151 static addr_entry_t smb_nbns
[SMB_PI_MAX_WINS
];
153 static int smb_netbios_process_response(uint16_t, addr_entry_t
*,
154 struct name_packet
*, uint32_t);
156 static int smb_send_name_service_packet(addr_entry_t
*addr
,
157 struct name_packet
*packet
);
160 * Allocate a transaction id.
163 smb_netbios_name_trn_id(void)
165 static uint16_t trn_id
;
166 static mutex_t trn_id_mtx
;
168 (void) mutex_lock(&trn_id_mtx
);
172 } while (trn_id
== 0 || trn_id
== (uint16_t)-1);
174 (void) mutex_unlock(&trn_id_mtx
);
179 smb_end_node_challenge(nbt_name_reply_t
*reply_info
)
184 struct resource_record
*answer
;
185 struct name_question question
;
187 struct name_entry
*destination
;
188 struct name_packet packet
;
192 * The response packet has in it the address of the presumed owner
193 * of the name. Challenge that owner. If owner either does not
194 * respond or indicates that they no longer own the name, claim the
195 * name. Otherwise, the name cannot be claimed.
198 if ((answer
= reply_info
->packet
->answer
) == 0)
201 destination
= answer
->name
;
202 question
.name
= answer
->name
;
204 packet
.info
= NAME_QUERY_REQUEST
| NM_FLAGS_UNICAST
;
205 packet
.qdcount
= 1; /* question entries */
206 packet
.question
= &question
;
207 packet
.ancount
= 0; /* answer recs */
208 packet
.answer
= NULL
;
209 packet
.nscount
= 0; /* authority recs */
210 packet
.authority
= NULL
;
211 packet
.arcount
= 0; /* additional recs */
212 packet
.additional
= NULL
;
214 addr
= &destination
->addr_list
;
215 for (retry
= 0; retry
< UCAST_REQ_RETRY_COUNT
; retry
++) {
216 tid
= smb_netbios_name_trn_id();
217 packet
.name_trn_id
= tid
;
218 if (smb_send_name_service_packet(addr
, &packet
) >= 0) {
219 if ((rc
= smb_netbios_process_response(tid
, addr
,
220 &packet
, UCAST_REQ_RETRY_TIMEOUT
)) != 0)
224 st
.tv_nsec
= (UCAST_REQ_RETRY_TIMEOUT
* 1000000);
225 (void) nanosleep(&st
, 0);
231 static nbt_name_reply_t
*
232 smb_name_get_reply(uint16_t tid
, uint32_t timeout
)
235 struct resource_record
*answer
;
236 nbt_name_reply_t
*reply
;
237 uint32_t wait_time
, to_save
; /* in millisecond */
242 reply
= malloc(sizeof (nbt_name_reply_t
));
244 reply
->reply_ready
= B_FALSE
;
245 reply
->name_trn_id
= tid
;
246 (void) mutex_lock(&rq_mtx
);
247 QUEUE_INSERT_TAIL(&reply_queue
, reply
);
248 (void) mutex_unlock(&rq_mtx
);
251 (void) gettimeofday(&wt
, 0);
252 wait_time
= wt
.tv_usec
/ 1000;
255 to
.tv_nsec
= timeout
* 1000000;
256 (void) mutex_lock(&rq_mtx
);
257 (void) cond_reltimedwait(&rq_cv
, &rq_mtx
, &to
);
258 (void) mutex_unlock(&rq_mtx
);
260 if (reply
->reply_ready
) {
261 info
= reply
->packet
->info
;
262 if (PACKET_TYPE(info
) == WACK_RESPONSE
) {
263 answer
= reply
->packet
->answer
;
264 wait_time
= (answer
) ?
265 TO_MILLISECONDS(answer
->ttl
) :
269 timeout
= to_save
+ wait_time
;
270 reply
->reply_ready
= B_FALSE
;
271 reply
->name_trn_id
= tid
;
272 (void) mutex_lock(&rq_mtx
);
273 QUEUE_INSERT_TAIL(&reply_queue
, reply
);
274 (void) mutex_unlock(&rq_mtx
);
279 (void) gettimeofday(&wt
, 0);
280 wait_time
= (wt
.tv_usec
/ 1000) - wait_time
;
281 if (wait_time
>= timeout
) {
282 (void) mutex_lock(&rq_mtx
);
284 (void) mutex_unlock(&rq_mtx
);
288 timeout
-= wait_time
;
296 smb_reply_ready(struct name_packet
*packet
, addr_entry_t
*addr
)
298 nbt_name_reply_t
*reply
;
299 struct resource_record
*answer
;
301 (void) mutex_lock(&rq_mtx
);
302 for (reply
= reply_queue
.forw
; reply
!= &reply_queue
;
303 reply
= reply
->forw
) {
304 if (reply
->name_trn_id
== packet
->name_trn_id
) {
308 reply
->packet
= packet
;
309 reply
->reply_ready
= B_TRUE
;
310 (void) cond_signal(&rq_cv
);
311 (void) mutex_unlock(&rq_mtx
);
315 (void) mutex_unlock(&rq_mtx
);
317 /* Presumably nobody is waiting any more... */
320 answer
= packet
->answer
;
322 smb_netbios_name_freeaddrs(answer
->name
);
327 smb_netbios_process_response(uint16_t tid
, addr_entry_t
*addr
,
328 struct name_packet
*packet
, uint32_t timeout
)
332 nbt_name_reply_t
*reply
;
333 struct resource_record
*answer
;
334 struct name_entry
*name
;
335 struct name_entry
*entry
;
336 struct name_question
*question
;
339 if ((reply
= smb_name_get_reply(tid
, timeout
)) == 0) {
340 return (0); /* No reply: retry */
342 info
= reply
->packet
->info
;
343 answer
= reply
->packet
->answer
;
346 switch (PACKET_TYPE(info
)) {
347 case NAME_QUERY_RESPONSE
:
348 if (POSITIVE_RESPONSE(info
)) {
349 addr
= &answer
->name
->addr_list
;
352 * Make sure that remote name is not
355 addr
->attributes
&= ~NAME_ATTR_LOCAL
;
358 addr
->ttl
= answer
->ttl
;
360 addr
->ttl
= DEFAULT_TTL
;
361 addr
->refresh_ttl
= TO_SECONDS(addr
->ttl
);
362 addr
->ttl
= addr
->refresh_ttl
;
365 } while (addr
!= &answer
->name
->addr_list
);
366 smb_netbios_name_logf(answer
->name
);
367 (void) smb_netbios_cache_insert_list(answer
->name
);
374 case NAME_REGISTRATION_RESPONSE
:
375 if (NEGATIVE_RESPONSE(info
)) {
376 if (RCODE(info
) == RCODE_CFT_ERR
) {
383 entry
= smb_netbios_cache_lookup(name
);
386 * a name in the state "conflict
387 * detected" does not "logically" exist
388 * on that node. No further session
389 * will be accepted on that name.
390 * No datagrams can be sent against
392 * Such an entry will not be used for
393 * purposes of processing incoming
395 * The only valid user NetBIOS operation
396 * against such a name is DELETE NAME.
398 entry
->attributes
|= NAME_ATTR_CONFLICT
;
400 "nbns: name conflict: %15.15s",
402 smb_netbios_cache_unlock_entry(entry
);
411 * adjust refresh timeout value,
414 question
= packet
->question
;
415 ttl
= (answer
&& answer
->ttl
) ? answer
->ttl
: DEFAULT_TTL
;
416 ttl
= TO_SECONDS(ttl
);
417 if ((entry
= smb_netbios_cache_lookup(question
->name
)) != 0) {
418 addr
= &entry
->addr_list
;
420 if ((addr
->refresh_ttl
== 0) ||
421 (ttl
< addr
->refresh_ttl
))
422 addr
->refresh_ttl
= addr
->ttl
= ttl
;
424 } while (addr
!= &entry
->addr_list
);
425 smb_netbios_cache_unlock_entry(entry
);
431 case NAME_RELEASE_RESPONSE
:
435 case END_NODE_CHALLENGE_REGISTRATION_REQUEST
:
437 * The response packet has in it the
438 * address of the presumed owner of the
439 * name. Challenge that owner. If
440 * owner either does not respond or
441 * indicates that they no longer own the
442 * name, claim the name. Otherwise,
443 * the name cannot be claimed.
445 rc
= smb_end_node_challenge(reply
);
454 smb_netbios_name_freeaddrs(answer
->name
);
458 return (rc
); /* retry */
462 * smb_name_buf_from_packet
465 * Convert a NetBIOS Name Server Packet Block (npb)
466 * into the bits and bytes destined for the wire.
467 * The "buf" is used as a heap.
470 * char * buf -> Buffer, from the wire
471 * unsigned n_buf -> Length of 'buf'
472 * name_packet *npb -> Packet block, decode into
473 * unsigned n_npb -> Max bytes in 'npb'
476 * >0 -> Encode successful, value is length of packet in "buf"
477 * -1 -> Hard error, can not possibly encode
478 * -2 -> Need more memory in buf -- it's too small
481 smb_name_buf_from_packet(unsigned char *buf
, int n_buf
,
482 struct name_packet
*npb
)
485 unsigned char *heap
= buf
;
486 unsigned char *end_heap
= heap
+ n_buf
;
487 unsigned char comp_name_buf
[MAX_NAME_LENGTH
];
491 if (n_buf
< NAME_HEADER_SIZE
)
492 return (-1); /* no header, impossible */
494 BE_OUT16(heap
, npb
->name_trn_id
);
497 BE_OUT16(heap
, npb
->info
);
500 BE_OUT16(heap
, npb
->qdcount
);
503 BE_OUT16(heap
, npb
->ancount
);
506 BE_OUT16(heap
, npb
->nscount
);
509 BE_OUT16(heap
, npb
->arcount
);
512 for (i
= 0; i
< npb
->qdcount
; i
++) {
513 if ((heap
+ 34 + 4) > end_heap
)
516 (void) smb_first_level_name_encode(npb
->question
[i
].name
,
517 comp_name_buf
, sizeof (comp_name_buf
));
518 (void) strcpy((char *)heap
, (char *)comp_name_buf
);
519 heap
+= strlen((char *)comp_name_buf
) + 1;
521 BE_OUT16(heap
, npb
->question
[i
].question_type
);
524 BE_OUT16(heap
, npb
->question
[i
].question_class
);
528 for (step
= 1; step
<= 3; step
++) {
529 struct resource_record
*nrr
;
532 /* truly ugly, but saves code copying */
536 } else if (step
== 2) {
538 nrr
= npb
->authority
;
539 } else { /* step == 3 */
541 nrr
= npb
->additional
;
544 for (i
= 0; i
< n
; i
++) {
545 if ((heap
+ 34 + 10) > end_heap
)
548 (void) smb_first_level_name_encode(nrr
->name
,
549 comp_name_buf
, sizeof (comp_name_buf
));
550 (void) strcpy((char *)heap
, (char *)comp_name_buf
);
551 heap
+= strlen((char *)comp_name_buf
) + 1;
553 BE_OUT16(heap
, nrr
[i
].rr_type
);
556 BE_OUT16(heap
, nrr
[i
].rr_class
);
559 BE_OUT32(heap
, nrr
[i
].ttl
);
562 BE_OUT16(heap
, nrr
[i
].rdlength
);
565 if ((tmp
= nrr
[i
].rdlength
) > 0) {
566 if ((heap
+ tmp
) > end_heap
)
569 if (nrr
[i
].rr_type
== NAME_RR_TYPE_NB
&&
570 nrr
[i
].rr_class
== NAME_RR_CLASS_IN
&&
571 tmp
>= 6 && nrr
[i
].rdata
== 0) {
572 tmp
= nrr
[i
].name
->attributes
&
574 NAME_ATTR_OWNER_NODE_TYPE
);
578 raddr
= &nrr
[i
].name
->addr_list
;
580 &raddr
->sin
.sin_addr
.s_addr
,
584 bcopy(nrr
[i
].rdata
, heap
, tmp
);
596 * Lookup for character 'c' in first 'n' chars of string 's'.
597 * Returns pointer to the found char, otherwise returns 0.
600 strnchr(const char *s
, char c
, int n
)
602 char *ps
= (char *)s
;
603 char *es
= (char *)s
+ n
;
605 while (ps
< es
&& *ps
) {
612 if (*ps
== '\0' && c
== '\0')
619 is_multihome(char *name
)
621 return (smb_nic_getnum(name
) > 1);
625 * smb_netbios_getname
627 * Get the Netbios name part of the given record.
628 * Does some boundary checks.
630 * Returns the name length on success, otherwise
634 smb_netbios_getname(char *name
, char *buf
, char *buf_end
)
639 if (buf
>= buf_end
) {
640 /* no room for a NB name */
644 name_end
= strnchr(buf
, '\0', buf_end
- buf
+ 1);
646 /* not a valid NB name */
650 name_len
= name_end
- buf
+ 1;
652 (void) strlcpy(name
, buf
, name_len
);
657 * smb_name_buf_to_packet
659 * Convert the bits and bytes that came from the wire into a NetBIOS
660 * Name Server Packet Block (npb). The "block" is used as a heap.
662 * Returns a pointer to a name packet on success. Otherwise, returns
665 static struct name_packet
*
666 smb_name_buf_to_packet(char *buf
, int n_buf
)
668 struct name_packet
*npb
;
670 unsigned char *scan
= (unsigned char *)buf
;
671 unsigned char *scan_end
= scan
+ n_buf
;
672 char name_buf
[MAX_NAME_LENGTH
];
673 struct resource_record
*nrr
= 0;
674 int rc
, i
, n
, nn
, ns
;
675 uint16_t name_trn_id
, info
;
676 uint16_t qdcount
, ancount
, nscount
, arcount
;
680 if (n_buf
< NAME_HEADER_SIZE
) {
681 /* truncated header */
682 syslog(LOG_DEBUG
, "nbns: short packet (%d bytes)", n_buf
);
686 name_trn_id
= BE_IN16(scan
); scan
+= 2;
687 info
= BE_IN16(scan
); scan
+= 2;
688 qdcount
= BE_IN16(scan
); scan
+= 2;
689 ancount
= BE_IN16(scan
); scan
+= 2;
690 nscount
= BE_IN16(scan
); scan
+= 2;
691 arcount
= BE_IN16(scan
); scan
+= 2;
693 ns
= sizeof (struct name_entry
);
694 n
= n_buf
+ sizeof (struct name_packet
) +
695 ((unsigned)qdcount
* (sizeof (struct name_question
) + ns
)) +
696 ((unsigned)ancount
* (sizeof (struct resource_record
) + ns
)) +
697 ((unsigned)nscount
* (sizeof (struct resource_record
) + ns
)) +
698 ((unsigned)arcount
* (sizeof (struct resource_record
) + ns
));
700 if ((npb
= malloc(n
)) == NULL
)
704 heap
= npb
->block_data
;
705 npb
->name_trn_id
= name_trn_id
;
707 npb
->qdcount
= qdcount
;
708 npb
->ancount
= ancount
;
709 npb
->nscount
= nscount
;
710 npb
->arcount
= arcount
;
712 /* scan is in position for question entries */
715 * Measure the space needed for the tables
718 /* LINTED - E_BAD_PTR_CAST_ALIGN */
719 npb
->question
= (struct name_question
*)heap
;
720 heap
+= qdcount
* sizeof (struct name_question
);
721 for (i
= 0; i
< qdcount
; i
++) {
722 /* LINTED - E_BAD_PTR_CAST_ALIGN */
723 npb
->question
[i
].name
= (struct name_entry
*)heap
;
724 heap
+= sizeof (struct name_entry
);
728 /* LINTED - E_BAD_PTR_CAST_ALIGN */
729 nrr
= (struct resource_record
*)heap
;
732 /* LINTED - E_BAD_PTR_CAST_ALIGN */
733 npb
->answer
= (struct resource_record
*)heap
;
734 heap
+= ancount
* sizeof (struct resource_record
);
738 /* LINTED - E_BAD_PTR_CAST_ALIGN */
739 npb
->authority
= (struct resource_record
*)heap
;
740 heap
+= nscount
* sizeof (struct resource_record
);
744 /* LINTED - E_BAD_PTR_CAST_ALIGN */
745 npb
->additional
= (struct resource_record
*)heap
;
746 heap
+= arcount
* sizeof (struct resource_record
);
750 * Populate each resource_record's .name field.
751 * Done as a second pass so that all resource records
752 * (answer, authority, additional) are consecutive via nrr[i].
754 for (i
= 0; i
< (ancount
+ nscount
+ arcount
); i
++) {
755 /* LINTED - E_BAD_PTR_CAST_ALIGN */
756 nrr
[i
].name
= (struct name_entry
*)heap
;
757 heap
+= sizeof (struct name_entry
);
761 for (i
= 0; i
< npb
->qdcount
; i
++) {
762 name_len
= smb_netbios_getname(name_buf
, (char *)scan
,
769 smb_init_name_struct(NETBIOS_EMPTY_NAME
, 0, 0, 0, 0, 0, 0,
770 npb
->question
[i
].name
);
771 rc
= smb_first_level_name_decode((unsigned char *)name_buf
,
772 npb
->question
[i
].name
);
774 /* Couldn't decode the question name */
780 if (scan
+ 4 > scan_end
) {
781 /* no room for Question Type(2) and Class(2) fields */
786 npb
->question
[i
].question_type
= BE_IN16(scan
); scan
+= 2;
787 npb
->question
[i
].question_class
= BE_IN16(scan
); scan
+= 2;
791 * Cheat. Remaining sections are of the same resource_record
792 * format. Table space is consecutive.
795 for (i
= 0; i
< (ancount
+ nscount
+ arcount
); i
++) {
796 if (scan
[0] == 0xc0) {
797 /* Namebuf is reused... */
800 name_len
= smb_netbios_getname(name_buf
, (char *)scan
,
810 if (scan
+ 10 > scan_end
) {
812 * no room for RR_TYPE (2), RR_CLASS (2), TTL (4) and
813 * RDLENGTH (2) fields.
819 smb_init_name_struct(NETBIOS_EMPTY_NAME
, 0, 0, 0, 0, 0, 0,
821 if ((rc
= smb_first_level_name_decode((unsigned char *)name_buf
,
827 nrr
[i
].rr_type
= BE_IN16(scan
); scan
+= 2;
828 nrr
[i
].rr_class
= BE_IN16(scan
); scan
+= 2;
829 nrr
[i
].ttl
= BE_IN32(scan
); scan
+= 4;
830 nrr
[i
].rdlength
= BE_IN16(scan
); scan
+= 2;
832 if ((n
= nrr
[i
].rdlength
) > 0) {
833 if ((scan
+ n
) > scan_end
) {
834 /* no room for RDATA */
838 bcopy(scan
, heap
, n
);
841 if (nrr
[i
].rr_type
== 0x0020 &&
842 nrr
[i
].rr_class
== 0x01 && n
>= 6) {
845 next
= &nrr
[i
].name
->addr_list
;
848 sizeof (addr_entry_t
));
850 /* not enough memory */
855 &nrr
[i
].name
->addr_list
,
858 nrr
[i
].name
->attributes
=
860 next
->sin
.sin_family
= AF_INET
;
861 next
->sinlen
= sizeof (next
->sin
);
863 &next
->sin
.sin_addr
.s_addr
,
864 scan
+ 2, sizeof (uint32_t));
866 htons(IPPORT_NETBIOS_DGM
);
881 * smb_send_name_service_packet
885 * Send out a name service packet to proper destination.
888 * struct netbios_name *dest -> NETBIOS name of destination
889 * struct name_packet *packet -> Packet to send
896 smb_send_name_service_packet(addr_entry_t
*addr
, struct name_packet
*packet
)
898 unsigned char buf
[MAX_DATAGRAM_LENGTH
];
901 if ((len
= smb_name_buf_from_packet(buf
, sizeof (buf
), packet
)) < 0) {
906 return (sendto(name_sock
, buf
, len
, MSG_EOR
,
907 (struct sockaddr
*)&addr
->sin
, addr
->sinlen
));
911 * smb_netbios_send_rcv
913 * This function sends the given NetBIOS packet to the given
914 * address and get back the response. If send operation is not
915 * successful, it's repeated 'retries' times.
918 * 0 Unsuccessful send operation; no reply
922 smb_netbios_send_rcv(int bcast
, addr_entry_t
*destination
,
923 struct name_packet
*packet
, uint32_t retries
, uint32_t timeout
)
930 for (retry
= 0; retry
< retries
; retry
++) {
931 if ((destination
->flags
& ADDR_FLAG_VALID
) == 0)
934 tid
= smb_netbios_name_trn_id();
935 packet
->name_trn_id
= tid
;
936 if (smb_send_name_service_packet(destination
, packet
) >= 0) {
937 rc
= smb_netbios_process_response(tid
, destination
,
940 if ((rc
> 0) || (bcast
== BROADCAST
))
948 st
.tv_nsec
= (timeout
* 1000000);
949 (void) nanosleep(&st
, 0);
956 * RFC 1002 4.2.2. NAME REGISTRATION REQUEST
959 smb_send_name_registration_request(int bcast
, struct name_question
*question
,
960 struct resource_record
*additional
)
965 addr_entry_t
*destination
;
966 struct name_packet packet
;
970 type
= question
->name
->name
[15];
971 if ((type
!= NBT_WKSTA
) && (type
!= NBT_SERVER
)) {
972 syslog(LOG_DEBUG
, "nbns: name registration bad type (0x%02x)",
974 smb_netbios_name_logf(question
->name
);
975 question
->name
->attributes
&= ~NAME_ATTR_LOCAL
;
979 if (bcast
== BROADCAST
) {
982 destination
= smb_bcast_list
;
983 addr_num
= bcast_num
;
984 retries
= BCAST_REQ_RETRY_COUNT
;
985 timeout
= BCAST_REQ_RETRY_TIMEOUT
;
986 packet
.info
= NAME_REGISTRATION_REQUEST
| NM_FLAGS_BROADCAST
;
990 destination
= smb_nbns
;
992 retries
= UCAST_REQ_RETRY_COUNT
;
993 timeout
= UCAST_REQ_RETRY_TIMEOUT
;
994 packet
.info
= NAME_REGISTRATION_REQUEST
| NM_FLAGS_UNICAST
;
997 packet
.qdcount
= 1; /* question entries */
998 packet
.question
= question
;
999 packet
.ancount
= 0; /* answer recs */
1000 packet
.answer
= NULL
;
1001 packet
.nscount
= 0; /* authority recs */
1002 packet
.authority
= NULL
;
1003 packet
.arcount
= 1; /* additional recs */
1004 packet
.additional
= additional
;
1006 if (IS_UNIQUE(question
->name
->attributes
) &&
1007 (is_multihome((char *)(question
->name
->name
))))
1008 packet
.info
|= NAME_MULTIHOME_REGISTRATION_REQUEST
;
1010 for (i
= 0; i
< addr_num
; i
++) {
1012 * Only register with the Primary WINS server,
1013 * unless we got no reply.
1015 if ((bcast
== UNICAST
) && gotreply
)
1018 rc
= smb_netbios_send_rcv(bcast
, &destination
[i
], &packet
,
1028 * RFC 1002 4.2.4. NAME REFRESH REQUEST
1032 smb_send_name_refresh_request(int bcast
, struct name_question
*question
,
1033 struct resource_record
*additional
, int force
)
1040 addr_entry_t
*destination
;
1041 struct name_packet packet
;
1043 int i
, addr_num
, q_addrs
= 0;
1045 type
= question
->name
->name
[15];
1046 if ((type
!= NBT_WKSTA
) && (type
!= NBT_SERVER
)) {
1047 syslog(LOG_DEBUG
, "nbns: name refresh bad type (0x%02x)", type
);
1048 smb_netbios_name_logf(question
->name
);
1049 question
->name
->attributes
&= ~NAME_ATTR_LOCAL
;
1056 destination
= smb_bcast_list
;
1057 addr_num
= bcast_num
;
1058 retries
= BCAST_REQ_RETRY_COUNT
;
1059 timeout
= BCAST_REQ_RETRY_TIMEOUT
;
1060 packet
.info
= NAME_REFRESH_REQUEST
| NM_FLAGS_BROADCAST
;
1066 destination
= smb_nbns
;
1067 addr_num
= nbns_num
;
1068 retries
= UCAST_REQ_RETRY_COUNT
;
1069 timeout
= UCAST_REQ_RETRY_TIMEOUT
;
1070 packet
.info
= NAME_REFRESH_REQUEST
| NM_FLAGS_UNICAST
;
1074 destination
= &question
->name
->addr_list
;
1076 * the value of addr_num is irrelvant here, because
1077 * the code is going to do special_process so it doesn't
1078 * need the addr_num. We set a value here just to avoid
1082 retries
= UCAST_REQ_RETRY_COUNT
;
1083 timeout
= UCAST_REQ_RETRY_TIMEOUT
;
1084 packet
.info
= NAME_REFRESH_REQUEST
| NM_FLAGS_UNICAST
;
1089 if (IS_UNIQUE(question
->name
->attributes
) &&
1090 (is_multihome((char *)(question
->name
->name
))))
1091 packet
.info
|= NAME_MULTIHOME_REGISTRATION_REQUEST
;
1093 packet
.qdcount
= 1; /* question entries */
1094 packet
.question
= question
;
1095 packet
.ancount
= 0; /* answer recs */
1096 packet
.answer
= NULL
;
1097 packet
.nscount
= 0; /* authority recs */
1098 packet
.authority
= NULL
;
1099 packet
.arcount
= 1; /* additional recs */
1100 packet
.additional
= additional
;
1103 goto special_process
;
1105 for (i
= 0; i
< addr_num
; i
++) {
1106 rc
= smb_netbios_send_rcv(bcast
, &destination
[i
], &packet
,
1117 rc
= smb_netbios_send_rcv(bcast
, addr
, &packet
,
1122 } while (addr
!= destination
);
1128 * RFC 1002 4.2.5. POSITIVE NAME REGISTRATION RESPONSE
1129 * RFC 1002 4.2.6. NEGATIVE NAME REGISTRATION RESPONSE
1132 smb_send_name_registration_response(addr_entry_t
*addr
,
1133 struct name_packet
*original_packet
, uint16_t rcode
)
1135 struct name_packet packet
;
1136 struct resource_record answer
;
1138 bzero(&packet
, sizeof (struct name_packet
));
1139 bzero(&answer
, sizeof (struct resource_record
));
1141 packet
.name_trn_id
= original_packet
->name_trn_id
;
1142 packet
.info
= NAME_REGISTRATION_RESPONSE
| NAME_NM_FLAGS_RA
|
1143 (rcode
& NAME_RCODE_MASK
);
1144 packet
.qdcount
= 0; /* question entries */
1145 packet
.question
= NULL
;
1146 packet
.ancount
= 1; /* answer recs */
1147 packet
.answer
= &answer
;
1148 packet
.nscount
= 0; /* authority recs */
1149 packet
.authority
= NULL
;
1150 packet
.arcount
= 0; /* additional recs */
1151 packet
.additional
= NULL
;
1153 answer
.name
= original_packet
->question
->name
;
1154 answer
.rr_type
= NAME_QUESTION_TYPE_NB
;
1155 answer
.rr_class
= NAME_QUESTION_CLASS_IN
;
1156 answer
.ttl
= original_packet
->additional
->ttl
;
1157 answer
.rdlength
= original_packet
->additional
->rdlength
;
1158 answer
.rdata
= original_packet
->additional
->rdata
;
1160 return (smb_send_name_service_packet(addr
, &packet
));
1164 * RFC 1002 4.2.9. NAME RELEASE REQUEST & DEMAND
1167 smb_send_name_release_request_and_demand(int bcast
,
1168 struct name_question
*question
, struct resource_record
*additional
)
1175 addr_entry_t
*destination
;
1176 struct name_packet packet
;
1178 if (bcast
== BROADCAST
) {
1181 destination
= smb_bcast_list
;
1182 addr_num
= bcast_num
;
1183 retries
= 1; /* BCAST_REQ_RETRY_COUNT */
1184 timeout
= 100; /* BCAST_REQ_RETRY_TIMEOUT */
1185 packet
.info
= NAME_RELEASE_REQUEST
| NM_FLAGS_BROADCAST
;
1189 destination
= smb_nbns
;
1190 addr_num
= nbns_num
;
1191 retries
= 1; /* UCAST_REQ_RETRY_COUNT */
1192 timeout
= 100; /* UCAST_REQ_RETRY_TIMEOUT */
1193 packet
.info
= NAME_RELEASE_REQUEST
| NM_FLAGS_UNICAST
;
1196 packet
.qdcount
= 1; /* question entries */
1197 packet
.question
= question
;
1198 packet
.ancount
= 0; /* answer recs */
1199 packet
.answer
= NULL
;
1200 packet
.nscount
= 0; /* authority recs */
1201 packet
.authority
= NULL
;
1202 packet
.arcount
= 1; /* additional recs */
1203 packet
.additional
= additional
;
1205 for (i
= 0; i
< addr_num
; i
++) {
1206 rc
= smb_netbios_send_rcv(bcast
, &destination
[i
], &packet
,
1216 * RFC 1002 4.2.10. POSITIVE NAME RELEASE RESPONSE
1217 * RFC 1002 4.2.11. NEGATIVE NAME RELEASE RESPONSE
1220 /* LINTED - E_STATIC_UNUSED */
1221 smb_send_name_release_response(addr_entry_t
*addr
,
1222 struct name_packet
*original_packet
, uint16_t rcode
)
1224 struct name_packet packet
;
1225 struct resource_record answer
;
1227 bzero(&packet
, sizeof (struct name_packet
));
1228 bzero(&answer
, sizeof (struct resource_record
));
1230 packet
.name_trn_id
= original_packet
->name_trn_id
;
1231 packet
.info
= NAME_RELEASE_RESPONSE
| (rcode
& NAME_RCODE_MASK
);
1232 packet
.qdcount
= 0; /* question entries */
1233 packet
.question
= NULL
;
1234 packet
.ancount
= 1; /* answer recs */
1235 packet
.answer
= &answer
;
1236 packet
.nscount
= 0; /* authority recs */
1237 packet
.authority
= NULL
;
1238 packet
.arcount
= 0; /* additional recs */
1239 packet
.additional
= NULL
;
1241 answer
.name
= original_packet
->question
->name
;
1242 answer
.rr_type
= NAME_QUESTION_TYPE_NB
;
1243 answer
.rr_class
= NAME_QUESTION_CLASS_IN
;
1244 answer
.ttl
= original_packet
->additional
->ttl
;
1245 answer
.rdlength
= original_packet
->additional
->rdlength
;
1246 answer
.rdata
= original_packet
->additional
->rdata
;
1248 return (smb_send_name_service_packet(addr
, &packet
));
1252 * RFC 1002 4.2.12. NAME QUERY REQUEST
1255 smb_send_name_query_request(int bcast
, struct name_question
*question
)
1258 uint32_t retry
, retries
;
1261 addr_entry_t
*destination
;
1262 struct name_packet packet
;
1266 if (bcast
== BROADCAST
) {
1269 destination
= smb_bcast_list
;
1270 addr_num
= bcast_num
;
1271 retries
= BCAST_REQ_RETRY_COUNT
;
1272 timeout
= BCAST_REQ_RETRY_TIMEOUT
;
1273 packet
.info
= NAME_QUERY_REQUEST
| NM_FLAGS_BROADCAST
;
1277 destination
= smb_nbns
;
1278 addr_num
= nbns_num
;
1279 retries
= UCAST_REQ_RETRY_COUNT
;
1280 timeout
= UCAST_REQ_RETRY_TIMEOUT
;
1281 packet
.info
= NAME_QUERY_REQUEST
| NM_FLAGS_UNICAST
;
1283 packet
.qdcount
= 1; /* question entries */
1284 packet
.question
= question
;
1285 packet
.ancount
= 0; /* answer recs */
1286 packet
.answer
= NULL
;
1287 packet
.nscount
= 0; /* authority recs */
1288 packet
.authority
= NULL
;
1289 packet
.arcount
= 0; /* additional recs */
1290 packet
.additional
= NULL
;
1292 for (i
= 0; i
< addr_num
; i
++) {
1293 for (retry
= 0; retry
< retries
; retry
++) {
1294 if ((destination
[i
].flags
& ADDR_FLAG_VALID
) == 0)
1296 tid
= smb_netbios_name_trn_id();
1297 packet
.name_trn_id
= tid
;
1299 if (smb_send_name_service_packet(&destination
[i
],
1301 if ((rc
= smb_netbios_process_response(tid
,
1303 &packet
, timeout
)) != 0)
1307 st
.tv_nsec
= (timeout
* 1000000);
1308 (void) nanosleep(&st
, 0);
1316 * RFC 1002 4.2.13. POSITIVE NAME QUERY RESPONSE
1317 * RFC 1002 4.2.14. NEGATIVE NAME QUERY RESPONSE
1320 smb_send_name_query_response(addr_entry_t
*addr
,
1321 struct name_packet
*original_packet
, struct name_entry
*entry
,
1324 addr_entry_t
*raddr
;
1325 struct name_packet packet
;
1326 struct resource_record answer
;
1328 unsigned char data
[MAX_DATAGRAM_LENGTH
];
1329 unsigned char *scan
= data
;
1332 packet
.name_trn_id
= original_packet
->name_trn_id
;
1333 packet
.info
= NAME_QUERY_RESPONSE
| (rcode
& NAME_RCODE_MASK
);
1334 packet
.qdcount
= 0; /* question entries */
1335 packet
.question
= NULL
;
1336 packet
.ancount
= 1; /* answer recs */
1337 packet
.answer
= &answer
;
1338 packet
.nscount
= 0; /* authority recs */
1339 packet
.authority
= NULL
;
1340 packet
.arcount
= 0; /* additional recs */
1341 packet
.additional
= NULL
;
1343 answer
.name
= entry
;
1344 answer
.rr_class
= NAME_QUESTION_CLASS_IN
;
1345 answer
.ttl
= entry
->addr_list
.ttl
;
1346 answer
.rdata
= data
;
1348 answer
.rr_type
= NAME_RR_TYPE_NULL
;
1349 answer
.rdlength
= 0;
1352 answer
.rdlength
= 0;
1353 answer
.rr_type
= NAME_QUESTION_TYPE_NB
;
1354 raddr
= &entry
->addr_list
;
1357 attr
= entry
->attributes
& (NAME_ATTR_GROUP
|
1358 NAME_ATTR_OWNER_NODE_TYPE
);
1360 BE_OUT16(scan
, attr
); scan
+= 2;
1361 ret_addr
= LE_32(raddr
->sin
.sin_addr
.s_addr
);
1363 *scan
++ = ret_addr
>> 8;
1364 *scan
++ = ret_addr
>> 16;
1365 *scan
++ = ret_addr
>> 24;
1367 answer
.rdlength
+= 6;
1368 raddr
= raddr
->forw
;
1369 } while (raddr
!= &entry
->addr_list
);
1372 return (smb_send_name_service_packet(addr
, &packet
));
1376 * RFC 1002 4.2.18. NODE STATUS RESPONSE
1379 smb_send_node_status_response(addr_entry_t
*addr
,
1380 struct name_packet
*original_packet
)
1382 uint32_t net_ipaddr
;
1383 int64_t max_connections
;
1384 struct arpreq arpreq
;
1385 struct name_packet packet
;
1386 struct resource_record answer
;
1387 unsigned char *scan
;
1388 unsigned char *scan_end
;
1389 unsigned char data
[MAX_NETBIOS_REPLY_DATA_SIZE
];
1390 boolean_t scan_done
= B_FALSE
;
1391 smb_inaddr_t ipaddr
;
1393 bzero(&packet
, sizeof (struct name_packet
));
1394 bzero(&answer
, sizeof (struct resource_record
));
1396 packet
.name_trn_id
= original_packet
->name_trn_id
;
1397 packet
.info
= NODE_STATUS_RESPONSE
;
1398 packet
.qdcount
= 0; /* question entries */
1399 packet
.question
= NULL
;
1400 packet
.ancount
= 1; /* answer recs */
1401 packet
.answer
= &answer
;
1402 packet
.nscount
= 0; /* authority recs */
1403 packet
.authority
= NULL
;
1404 packet
.arcount
= 0; /* additional recs */
1405 packet
.additional
= NULL
;
1407 answer
.name
= original_packet
->question
->name
;
1408 answer
.rr_type
= NAME_RR_TYPE_NBSTAT
;
1409 answer
.rr_class
= NAME_QUESTION_CLASS_IN
;
1411 answer
.rdata
= data
;
1413 scan
= smb_netbios_cache_status(data
, MAX_NETBIOS_REPLY_DATA_SIZE
,
1414 original_packet
->question
->name
->scope
);
1416 scan_end
= data
+ MAX_NETBIOS_REPLY_DATA_SIZE
;
1418 ipaddr
.a_ipv4
= addr
->sin
.sin_addr
.s_addr
;
1419 ipaddr
.a_family
= AF_INET
;
1420 if (smb_nic_is_same_subnet(&ipaddr
))
1421 net_ipaddr
= addr
->sin
.sin_addr
.s_addr
;
1425 (void) smb_config_getnum(SMB_CI_MAX_CONNECTIONS
, &max_connections
);
1427 while (!scan_done
) {
1428 if ((scan
+ 6) >= scan_end
) {
1429 packet
.info
|= NAME_NM_FLAGS_TC
;
1433 if (net_ipaddr
!= 0) {
1434 struct sockaddr_in
*s_in
;
1437 s
= socket(AF_INET
, SOCK_DGRAM
, 0);
1438 /* LINTED - E_BAD_PTR_CAST_ALIGN */
1439 s_in
= (struct sockaddr_in
*)&arpreq
.arp_pa
;
1440 s_in
->sin_family
= AF_INET
;
1441 s_in
->sin_addr
.s_addr
= net_ipaddr
;
1442 if (ioctl(s
, SIOCGARP
, (caddr_t
)&arpreq
) < 0) {
1445 bcopy(&arpreq
.arp_ha
.sa_data
, scan
, 6);
1453 if ((scan
+ 26) >= scan_end
) {
1454 packet
.info
|= NAME_NM_FLAGS_TC
;
1460 if ((scan
+ 2) >= scan_end
) {
1461 packet
.info
|= NAME_NM_FLAGS_TC
;
1464 BE_OUT16(scan
, 0); scan
+= 2;
1466 if ((scan
+ 2) >= scan_end
) {
1467 packet
.info
|= NAME_NM_FLAGS_TC
;
1470 BE_OUT16(scan
, 0); scan
+= 2;
1472 if ((scan
+ 2) >= scan_end
) {
1473 packet
.info
|= NAME_NM_FLAGS_TC
;
1476 BE_OUT16(scan
, 0); scan
+= 2;
1478 if ((scan
+ 2) >= scan_end
) {
1479 packet
.info
|= NAME_NM_FLAGS_TC
;
1482 BE_OUT16(scan
, 0); scan
+= 2;
1484 if ((scan
+ 2) >= scan_end
) {
1485 packet
.info
|= NAME_NM_FLAGS_TC
;
1488 BE_OUT16(scan
, 0); scan
+= 2;
1490 if ((scan
+ 2) >= scan_end
) {
1491 packet
.info
|= NAME_NM_FLAGS_TC
;
1494 BE_OUT16(scan
, 0); scan
+= 2;
1496 if ((scan
+ 2) >= scan_end
) {
1497 packet
.info
|= NAME_NM_FLAGS_TC
;
1500 BE_OUT16(scan
, 0); scan
+= 2;
1502 if ((scan
+ 2) >= scan_end
) {
1503 packet
.info
|= NAME_NM_FLAGS_TC
;
1506 BE_OUT16(scan
, max_connections
); scan
+= 2;
1508 if ((scan
+ 2) >= scan_end
) {
1509 packet
.info
|= NAME_NM_FLAGS_TC
;
1513 BE_OUT16(scan
, 0); scan
+= 2;
1517 answer
.rdlength
= scan
- data
;
1518 return (smb_send_name_service_packet(addr
, &packet
));
1522 smb_name_Bnode_add_name(struct name_entry
*name
)
1524 struct name_question question
;
1525 struct resource_record additional
;
1526 unsigned char data
[8];
1531 addr
= &name
->addr_list
;
1534 /* build name service packet */
1535 question
.name
= name
;
1537 * question.name->attributes |= NAME_NB_FLAGS_ONT_B;
1538 * This is commented because NAME_NB_FLAGS_ONT_B is 0
1540 question
.question_type
= NAME_QUESTION_TYPE_NB
;
1541 question
.question_class
= NAME_QUESTION_CLASS_IN
;
1543 additional
.name
= name
;
1544 additional
.rr_class
= NAME_QUESTION_CLASS_IN
;
1546 additional
.rdata
= data
;
1547 additional
.rdlength
= 6;
1548 additional
.rr_type
= NAME_QUESTION_TYPE_NB
;
1549 attr
= name
->attributes
& (NAME_ATTR_GROUP
|
1550 NAME_ATTR_OWNER_NODE_TYPE
);
1552 BE_OUT16(&data
[0], attr
);
1553 (void) memcpy(&data
[2], &addr
->sin
.sin_addr
.s_addr
,
1556 rc
|= smb_send_name_registration_request(BROADCAST
, &question
,
1560 } while (addr
!= &name
->addr_list
);
1566 smb_name_Bnode_find_name(struct name_entry
*name
)
1568 struct name_question question
;
1570 question
.name
= name
;
1571 question
.question_type
= NAME_QUESTION_TYPE_NB
;
1572 question
.question_class
= NAME_QUESTION_CLASS_IN
;
1574 return (smb_send_name_query_request(BROADCAST
, &question
));
1578 smb_name_Bnode_delete_name(struct name_entry
*name
)
1580 struct name_question question
;
1581 struct resource_record additional
;
1582 addr_entry_t
*raddr
;
1583 unsigned char data
[MAX_DATAGRAM_LENGTH
];
1584 unsigned char *scan
= data
;
1589 question
.name
= name
;
1590 question
.question_type
= NAME_QUESTION_TYPE_NB
;
1591 question
.question_class
= NAME_QUESTION_CLASS_IN
;
1593 additional
.name
= name
;
1594 additional
.rr_class
= NAME_QUESTION_CLASS_IN
;
1596 additional
.rdata
= data
;
1597 additional
.rdlength
= 0;
1598 additional
.rr_type
= NAME_QUESTION_TYPE_NB
;
1599 raddr
= &name
->addr_list
;
1602 attr
= name
->attributes
& (NAME_ATTR_GROUP
|
1603 NAME_ATTR_OWNER_NODE_TYPE
);
1605 BE_OUT16(scan
, attr
); scan
+= 2;
1606 ret_addr
= LE_32(raddr
->sin
.sin_addr
.s_addr
);
1608 *scan
++ = ret_addr
>> 8;
1609 *scan
++ = ret_addr
>> 16;
1610 *scan
++ = ret_addr
>> 24;
1612 additional
.rdlength
+= 6;
1613 } while (raddr
!= &name
->addr_list
);
1615 return (smb_send_name_release_request_and_demand(BROADCAST
,
1616 &question
, &additional
));
1620 smb_name_Pnode_add_name(struct name_entry
*name
)
1622 struct name_question question
;
1623 struct resource_record additional
;
1624 unsigned char data
[8];
1630 addr
= &name
->addr_list
;
1632 question
.name
= name
;
1633 question
.question_type
= NAME_QUESTION_TYPE_NB
;
1634 question
.question_class
= NAME_QUESTION_CLASS_IN
;
1636 additional
.name
= name
;
1637 additional
.rr_class
= NAME_QUESTION_CLASS_IN
;
1639 additional
.rdata
= data
;
1640 additional
.rdlength
= 6;
1641 additional
.rr_type
= NAME_QUESTION_TYPE_NB
;
1642 attr
= name
->attributes
&
1643 (NAME_ATTR_GROUP
| NAME_ATTR_OWNER_NODE_TYPE
);
1645 BE_OUT16(&data
[0], attr
);
1646 (void) memcpy(&data
[2], &addr
->sin
.sin_addr
.s_addr
,
1649 rc
|= smb_send_name_registration_request(UNICAST
, &question
,
1654 } while (addr
!= &name
->addr_list
);
1660 smb_name_Pnode_refresh_name(struct name_entry
*name
)
1662 struct name_question question
;
1663 struct resource_record additional
;
1664 unsigned char data
[8];
1670 addr
= &name
->addr_list
;
1672 question
.name
= name
;
1673 question
.question_type
= NAME_QUESTION_TYPE_NB
;
1674 question
.question_class
= NAME_QUESTION_CLASS_IN
;
1676 additional
.name
= name
;
1677 additional
.rr_class
= NAME_QUESTION_CLASS_IN
;
1679 additional
.rdata
= data
;
1680 additional
.rdlength
= 6;
1681 additional
.rr_type
= NAME_QUESTION_TYPE_NB
;
1682 attr
= name
->attributes
&
1683 (NAME_ATTR_GROUP
| NAME_ATTR_OWNER_NODE_TYPE
);
1685 BE_OUT16(&data
[0], attr
);
1686 (void) memcpy(&data
[2], &addr
->sin
.sin_addr
.s_addr
,
1689 rc
|= smb_send_name_refresh_request(UNICAST
, &question
,
1693 } while (addr
!= &name
->addr_list
);
1699 smb_name_Pnode_find_name(struct name_entry
*name
)
1701 struct name_question question
;
1704 * Host initiated processing for a P node
1706 question
.name
= name
;
1707 question
.name
->attributes
|= NAME_NB_FLAGS_ONT_P
;
1708 question
.question_type
= NAME_QUESTION_TYPE_NB
;
1709 question
.question_class
= NAME_QUESTION_CLASS_IN
;
1711 return (smb_send_name_query_request(UNICAST
, &question
));
1715 smb_name_Pnode_delete_name(struct name_entry
*name
)
1717 struct name_question question
;
1718 struct resource_record additional
;
1719 addr_entry_t
*raddr
;
1720 unsigned char data
[MAX_DATAGRAM_LENGTH
];
1721 unsigned char *scan
= data
;
1726 question
.name
= name
;
1727 question
.name
->attributes
|= NAME_NB_FLAGS_ONT_P
;
1728 question
.question_type
= NAME_QUESTION_TYPE_NB
;
1729 question
.question_class
= NAME_QUESTION_CLASS_IN
;
1731 additional
.name
= name
;
1732 additional
.rr_class
= NAME_QUESTION_CLASS_IN
;
1734 additional
.rdata
= data
;
1735 additional
.rdlength
= 0;
1736 additional
.rr_type
= NAME_QUESTION_TYPE_NB
;
1737 raddr
= &name
->addr_list
;
1740 attr
= name
->attributes
& (NAME_ATTR_GROUP
|
1741 NAME_ATTR_OWNER_NODE_TYPE
);
1743 BE_OUT16(scan
, attr
); scan
+= 2;
1744 ret_addr
= LE_32(raddr
->sin
.sin_addr
.s_addr
);
1746 *scan
++ = ret_addr
>> 8;
1747 *scan
++ = ret_addr
>> 16;
1748 *scan
++ = ret_addr
>> 24;
1750 additional
.rdlength
= 6;
1751 raddr
= raddr
->forw
;
1752 (void) smb_send_name_release_request_and_demand(UNICAST
,
1753 &question
, &additional
);
1754 } while (raddr
!= &name
->addr_list
);
1760 smb_name_Mnode_add_name(struct name_entry
*name
)
1762 if (smb_name_Bnode_add_name(name
) > 0) {
1764 return (1); /* No name server configured */
1766 return (smb_name_Pnode_add_name(name
));
1772 smb_name_Hnode_add_name(struct name_entry
*name
)
1775 if (smb_name_Pnode_add_name(name
) == 1)
1779 return (smb_name_Bnode_add_name(name
));
1783 smb_name_Mnode_find_name(struct name_entry
*name
)
1785 if (smb_name_Bnode_find_name(name
) == 1)
1789 return (1); /* No name server configured */
1791 return (smb_name_Pnode_find_name(name
));
1795 smb_name_Hnode_find_name(struct name_entry
*name
)
1798 if (smb_name_Pnode_find_name(name
) == 1)
1801 return (smb_name_Bnode_find_name(name
));
1805 smb_name_Mnode_delete_name(struct name_entry
*name
)
1807 (void) smb_name_Bnode_delete_name(name
);
1810 return (-1); /* No name server configured */
1812 if (smb_name_Pnode_delete_name(name
) > 0)
1819 smb_name_Hnode_delete_name(struct name_entry
*name
)
1822 if (smb_name_Pnode_delete_name(name
) > 0)
1825 return (smb_name_Bnode_delete_name(name
));
1829 smb_name_process_Bnode_packet(struct name_packet
*packet
, addr_entry_t
*addr
)
1831 struct name_entry
*name
;
1832 struct name_entry
*entry
;
1833 struct name_question
*question
;
1834 struct resource_record
*additional
;
1836 question
= packet
->question
;
1837 additional
= packet
->additional
;
1839 switch (packet
->info
& NAME_OPCODE_OPCODE_MASK
) {
1840 case NAME_OPCODE_REFRESH
:
1841 /* Guard against malformed packets */
1842 if ((question
== 0) || (additional
== 0))
1844 if (additional
->name
->addr_list
.sin
.sin_addr
.s_addr
== 0)
1847 name
= question
->name
;
1848 name
->addr_list
.ttl
= additional
->ttl
;
1849 name
->attributes
= additional
->name
->attributes
;
1850 name
->addr_list
.sin
= additional
->name
->addr_list
.sin
;
1851 name
->addr_list
.forw
= name
->addr_list
.back
= &name
->addr_list
;
1853 if ((entry
= smb_netbios_cache_lookup_addr(name
)) != 0) {
1854 smb_netbios_cache_update_entry(entry
, question
->name
);
1855 smb_netbios_cache_unlock_entry(entry
);
1858 (void) smb_netbios_cache_insert(question
->name
);
1861 case NAME_OPCODE_QUERY
:
1863 * This opcode covers both NAME_QUERY_REQUEST and
1864 * NODE_STATUS_REQUEST. They can be distinguished
1865 * based on the type of question entry.
1868 /* All query requests have to have question entry */
1872 if (question
->question_type
== NAME_QUESTION_TYPE_NB
) {
1873 name
= question
->name
;
1874 if ((entry
= smb_netbios_cache_lookup(name
)) != 0) {
1875 (void) smb_send_name_query_response(addr
,
1877 smb_netbios_cache_unlock_entry(entry
);
1881 if (question
->question_type
== NAME_QUESTION_TYPE_NBSTAT
) {
1883 * Name of "*" may be used to force node to
1884 * divulge status for administrative purposes
1886 name
= question
->name
;
1888 if (NETBIOS_NAME_IS_STAR(name
->name
) ||
1889 ((entry
= smb_netbios_cache_lookup(name
)) != 0)) {
1891 smb_netbios_cache_unlock_entry(entry
);
1893 * send only those names that are
1894 * in the same scope as the scope
1895 * field in the request packet
1897 (void) smb_send_node_status_response(addr
,
1909 smb_name_process_Pnode_packet(struct name_packet
*packet
, addr_entry_t
*addr
)
1911 struct name_entry
*name
;
1912 struct name_entry
*entry
;
1913 struct name_question
*question
;
1914 struct resource_record
*additional
;
1916 question
= packet
->question
;
1917 additional
= packet
->additional
;
1919 if (packet
->info
& NAME_NM_FLAGS_B
) {
1921 * always ignore UDP broadcast packets
1926 switch (packet
->info
& NAME_OPCODE_OPCODE_MASK
) {
1927 case NAME_OPCODE_REFRESH
:
1928 /* Guard against malformed packets */
1929 if ((question
== 0) || (additional
== 0))
1931 if (additional
->name
->addr_list
.sin
.sin_addr
.s_addr
== 0)
1934 name
= question
->name
;
1935 name
->addr_list
.ttl
= additional
->ttl
;
1936 name
->attributes
= additional
->name
->attributes
;
1937 name
->addr_list
.sin
= additional
->name
->addr_list
.sin
;
1938 name
->addr_list
.forw
= name
->addr_list
.back
= &name
->addr_list
;
1940 if ((entry
= smb_netbios_cache_lookup(name
)) != 0) {
1941 smb_netbios_cache_update_entry(entry
, name
);
1942 smb_netbios_cache_unlock_entry(entry
);
1945 (void) smb_netbios_cache_insert(name
);
1947 (void) smb_send_name_registration_response(addr
, packet
, 0);
1950 case NAME_OPCODE_QUERY
:
1952 * This opcode covers both NAME_QUERY_REQUEST and
1953 * NODE_STATUS_REQUEST. They can be distinguished
1954 * based on the type of question entry.
1957 /* All query requests have to have question entry */
1961 if (question
->question_type
== NAME_QUESTION_TYPE_NB
) {
1962 name
= question
->name
;
1963 if ((entry
= smb_netbios_cache_lookup(name
)) != 0) {
1965 * send response to the IP address and port
1966 * number from which the request was received.
1968 (void) smb_send_name_query_response(addr
,
1970 smb_netbios_cache_unlock_entry(entry
);
1973 * send response to the requestor
1975 (void) smb_send_name_query_response(addr
,
1976 packet
, name
, RCODE_NAM_ERR
);
1980 if (question
->question_type
== NAME_QUESTION_TYPE_NBSTAT
) {
1982 * Name of "*" may be used to force node to
1983 * divulge status for administrative purposes
1985 name
= question
->name
;
1987 if (NETBIOS_NAME_IS_STAR(name
->name
) ||
1988 ((entry
= smb_netbios_cache_lookup(name
)) != 0)) {
1990 * send only those names that are
1991 * in the same scope as the scope
1992 * field in the request packet
1995 smb_netbios_cache_unlock_entry(entry
);
1996 (void) smb_send_node_status_response(addr
,
2008 smb_name_process_Mnode_packet(struct name_packet
*packet
, addr_entry_t
*addr
)
2010 if (packet
->info
& NAME_NM_FLAGS_B
)
2011 smb_name_process_Bnode_packet(packet
, addr
);
2013 smb_name_process_Pnode_packet(packet
, addr
);
2017 smb_name_process_Hnode_packet(struct name_packet
*packet
, addr_entry_t
*addr
)
2019 if (packet
->info
& NAME_NM_FLAGS_B
)
2020 smb_name_process_Bnode_packet(packet
, addr
);
2022 smb_name_process_Pnode_packet(packet
, addr
);
2027 * smb_netbios_name_tick
2029 * Called once a second to handle name server timeouts.
2032 smb_netbios_name_tick(void)
2034 struct name_entry
*name
;
2035 struct name_entry
*entry
;
2037 (void) mutex_lock(&refresh_queue
.mtx
);
2038 smb_netbios_cache_refresh(&refresh_queue
);
2040 while ((name
= refresh_queue
.head
.forw
) != &refresh_queue
.head
) {
2042 if (IS_LOCAL(name
->attributes
)) {
2043 if (IS_UNIQUE(name
->attributes
)) {
2044 (void) smb_name_Pnode_refresh_name(name
);
2047 entry
= smb_name_find_name(name
);
2048 smb_name_unlock_name(entry
);
2052 (void) mutex_unlock(&refresh_queue
.mtx
);
2054 smb_netbios_cache_reset_ttl();
2058 * smb_name_find_name
2060 * Lookup name cache for the given name.
2061 * If it's not in the cache it'll send a
2062 * name query request and then lookup the
2063 * cache again. Note that if a name is
2064 * returned it's locked and called MUST
2065 * unlock it by calling smb_name_unlock_name()
2068 smb_name_find_name(struct name_entry
*name
)
2070 struct name_entry
*result
;
2072 if ((result
= smb_netbios_cache_lookup(name
)) == 0) {
2073 switch (smb_node_type
) {
2075 (void) smb_name_Bnode_find_name(name
);
2078 (void) smb_name_Pnode_find_name(name
);
2081 (void) smb_name_Mnode_find_name(name
);
2085 (void) smb_name_Hnode_find_name(name
);
2088 return (smb_netbios_cache_lookup(name
));
2095 smb_name_unlock_name(struct name_entry
*name
)
2097 smb_netbios_cache_unlock_entry(name
);
2101 smb_name_add_name(struct name_entry
*name
)
2105 smb_netbios_name_logf(name
);
2107 switch (smb_node_type
) {
2109 rc
= smb_name_Bnode_add_name(name
);
2112 rc
= smb_name_Pnode_add_name(name
);
2115 rc
= smb_name_Mnode_add_name(name
);
2119 rc
= smb_name_Hnode_add_name(name
);
2124 (void) smb_netbios_cache_insert(name
);
2130 smb_name_delete_name(struct name_entry
*name
)
2135 type
= name
->name
[15];
2136 if ((type
!= NBT_WKSTA
) && (type
!= NBT_SERVER
)) {
2137 syslog(LOG_DEBUG
, "nbns: name delete bad type (0x%02x)", type
);
2138 smb_netbios_name_logf(name
);
2139 name
->attributes
&= ~NAME_ATTR_LOCAL
;
2143 smb_netbios_cache_delete(name
);
2145 switch (smb_node_type
) {
2147 rc
= smb_name_Bnode_delete_name(name
);
2150 rc
= smb_name_Pnode_delete_name(name
);
2153 rc
= smb_name_Mnode_delete_name(name
);
2157 rc
= smb_name_Hnode_delete_name(name
);
2174 * smb_netbios_worker
2176 * Process incoming request/response packets for Netbios
2177 * name service (on port 138).
2180 smb_netbios_worker(void *arg
)
2182 worker_param_t
*p
= (worker_param_t
*)arg
;
2183 addr_entry_t
*addr
= p
->addr
;
2184 struct name_packet
*packet
;
2186 if ((packet
= smb_name_buf_to_packet(p
->buf
, p
->length
)) != NULL
) {
2187 if (packet
->info
& NAME_OPCODE_R
) {
2189 smb_reply_ready(packet
, addr
);
2195 /* Request packet */
2196 switch (smb_node_type
) {
2198 smb_name_process_Bnode_packet(packet
, addr
);
2201 smb_name_process_Pnode_packet(packet
, addr
);
2204 smb_name_process_Mnode_packet(packet
, addr
);
2208 smb_name_process_Hnode_packet(packet
, addr
);
2213 smb_netbios_name_freeaddrs(packet
->answer
->name
);
2216 syslog(LOG_ERR
, "nbns: packet decode failed");
2226 * Configure the node type. If a WINS server has been specified,
2227 * act like an H-node. Otherwise, behave like a B-node.
2230 smb_netbios_node_config(void)
2232 static smb_cfg_id_t wins
[SMB_PI_MAX_WINS
] = {
2240 smb_node_type
= SMB_NODETYPE_B
;
2242 bzero(smb_nbns
, sizeof (addr_entry_t
) * SMB_PI_MAX_WINS
);
2244 for (i
= 0; i
< SMB_PI_MAX_WINS
; ++i
) {
2246 (void) smb_config_getstr(wins
[i
], ipstr
, sizeof (ipstr
));
2248 if ((ipaddr
= inet_addr(ipstr
)) == INADDR_NONE
)
2251 smb_node_type
= SMB_NODETYPE_H
;
2252 smb_nbns
[nbns_num
].flags
= ADDR_FLAG_VALID
;
2253 smb_nbns
[nbns_num
].sinlen
= sizeof (struct sockaddr_in
);
2254 smb_nbns
[nbns_num
].sin
.sin_family
= AF_INET
;
2255 smb_nbns
[nbns_num
].sin
.sin_addr
.s_addr
= ipaddr
;
2256 smb_nbns
[nbns_num
].sin
.sin_port
= htons(IPPORT_NETBIOS_NS
);
2262 smb_netbios_name_registration(void)
2264 nbcache_iter_t nbc_iter
;
2265 struct name_entry
*name
;
2268 rc
= smb_netbios_cache_getfirst(&nbc_iter
);
2270 name
= nbc_iter
.nbc_entry
;
2271 (void) smb_netbios_name_logf(name
);
2272 if (IS_UNIQUE(name
->attributes
) && IS_LOCAL(name
->attributes
)) {
2273 switch (smb_node_type
) {
2274 case SMB_NODETYPE_B
:
2275 (void) smb_name_Bnode_add_name(name
);
2277 case SMB_NODETYPE_P
:
2278 (void) smb_name_Pnode_add_name(name
);
2280 case SMB_NODETYPE_M
:
2281 (void) smb_name_Mnode_add_name(name
);
2283 case SMB_NODETYPE_H
:
2285 (void) smb_name_Hnode_add_name(name
);
2290 rc
= smb_netbios_cache_getnext(&nbc_iter
);
2295 * Note that the node configuration must be setup before calling
2296 * smb_init_name_struct().
2299 smb_netbios_name_config(void)
2301 addr_entry_t
*bcast_entry
;
2302 struct name_entry name
;
2306 (void) mutex_lock(&nbt_name_config_mtx
);
2307 smb_netbios_node_config();
2310 bzero(smb_bcast_list
, sizeof (addr_entry_t
) * SMB_PI_MAX_NETWORKS
);
2312 rc
= smb_nic_getfirst(&ni
);
2313 while (rc
== SMB_NIC_SUCCESS
) {
2314 if ((ni
.ni_nic
.nic_smbflags
& SMB_NICF_NBEXCL
) ||
2315 (ni
.ni_nic
.nic_smbflags
& SMB_NICF_ALIAS
)) {
2316 rc
= smb_nic_getnext(&ni
);
2320 bcast_entry
= &smb_bcast_list
[bcast_num
];
2321 bcast_entry
->flags
= ADDR_FLAG_VALID
;
2322 bcast_entry
->attributes
= NAME_ATTR_LOCAL
;
2323 bcast_entry
->sinlen
= sizeof (struct sockaddr_in
);
2324 bcast_entry
->sin
.sin_family
= AF_INET
;
2325 bcast_entry
->sin
.sin_port
= htons(IPPORT_NETBIOS_NS
);
2326 bcast_entry
->sin
.sin_addr
.s_addr
= ni
.ni_nic
.nic_bcast
;
2329 smb_init_name_struct((unsigned char *)ni
.ni_nic
.nic_host
,
2330 NBT_WKSTA
, 0, ni
.ni_nic
.nic_ip
.a_ipv4
,
2331 htons(IPPORT_NETBIOS_DGM
),
2332 NAME_ATTR_UNIQUE
, NAME_ATTR_LOCAL
, &name
);
2333 (void) smb_netbios_cache_insert(&name
);
2335 smb_init_name_struct((unsigned char *)ni
.ni_nic
.nic_host
,
2336 NBT_SERVER
, 0, ni
.ni_nic
.nic_ip
.a_ipv4
,
2337 htons(IPPORT_NETBIOS_DGM
),
2338 NAME_ATTR_UNIQUE
, NAME_ATTR_LOCAL
, &name
);
2339 (void) smb_netbios_cache_insert(&name
);
2341 rc
= smb_nic_getnext(&ni
);
2344 smb_netbios_name_registration();
2345 (void) mutex_unlock(&nbt_name_config_mtx
);
2349 smb_netbios_name_unconfig(void)
2351 struct name_entry
*name
;
2353 (void) mutex_lock(&nbt_name_config_mtx
);
2354 (void) mutex_lock(&delete_queue
.mtx
);
2355 smb_netbios_cache_delete_locals(&delete_queue
);
2357 while ((name
= delete_queue
.head
.forw
) != &delete_queue
.head
) {
2359 (void) smb_name_delete_name(name
);
2362 (void) mutex_unlock(&delete_queue
.mtx
);
2363 (void) mutex_unlock(&nbt_name_config_mtx
);
2367 smb_netbios_name_reconfig(void)
2369 smb_netbios_name_unconfig();
2370 smb_netbios_name_config();
2374 * NetBIOS Name Service (port 137)
2378 smb_netbios_name_service(void *arg
)
2380 struct sockaddr_in sin
;
2385 worker_param_t
*worker_param
;
2386 smb_inaddr_t ipaddr
;
2389 * Initialize reply_queue
2391 bzero(&reply_queue
, sizeof (reply_queue
));
2392 reply_queue
.forw
= reply_queue
.back
= &reply_queue
;
2394 if ((name_sock
= socket(AF_INET
, SOCK_DGRAM
, 0)) < 0) {
2395 syslog(LOG_ERR
, "nbns: socket failed: %m");
2396 smb_netbios_event(NETBIOS_EVENT_ERROR
);
2401 (void) setsockopt(name_sock
, SOL_SOCKET
, SO_REUSEADDR
, &flag
,
2404 (void) setsockopt(name_sock
, SOL_SOCKET
, SO_BROADCAST
, &flag
,
2407 bzero(&sin
, sizeof (struct sockaddr_in
));
2408 sin
.sin_family
= AF_INET
;
2409 sin
.sin_port
= htons(IPPORT_NETBIOS_NS
);
2410 if (bind(name_sock
, (struct sockaddr
*)&sin
, sizeof (sin
)) != 0) {
2411 syslog(LOG_ERR
, "nbns: bind(%d) failed: %m",
2413 (void) close(name_sock
);
2414 smb_netbios_event(NETBIOS_EVENT_ERROR
);
2418 smb_netbios_event(NETBIOS_EVENT_NS_START
);
2420 while (smb_netbios_running()) {
2421 buf
= malloc(MAX_DATAGRAM_LENGTH
);
2422 addr
= malloc(sizeof (addr_entry_t
));
2423 if ((buf
== NULL
) || (addr
== NULL
)) {
2424 /* Sleep for 10 seconds and try again */
2427 smb_netbios_sleep(10);
2430 ignore
: bzero(addr
, sizeof (addr_entry_t
));
2431 addr
->sinlen
= sizeof (addr
->sin
);
2432 addr
->forw
= addr
->back
= addr
;
2434 if ((len
= recvfrom(name_sock
, buf
, MAX_DATAGRAM_LENGTH
,
2435 0, (struct sockaddr
*)&addr
->sin
, &addr
->sinlen
)) < 0) {
2436 if (errno
== ENOMEM
|| errno
== ENFILE
||
2438 /* Sleep for 10 seconds and try again */
2441 smb_netbios_sleep(10);
2444 syslog(LOG_ERR
, "nbns: recvfrom failed: %m");
2447 smb_netbios_event(NETBIOS_EVENT_ERROR
);
2451 /* Ignore any incoming packets from myself... */
2453 ipaddr
.a_ipv4
= addr
->sin
.sin_addr
.s_addr
;
2454 ipaddr
.a_family
= AF_INET
;
2455 if (smb_nic_is_local(&ipaddr
))
2459 * Launch a netbios worker to process the received packet.
2461 worker_param
= malloc(sizeof (worker_param_t
));
2464 pthread_attr_t tattr
;
2466 worker_param
->addr
= addr
;
2467 worker_param
->buf
= buf
;
2468 worker_param
->length
= len
;
2470 (void) pthread_attr_init(&tattr
);
2471 (void) pthread_attr_setdetachstate(&tattr
,
2472 PTHREAD_CREATE_DETACHED
);
2473 (void) pthread_create(&worker
, &tattr
,
2474 smb_netbios_worker
, worker_param
);
2475 (void) pthread_attr_destroy(&tattr
);
2480 smb_netbios_event(NETBIOS_EVENT_NS_STOP
);
2481 smb_netbios_wait(NETBIOS_EVENT_BROWSER_STOP
);
2483 if (!smb_netbios_error())
2484 smb_netbios_name_unconfig();
2486 (void) close(name_sock
);