1 /* 2 * CDDL HEADER START 3 * 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. 7 * 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. 12 * 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] 18 * 19 * CDDL HEADER END 20 */ 21 /* 22 * Copyright 2010 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 */ 25 26 #include <sys/tzfile.h> 27 #include <errno.h> 28 #include <stdlib.h> 29 #include <stdio.h> 30 #include <unistd.h> 31 #include <syslog.h> 32 #include <string.h> 33 #include <strings.h> 34 #include <time.h> 35 #include <synch.h> 36 #include <netdb.h> 37 #include <sys/socket.h> 38 #include <arpa/inet.h> 39 40 #include <smbsrv/libsmb.h> 41 #include <smbsrv/libsmbns.h> 42 #include <smbsrv/smb.h> 43 #include <smbsrv/mailslot.h> 44 #include <smbns_browser.h> 45 #include <smbns_netbios.h> 46 47 /* 48 * ntdomain_info 49 * Temporary. It should be removed once NBTD is integrated. 50 */ 51 smb_ntdomain_t ntdomain_info; 52 mutex_t ntdomain_mtx; 53 cond_t ntdomain_cv; 54 55 #define SMB_SERVER_SIGNATURE 0xaa550415 56 57 typedef struct smb_hostinfo { 58 list_node_t hi_lnd; 59 smb_nic_t hi_nic; 60 char hi_nbname[NETBIOS_NAME_SZ]; 61 name_entry_t hi_netname; 62 uint32_t hi_nextannouce; 63 int hi_reps; 64 int hi_interval; 65 uint8_t hi_updatecnt; 66 uint32_t hi_type; 67 smb_version_t hi_version; 68 } smb_hostinfo_t; 69 70 typedef struct smb_browserinfo { 71 list_t bi_hlist; 72 int bi_hcnt; 73 rwlock_t bi_hlist_rwl; 74 boolean_t bi_changed; 75 mutex_t bi_mtx; 76 } smb_browserinfo_t; 77 78 static smb_browserinfo_t smb_binfo; 79 80 static int smb_browser_init(void); 81 static void smb_browser_infoinit(void); 82 static void smb_browser_infoterm(void); 83 static void smb_browser_infofree(void); 84 85 86 void 87 smb_browser_reconfig(void) 88 { 89 (void) mutex_lock(&smb_binfo.bi_mtx); 90 smb_binfo.bi_changed = B_TRUE; 91 (void) mutex_unlock(&smb_binfo.bi_mtx); 92 } 93 94 /* 95 * 3. Browser Overview 96 * 97 * Hosts involved in the browsing process can be separated into two 98 * distinct groups, browser clients and browser servers (often referred to 99 * simply as "browsers"). 100 * 101 * A browser is a server which maintains information about servers - 102 * primarily the domain they are in and the services that they are running 103 * -- and about domains. Browsers may assume several different roles in 104 * their lifetimes, and dynamically switch between them. 105 * 106 * Browser clients are of two types: workstations and (non-browser) 107 * servers. In the context of browsing, workstations query browsers for the 108 * information they contain; servers supply browsers the information by 109 * registering with them. Note that, at times, browsers may themselves 110 * behave as browser clients and query other browsers. 111 * 112 * For the purposes of this specification, a domain is simply a name with 113 * which to associate a group of resources such as computers, servers and 114 * users. Domains allow a convenient means for browser clients to restrict 115 * the scope of a search when they query browser servers. Every domain has 116 * a "master" server called the Primary Domain Controller (PDC) that 117 * manages various activities within the domain. 118 * 119 * One browser for each domain on a subnet is designated the Local Master 120 * Browser for that domain. Servers in its domain on the subnet register 121 * with it, as do the Local Master Browsers for other domains on the 122 * subnet. It uses these registrations to maintain authoritative 123 * information about its domain on its subnet. If there are other subnets 124 * in the network, it also knows the name of the server running the 125 * domain's Domain Master Browser; it registers with it, and uses it to 126 * obtain information about the rest of the network (see below). 127 * 128 * Clients on a subnet query browsers designated as the Backup Browsers for 129 * the subnet (not the Master Browser). Backup Browsers maintain a copy of 130 * the information on the Local Master Browser; they get it by periodically 131 * querying the Local Master Browser for all of its information. Clients 132 * find the Backup Browsers by asking the Local Master Browser. Clients are 133 * expected to spread their queries evenly across Backup Browsers to 134 * balance the load. 135 * 136 * The Local Master Browser is dynamically elected automatically. Multiple 137 * Backup Browser Servers may exist per subnet; they are selected from 138 * among the potential browser servers by the Local Master Browser, which 139 * is configured to select enough to handle the expected query load. 140 * 141 * When there are multiple subnets, a Domain Master Browser is assigned 142 * the task of keeping the multiple subnets in synchronization. The Primary 143 * Domain Controller (PDC) always acts as the Domain Master Browser. The 144 * Domain Master Browser periodically acts as a client and queries all the 145 * Local Master Browsers for its domain, asking them for a list containing 146 * all the domains and all the servers in their domain known within their 147 * subnets; it merges all the replies into a single master list. This 148 * allows a Domain Master Browser server to act as a collection point for 149 * inter-subnet browsing information. Local Master Browsers periodically 150 * query the Domain Master Browser to retrieve the network-wide information 151 * it maintains. 152 * 153 * When a domain spans only a single subnet, there will not be any distinct 154 * Local Master Browser; this role will be handled by the Domain Master 155 * Browser. Similarly, the Domain Master Browser is always the Local Master 156 * Browser for the subnet it is on. 157 * 158 * When a browser client suspects that the Local Master Browser has failed, 159 * the client will instigate an election in which the browser servers 160 * participate, and some browser servers may change roles. 161 * 162 * Some characteristics of a good browsing mechanism include: 163 * . minimal network traffic 164 * . minimum server discovery time 165 * . minimum change discovery latency 166 * . immunity to machine failures 167 * 168 * Historically, Browser implementations had been very closely tied to 169 * NETBIOS and datagrams. The early implementations caused a lot of 170 * broadcast traffic. See Appendix D for an overview that presents how the 171 * Browser specification evolved. 172 * 173 * 4. Browsing Protocol Architecture 174 * 175 * This section first describes the how the browsing protocol is layered, 176 * then describes the roles of clients, servers, and browsers in the 177 * browsing subsystem. 178 * 179 * 4.1 Layering of Browsing Protocol Requests 180 * 181 * Most of the browser functionality is implemented using mailslots. 182 * Mailslots provide a mechanism for fast, unreliable unidirectional data 183 * transfer; they are named via ASCII "mailslot (path) name". Mailslots are 184 * implemented using the CIFS Transact SMB which is encapsulated in a 185 * NETBIOS datagram. Browser protocol requests are sent to browser specific 186 * mailslots using some browser-specific NETBIOS names. These datagrams can 187 * either be unicast or broadcast, depending on whether the NETBIOS name is 188 * a "unique name" or a "group name". Various data structures, which are 189 * detailed subsequently within this document, flow as the data portion of 190 * the Transact SMB. 191 * 192 * Here is an example of a generic browser SMB, showing how a browser 193 * request is encapsulated in a TRANSACT SMB request. Note that the PID, 194 * TID, MID, UID, and Flags are all 0 in mailslot requests. 195 * 196 * SMB: C transact, File = \MAILSLOT\BROWSE 197 * SMB: SMB Status = Error Success 198 * SMB: Error class = No Error 199 * SMB: Error code = No Error 200 * SMB: Header: PID = 0x0000 TID = 0x0000 MID = 0x0000 UID = 0x0000 201 * SMB: Tree ID (TID) = 0 (0x0) 202 * SMB: Process ID (PID) = 0 (0x0) 203 * SMB: User ID (UID) = 0 (0x0) 204 * SMB: Multiplex ID (MID) = 0 (0x0) 205 * SMB: Flags Summary = 0 (0x0) 206 * SMB: Command = C transact 207 * SMB: Word count = 17 208 * SMB: Word parameters 209 * SMB: Total parm bytes = 0 210 * SMB: Total data bytes = 33 211 * SMB: Max parm bytes = 0 212 * SMB: Max data bytes = 0 213 * SMB: Max setup words = 0 214 * SMB: Transact Flags Summary = 0 (0x0) 215 * SMB: ...............0 = Leave session intact 216 * SMB: ..............0. = Response required 217 * SMB: Transact timeout = 0 (0x0) 218 * SMB: Parameter bytes = 0 (0x0) 219 * SMB: Parameter offset = 0 (0x0) 220 * SMB: Data bytes = 33 (0x21) 221 * SMB: Data offset = 86 (0x56) 222 * SMB: Setup word count = 3 223 * SMB: Setup words 224 * SMB: Mailslot opcode = Write mailslot 225 * SMB: Transaction priority = 1 226 * SMB: Mailslot class = Unreliable (broadcast) 227 * SMB: Byte count = 50 228 * SMB: Byte parameters 229 * SMB: Path name = \MAILSLOT\BROWSE 230 * SMB: Transaction data 231 * SMB: Data: Number of data bytes remaining = 33 (0x0021) 232 * 233 * Note the SMB command is Transact, the opcode within the Transact SMB is 234 * Mailslot Write, and the browser data structure is carried as the 235 * Transact data. 236 * The Transaction data begins with an opcode, that signifies the operation 237 * and determines the size and structure of data that follows. This opcode 238 * is named as per one of the below: 239 * 240 * HostAnnouncement 1 241 * AnnouncementRequest 2 242 * RequestElection 8 243 * GetBackupListReq 9 244 * GetBackupListResp 10 245 * BecomeBackup 11 246 * DomainAnnouncment 12 247 * MasterAnnouncement 13 248 * LocalMasterAnnouncement 15 249 * 250 * Browser datagrams are often referred to as simply browser frames. The 251 * frames are in particular, referred to by the name of the opcode within 252 * the Transaction data e.g. a GetBackupListReq browser frame, a 253 * RequestElection browser frame, etc. 254 * 255 * The structures that are sent as the data portion of the Transact SMB are 256 * described in section(s) 6.2 through 6.12 in this document. These 257 * structures are tightly packed, i.e. there are no intervening pad bytes 258 * in the structure, unless they are explicitly described as being there. 259 * All quantities are sent in native Intel format and multi-byte values are 260 * transmitted least significant byte first. 261 * 262 * Besides mailslots and Transaction SMBs, the other important piece of the 263 * browser architecture is the NetServerEnum2 request. This request that 264 * allows an application to interrogate a Browser Server and obtain a 265 * complete list of resources (servers, domains, etc) known to that Browser 266 * server. Details of the NetServerEnum2 request are presented in section 267 * 6.4. Some examples of the NetServerEnum2 request being used are when a 268 * Local Master Browser sends a NetServerEnum2 request to the Domain Master 269 * Browser and vice versa. Another example is when a browser client sends a 270 * NetServerEnum2 request to a Backup Browser server. 271 * 272 * 4.3 Non-Browser Server 273 * 274 * A non-browser server is a server that has some resource(s) or service(s) 275 * it wishes to advertise as being available using the browsing protocol. 276 * Examples of non-browser servers would be an SQL server, print server, 277 * etc. 278 * 279 * A non-browser server MUST periodically send a HostAnnouncement browser 280 * frame, specifying the type of resources or services it is advertising. 281 * Details are in section 6.5. 282 * 283 * A non-browser server SHOULD announce itself relatively frequently when 284 * it first starts up in order to make its presence quickly known to the 285 * browsers and thence to potential clients. The frequency of the 286 * announcements SHOULD then be gradually stretched, so as to minimize 287 * network traffic. Typically, non-browser servers announce themselves 288 * once every minute upon start up and then gradually adjust the frequency 289 * of the announcements to once every 12 minutes. 290 * 291 * A non-browser server SHOULD send a HostAnnouncement browser frame 292 * specifying a type of 0 just prior to shutting down, to allow it to 293 * quickly be removed from the list of available servers. 294 * 295 * A non-browser server MUST receive and process AnnouncementRequest frames 296 * from the Local Master Browser, and MUST respond with a HostAnnouncement 297 * frame, after a delay chosen randomly from the interval [0,30] seconds. 298 * AnnouncementRequests typically happen when a Local Master Browser starts 299 * up with an empty list of servers for the domain, and wants to fill it 300 * quickly. The 30 second range for responses prevents the Master Browser 301 * from becoming overloaded and losing replies, as well as preventing the 302 * network from being flooded with responses. 303 * 304 * 4.4 Browser Servers 305 * 306 * The following sections describe the roles of the various types of 307 * browser servers. 308 * 309 * 4.4.1 Potential Browser Server 310 * 311 * A Potential Browser server is a browser server that is capable of being 312 * a Backup Browser server or Master Browser server, but is not currently 313 * fulfilling either of those roles. 314 * 315 * A Potential Browser MUST set type SV_TYPE_POTENTIAL_BROWSER (see section 316 * 6.4.1) in its HostAnnouncement until it is ready to shut down. In its 317 * last HostAnnouncement frame before it shuts down, it SHOULD specify a 318 * type of 0. 319 * 320 * A Potential Browser server MUST receive and process BecomeBackup frames 321 * (see section 6.9) and become a backup browser upon their receipt. 322 * 323 * A Potential Browser MUST participate in browser elections (see section 324 * 6.8). 325 * 326 * 4.4.2 Backup Browser 327 * 328 * Backup Browser servers are a subset of the Potential Browsers that have 329 * been chosen by the Master Browser on their subnet to be the Backup 330 * Browsers for the subnet. 331 * 332 * A Backup Browser MUST set type SV_TYPE_BACKUP_BROWSER (see section 333 * 6.4.1) in its HostAnnouncement until it is ready to shut down. In its 334 * last HostAnnouncement frame before it shuts down, it SHOULD specify a 335 * type of 0. 336 * 337 * A Backup Browser MUST listen for a LocalMasterAnnouncement frame (see 338 * section 6.10) from the Local Master Browser, and use it to set the name 339 * of the Master Browser it queries for the server and domain lists. 340 * 341 * A Backup Browsers MUST periodically make a NetServerEnum2 request of 342 * the Master Browser on its subnet for its domain to get a list of servers 343 * in that domain, as well as a list of domains. The period is a 344 * configuration option balancing currency of the information with network 345 * traffic costs - a typical value is 15 minutes. 346 * 347 * A Backup Browser SHOULD force an election by sending a RequestElection 348 * frame (see section 6.7) if it does not get a response to its periodic 349 * NetServeEnum2 request to the Master Browser. 350 * 351 * A Backup Browser MUST receive and process NetServerEnum2 requests from 352 * browser clients, for its own domain and others. If the request is for a 353 * list of servers in its domain, or for a list of domains, it can answer 354 * from its internal lists. If the request is for a list of servers in a 355 * domain different than the one it serves, it sends a NetServerEnum2 356 * request to the Domain Master Browser for that domain (which it can in 357 * find in its list of domains and their Domain Master Browsers). 358 * 359 * A Backup Browser MUST participate in browser elections (see section 360 * 6.8). 361 * 362 * 4.4.3 Master Browser 363 * 364 * Master Browsers are responsible for: 365 * . indicating it is a Master Browser 366 * . receiving server announcements and building a list of such servers 367 * and keeping it reasonably up-to-date. 368 * . returning lists of Backup Browsers to browser clients. 369 * . ensuring an appropriate number of Backup Browsers are available. 370 * . announcing their existence to other Master Browsers on their subnet, 371 * to the Domain Master Browser for their domain, and to all browsers in 372 * their domain on their subnet 373 * . forwarding requests for lists of servers on other domains to the 374 * Master Browser for that domain 375 * . keeping a list of domains in its subnet 376 * . synchronizing with the Domain Master Browser (if any) for its domain 377 * . participating in browser elections 378 * . ensuring that there is only one Master Browser on its subnet 379 * 380 * A Master Browser MUST set type SV_TYPE_MASTER_BROWSER (see section 381 * 6.4.1) in its HostAnnouncement until it is ready to shut down. In its 382 * last HostAnnouncement frame before it shuts down, it SHOULD specify a 383 * type of 0. 384 * 385 * A Master Browser MUST receive and process HostAnnouncement frames from 386 * servers, adding the server name and other information to its servers 387 * list; it must mark them as "local" entries. Periodically, it MUST check 388 * all local server entries to see if a server's HostAnnouncement has timed 389 * out (no HostAnnouncement received for three times the periodicity the 390 * server gave in the last received HostAnnouncement) and remove timed-out 391 * servers from its list. 392 * 393 * A Master Browser MUST receive and process DomainAnnouncement frames (see 394 * section 6.12) and maintain the domain names and their associated (Local) 395 * Master Browsers in its internal domain list until they time out; it must 396 * mark these as "local" entries. Periodically, it MUST check all local 397 * domain entries to see if a server's DomainAnnouncement has timed out (no 398 * DomainAnnouncement received for three times the periodicity the server 399 * gave in the last received DomainAnnouncement) and remove timed-out 400 * servers from its list. 401 * 402 * A Master Browser MUST receive and process GetBackupListRequest frames 403 * from clients, returning GetBackupListResponse frames containing a list 404 * of the Backup Servers for its domain. 405 * 406 * A Master Browser MUST eventually send BecomeBackup frames (see section 407 * 6.9) to one or more Potential Browser servers to increase the number of 408 * Backup Browsers if there are not enough Backup Browsers to handle the 409 * anticipated query load. Note: possible good times for checking for 410 * sufficient backup browsers are after being elected, when timing out 411 * server HostAnnouncements, and when receiving a server's HostAnnouncement 412 * for the first time. 413 * 414 * A Master Browser MUST periodically announce itself and the domain it 415 * serves to other (Local) Master Browsers on its subnet, by sending a 416 * DomainAnnouncement frame (see section 6.12) to its subnet. 417 * 418 * A Master Browser MUST send a MasterAnnouncement frame (see section 6.11) 419 * to the Domain Master Browser after it is first elected, and periodically 420 * thereafter. This informs the Domain Master Browser of the presence of 421 * all the Master Browsers. 422 * 423 * A Master Browser MUST periodically announce itself to all browsers for 424 * its domain on its subnet by sending a LocalMasterAnnouncement frame (see 425 * section 6.10). 426 * 427 * A Master Browser MUST receive and process NetServerEnum2 requests from 428 * browser clients, for its own domain and others. If the request is for a 429 * list of servers in its domain, or for a list of domains, it can answer 430 * from its internal lists. Entries in its list marked "local" MUST have 431 * the SV_TYPE_LOCAL_LIST_ONLY bit set in the returned results; it must be 432 * clear for all other entries. If the request is for a list of servers in 433 * a domain different than the one it serves, it sends a NetServerEnum2 434 * request to the Domain Master Browser for that domain (which it can in 435 * find in its list of domains and their Domain Master Browsers). 436 * 437 * Note: The list of servers that the Master Browser maintains and 438 * returns to the Backup Browsers, is limited in size to 64K of 439 * data. This will limit the number of systems that can be in a 440 * browse list in a single workgroup or domain to approximately two 441 * thousand systems. 442 * 443 * A Master Browser SHOULD request all servers to register with it by 444 * sending an AnnouncementRequest frame, if, on becoming the Master Browser 445 * by winning an election, its server list is empty. Otherwise, clients 446 * might get an incomplete list of servers until the servers' periodic 447 * registrations fill the server list. 448 * 449 * If the Master Browser on a subnet is not the Primary Domain Controller 450 * (PDC), then it is a Local Master Browser. 451 * 452 * A Local Master Browser MUST periodically synchronize with the Domain 453 * Master Browser (which is the PDC). This synchronization is performed by 454 * making a NetServerEnum2 request to the Domain Master Browser and merging 455 * the results with its list of servers and domains. An entry from the 456 * Domain Master Browser should be marked "non-local", and must not 457 * overwrite an entry with the same name marked "local". The Domain Master 458 * Browser is located as specified in Appendix B. 459 * 460 * A Master Browser MUST participate in browser elections (see section 461 * 6.8). 462 * 463 * A Master Browser MUST, if it receives a HostAnnouncement, 464 * DomainAnnouncement, or LocalMasterAnnouncement frame another system that 465 * claims to be the Master Browser for its domain, demote itself from 466 * Master Browser and force an election. This ensures that there is only 467 * ever one Master Browser in each workgroup or domain. 468 * 469 * A Master Browser SHOULD, if it loses an election, become a Backup 470 * Browser (without being told to do so by the new Master Browser). Since 471 * it has more up-to-date information in its lists than a Potential 472 * Browser, it is more efficient to have it be a Backup Browser than to 473 * promote a Potential Browser. 474 * 475 * 4.4.3.1 Preferred Master Browser 476 * 477 * A Preferred Master Browser supports exactly the same protocol elements 478 * as a Potential Browser, except as follows. 479 * 480 * A Preferred Master Browser MUST always force an election when it starts 481 * up. 482 * 483 * A Preferred Master Browser MUST participate in browser elections (see 484 * section 6.8). 485 * 486 * A Preferred Master Browser MUST set the Preferred Master bit in the 487 * RequestElection frame (see section 6.7) to bias the election in its 488 * favor. 489 * 490 * A Preferred Master Browser SHOULD, if it loses an election, 491 * automatically become a Backup Browser, without being told to do so by 492 * the Master Browser. 493 * 494 * 4.4.4 Domain Master Browser 495 * 496 * Since the Domain Master Browser always runs on the PDC, it must 497 * implement all the protocols required of a PDC in addition to the 498 * browsing protocol, and that is way beyond the scope of this 499 * specification. 500 * 501 * 5. Mailslot Protocol Specification 502 * 503 * The only transaction allowed to a mailslot is a mailslot write. Mailslot 504 * writes requests are encapsulated in TRANSACT SMBs. The following table 505 * shows the interpretation of the TRANSACT SMB parameters for a mailslot 506 * transaction: 507 * 508 * Name Value Description 509 * Command SMB_COM_TRANSACTION 510 * Name <name> STRING name of mail slot to write; 511 * must start with "\\MAILSLOT\\" 512 * SetupCount 3 Always 3 for mailslot writes 513 * Setup[0] 1 Command code == write mailslot 514 * Setup[1] Ignored 515 * Setup[2] Ignored 516 * TotalDataCount n Size of data in bytes to write to 517 * the mailslot 518 * Data[ n ] The data to write to the mailslot 519 * 520 */ 521 522 /* 523 * SMB: C transact, File = \MAILSLOT\BROWSE 524 * SMB: SMB Status = Error Success 525 * SMB: Error class = No Error 526 * SMB: Error code = No Error 527 * SMB: Header: PID = 0x0000 TID = 0x0000 MID = 0x0000 UID = 0x0000 528 * SMB: Tree ID (TID) = 0 (0x0) 529 * SMB: Process ID (PID) = 0 (0x0) 530 * SMB: User ID (UID) = 0 (0x0) 531 * SMB: Multiplex ID (MID) = 0 (0x0) 532 * SMB: Flags Summary = 0 (0x0) 533 * SMB: Command = C transact 534 * SMB: Word count = 17 535 * SMB: Word parameters 536 * SMB: Total parm bytes = 0 537 * SMB: Total data bytes = 33 538 * SMB: Max parm bytes = 0 539 * SMB: Max data bytes = 0 540 * SMB: Max setup words = 0 541 * SMB: Transact Flags Summary = 0 (0x0) 542 * SMB: ...............0 = Leave session intact 543 * SMB: ..............0. = Response required 544 * SMB: Transact timeout = 0 (0x0) 545 * SMB: Parameter bytes = 0 (0x0) 546 * SMB: Parameter offset = 0 (0x0) 547 * SMB: Data bytes = 33 (0x21) 548 * SMB: Data offset = 86 (0x56) 549 * SMB: Setup word count = 3 550 * SMB: Setup words 551 * SMB: Mailslot opcode = Write mailslot 552 * SMB: Transaction priority = 1 553 * SMB: Mailslot class = Unreliable (broadcast) 554 * SMB: Byte count = 50 555 * SMB: Byte parameters 556 * SMB: Path name = \MAILSLOT\BROWSE 557 * SMB: Transaction data 558 * SMB: Data: Number of data bytes remaining = 33 (0x0021) 559 * 560 * 5. Mailslot Protocol Specification 561 * 562 * The only transaction allowed to a mailslot is a mailslot write. Mailslot 563 * writes requests are encapsulated in TRANSACT SMBs. The following table 564 * shows the interpretation of the TRANSACT SMB parameters for a mailslot 565 * transaction: 566 * 567 * Name Value Description 568 * Command SMB_COM_TRANSACTION 569 * Name <name> STRING name of mail slot to write; 570 * must start with "\MAILSLOT\" 571 * SetupCount 3 Always 3 for mailslot writes 572 * Setup[0] 1 Command code == write mailslot 573 * Setup[1] Ignored 574 * Setup[2] Ignored 575 * TotalDataCount n Size of data in bytes to write to 576 * the mailslot 577 * Data[ n ] The data to write to the mailslot 578 * 579 * Magic 0xFF 'S' 'M' 'B' 580 * smb_com a byte, the "first" command 581 * Error a 4-byte union, ignored in a request 582 * smb_flg a one byte set of eight flags 583 * smb_flg2 a two byte set of 16 flags 584 * . twelve reserved bytes, have a role 585 * in connectionless transports (IPX, UDP?) 586 * smb_tid a 16-bit tree ID, a mount point sorta, 587 * 0xFFFF is this command does not have 588 * or require a tree context 589 * smb_pid a 16-bit process ID 590 * smb_uid a 16-bit user ID, specific to this "session" 591 * and mapped to a system (bona-fide) UID 592 * smb_mid a 16-bit multiplex ID, used to differentiate 593 * multiple simultaneous requests from the same 594 * process (pid) (ref RPC "xid") 595 */ 596 597 int 598 smb_browser_load_transact_header(unsigned char *buffer, int maxcnt, 599 int data_count, int reply, char *mailbox) 600 { 601 smb_msgbuf_t mb; 602 int mailboxlen; 603 char *fmt; 604 int result; 605 short class = (reply == ONE_WAY_TRANSACTION) ? 2 : 0; 606 607 /* 608 * If the mailboxlen is an even number we need to pad the 609 * header so that the data starts on a word boundary. 610 */ 611 fmt = "Mb4.bw20.bwwwwb.wl2.wwwwb.wwwws"; 612 mailboxlen = strlen(mailbox) + 1; 613 614 if ((mailboxlen & 0x01) == 0) { 615 ++mailboxlen; 616 fmt = "Mb4.bw20.bwwwwb.wl2.wwwwb.wwwws."; 617 } 618 619 bzero(buffer, maxcnt); 620 smb_msgbuf_init(&mb, buffer, maxcnt, 0); 621 622 result = smb_msgbuf_encode(&mb, fmt, 623 SMB_COM_TRANSACTION, /* Command */ 624 0x18, 625 0x3, 626 17, /* Count of parameter words */ 627 0, /* Total Parameter words sent */ 628 data_count, /* Total Data bytes sent */ 629 2, /* Max Parameters to return */ 630 0, /* Max data bytes to return */ 631 0, /* Max setup bytes to return */ 632 reply, /* No reply */ 633 0xffffffff, /* Timeout */ 634 0, /* Parameter bytes sent */ 635 0, /* Parameter offset */ 636 data_count, /* Data bytes sent */ 637 69 + mailboxlen, /* Data offset */ 638 3, /* Setup word count */ 639 1, /* Setup word[0] */ 640 0, /* Setup word[1] */ 641 class, /* Setup word[2] */ 642 mailboxlen + data_count, /* Total request bytes */ 643 mailbox); /* Mailbox address */ 644 645 smb_msgbuf_term(&mb); 646 return (result); 647 } 648 649 static int 650 smb_browser_addr_of_subnet(struct name_entry *name, smb_hostinfo_t *hinfo, 651 struct name_entry *result) 652 { 653 uint32_t ipaddr, mask, saddr; 654 addr_entry_t *addr; 655 656 if (name == NULL) 657 return (-1); 658 659 if (hinfo->hi_nic.nic_smbflags & SMB_NICF_ALIAS) 660 return (-1); 661 662 ipaddr = hinfo->hi_nic.nic_ip.a_ipv4; 663 mask = hinfo->hi_nic.nic_mask; 664 665 *result = *name; 666 addr = &name->addr_list; 667 do { 668 saddr = addr->sin.sin_addr.s_addr; 669 if ((saddr & mask) == (ipaddr & mask)) { 670 *result = *name; 671 result->addr_list = *addr; 672 result->addr_list.forw = result->addr_list.back = 673 &result->addr_list; 674 return (0); 675 } 676 addr = addr->forw; 677 } while (addr != &name->addr_list); 678 679 return (-1); 680 } 681 682 683 static int 684 smb_browser_bcast_addr_of_subnet(struct name_entry *name, uint32_t bcast, 685 struct name_entry *result) 686 { 687 if (name != NULL && name != result) 688 *result = *name; 689 690 result->addr_list.sin.sin_family = AF_INET; 691 result->addr_list.sinlen = sizeof (result->addr_list.sin); 692 result->addr_list.sin.sin_addr.s_addr = bcast; 693 result->addr_list.sin.sin_port = htons(IPPORT_NETBIOS_DGM); 694 result->addr_list.forw = result->addr_list.back = &result->addr_list; 695 return (0); 696 } 697 698 /* 699 * 6.5 HostAnnouncement Browser Frame 700 * 701 * To advertise its presence, i.e. to publish itself as being available, a 702 * non-browser server sends a HostAnnouncement browser frame. If the server 703 * is a member of domain "D", this frame is sent to the NETBIOS unique name 704 * D(1d) and mailslot "\\MAILSLOT\\BROWSE". The definition of the 705 * HostAnnouncement frame is: 706 * 707 * struct { 708 * unsigned short Opcode; 709 * unsigned char UpdateCount; 710 * uint32_t Periodicity; 711 * unsigned char ServerName[]; 712 * unsigned char VersionMajor; 713 * unsigned char VersionMinor; 714 * uint32_t Type; 715 * uint32_t Signature; 716 * unsigned char Comment[]; 717 * } 718 * 719 * where: 720 * Opcode - Identifies this structure as a browser server 721 * announcement and is defined as HostAnnouncement with a 722 * value of decimal 1. 723 * 724 * UpdateCount - must be sent as zero and ignored on receipt. 725 * 726 * Periodicity - The announcement frequency of the server (in 727 * seconds). The server will be removed from the browse list 728 * if it has not been heard from in 3X its announcement 729 * frequency. In no case will the server be removed from the 730 * browse list before the period 3X has elapsed. Actual 731 * implementations may take more than 3X to actually remove 732 * the server from the browse list. 733 * 734 * ServerName - Null terminated ASCII server name (up to 16 bytes 735 * in length). 736 * 737 * VersionMajor - The major version number of the OS the server 738 * is running. it will be returned by NetServerEnum2. 739 * 740 * VersionMinor - The minor version number of the OS the server 741 * is running. This is entirely informational and does not 742 * have any significance for the browsing protocol. 743 * 744 * Type - Specifies the type of the server. The server type bits 745 * are specified in the NetServerEnum2 section. 746 * 747 * Signature - The browser protocol minor version number in the 748 * low 8 bits, the browser protocol major version number in 749 * the next higher 8 bits and the signature 0xaa55 in the 750 * high 16 bits of this field. Thus, for this version of the 751 * browser protocol (1.15) this field has the value 752 * 0xaa55010f. This may used to isolate browser servers that 753 * are running out of revision browser software; otherwise, 754 * it is ignored. 755 * 756 * Comment - Null terminated ASCII comment for the server. 757 * Limited to 43 bytes. 758 * 759 * When a non-browser server starts up, it announces itself in the manner 760 * described once every minute. The frequency of these statements is 761 * gradually stretched to once every 12 minutes. 762 * 763 * Note: older non-browser servers in a domain "D" sent HostAnnouncement 764 * frames to the NETBIOS group name D(00). Non-Browser servers supporting 765 * version 1.15 of the browsing protocol SHOULD NOT use this NETBIOS name, 766 * but for backwards compatibility Master Browsers MAY receive and process 767 * HostAnnouncement frames on this name as described above for D(1d). 768 */ 769 770 static void 771 smb_browser_send_HostAnnouncement(smb_hostinfo_t *hinfo, 772 uint32_t next_announcement, boolean_t remove, 773 addr_entry_t *addr, char suffix) 774 { 775 smb_msgbuf_t mb; 776 int offset, announce_len, data_length; 777 struct name_entry dest_name; 778 unsigned char *buffer; 779 uint32_t type; 780 char resource_domain[SMB_PI_MAX_DOMAIN]; 781 782 if (smb_getdomainname(resource_domain, SMB_PI_MAX_DOMAIN) != 0) 783 return; 784 (void) smb_strupr(resource_domain); 785 786 if (addr == NULL) { 787 /* Local master Browser */ 788 smb_init_name_struct((unsigned char *)resource_domain, suffix, 789 0, 0, 0, 0, 0, &dest_name); 790 if (smb_browser_bcast_addr_of_subnet(0, hinfo->hi_nic.nic_bcast, 791 &dest_name) < 0) 792 return; 793 } else { 794 smb_init_name_struct((unsigned char *)resource_domain, suffix, 795 0, 0, 0, 0, 0, &dest_name); 796 dest_name.addr_list = *addr; 797 dest_name.addr_list.forw = dest_name.addr_list.back = 798 &dest_name.addr_list; 799 } 800 801 /* give some extra room */ 802 buffer = malloc(MAX_DATAGRAM_LENGTH * 2); 803 if (buffer == NULL) { 804 syslog(LOG_DEBUG, "smb browser: HostAnnouncement: %m"); 805 return; 806 } 807 808 data_length = 1 + 1 + 4 + 16 + 1 + 1 + 4 + 4 + 809 strlen(hinfo->hi_nic.nic_cmnt) + 1; 810 811 offset = smb_browser_load_transact_header(buffer, 812 MAX_DATAGRAM_LENGTH, data_length, ONE_WAY_TRANSACTION, 813 MAILSLOT_BROWSE); 814 815 if (offset < 0) { 816 free(buffer); 817 return; 818 } 819 820 /* 821 * A non-browser server SHOULD send a HostAnnouncement browser frame 822 * specifying a type of 0 just prior to shutting down, to allow it to 823 * quickly be removed from the list of available servers. 824 */ 825 if (remove || (!smb_netbios_running())) 826 type = 0; 827 else 828 type = hinfo->hi_type; 829 830 smb_msgbuf_init(&mb, buffer + offset, MAX_DATAGRAM_LENGTH - offset, 0); 831 832 announce_len = smb_msgbuf_encode(&mb, "bbl16cbblls", 833 HOST_ANNOUNCEMENT, 834 ++hinfo->hi_updatecnt, 835 next_announcement * 60000, /* Periodicity in MilliSeconds */ 836 hinfo->hi_nbname, 837 hinfo->hi_version.sv_major, 838 hinfo->hi_version.sv_minor, 839 type, 840 SMB_SERVER_SIGNATURE, 841 hinfo->hi_nic.nic_cmnt); 842 843 if (announce_len > 0) 844 (void) smb_netbios_datagram_send(&hinfo->hi_netname, &dest_name, 845 buffer, offset + announce_len); 846 847 free(buffer); 848 smb_msgbuf_term(&mb); 849 } 850 851 static void 852 smb_browser_process_AnnouncementRequest(struct datagram *datagram, 853 char *mailbox) 854 { 855 smb_hostinfo_t *hinfo; 856 uint32_t next_announcement; 857 uint32_t delay = random() % 29; /* in seconds */ 858 boolean_t h_found = B_FALSE; 859 860 if (strcmp(mailbox, MAILSLOT_LANMAN) != 0) { 861 syslog(LOG_DEBUG, "smb browser: wrong mailbox (%s)", mailbox); 862 return; 863 } 864 865 smb_netbios_sleep(delay); 866 867 (void) rw_rdlock(&smb_binfo.bi_hlist_rwl); 868 hinfo = list_head(&smb_binfo.bi_hlist); 869 while (hinfo) { 870 if ((hinfo->hi_nic.nic_ip.a_ipv4 & 871 hinfo->hi_nic.nic_mask) == 872 (datagram->src.addr_list.sin.sin_addr.s_addr & 873 hinfo->hi_nic.nic_mask)) { 874 h_found = B_TRUE; 875 break; 876 } 877 hinfo = list_next(&smb_binfo.bi_hlist, hinfo); 878 } 879 880 if (h_found) { 881 next_announcement = hinfo->hi_nextannouce * 60 * 1000; 882 smb_browser_send_HostAnnouncement(hinfo, next_announcement, 883 B_FALSE, &datagram->src.addr_list, NBT_MB); 884 } 885 (void) rw_unlock(&smb_binfo.bi_hlist_rwl); 886 } 887 888 void * 889 smb_browser_dispatch(void *arg) 890 { 891 struct datagram *datagram = (struct datagram *)arg; 892 smb_msgbuf_t mb; 893 int rc; 894 unsigned char command; 895 unsigned char parameter_words; 896 unsigned short total_parameter_words; 897 unsigned short total_data_count; 898 unsigned short max_parameters_to_return; 899 unsigned short max_data_to_return; 900 unsigned char max_setup_bytes_to_return; 901 unsigned short reply; 902 unsigned short parameter_bytes_sent; 903 unsigned short parameter_offset; 904 unsigned short data_bytes_sent; 905 unsigned short data_offset; 906 unsigned char setup_word_count; 907 unsigned short setup_word_0; 908 unsigned short setup_word_1; 909 unsigned short setup_word_2; 910 unsigned short total_request_bytes; 911 char *mailbox; 912 unsigned char message_type; 913 unsigned char *data; 914 int datalen; 915 916 syslog(LOG_DEBUG, "smb browser: packet received"); 917 918 smb_msgbuf_init(&mb, datagram->data, datagram->data_length, 0); 919 rc = smb_msgbuf_decode(&mb, "Mb27.bwwwwb.w6.wwwwb.wwwws", 920 &command, /* Command */ 921 ¶meter_words, /* Count of parameter words */ 922 &total_parameter_words, /* Total Parameter words sent */ 923 &total_data_count, /* Total Data bytes sent */ 924 &max_parameters_to_return, /* Max Parameters to return */ 925 &max_data_to_return, /* Max data bytes to return */ 926 &max_setup_bytes_to_return, /* Max setup bytes to return */ 927 &reply, /* No reply */ 928 ¶meter_bytes_sent, /* Parameter bytes sent */ 929 ¶meter_offset, /* Parameter offset */ 930 &data_bytes_sent, /* Data bytes sent */ 931 &data_offset, /* Data offset */ 932 &setup_word_count, /* Setup word count */ 933 &setup_word_0, /* Setup word[0] */ 934 &setup_word_1, /* Setup word[1] */ 935 &setup_word_2, /* Setup word[2] */ 936 &total_request_bytes, /* Total request bytes */ 937 &mailbox); /* Mailbox address */ 938 939 if (rc < 0) { 940 syslog(LOG_ERR, "smb browser: decode error"); 941 smb_msgbuf_term(&mb); 942 free(datagram); 943 return (0); 944 } 945 946 data = &datagram->data[data_offset]; 947 datalen = datagram->data_length - data_offset; 948 949 /* 950 * The PDC location protocol, i.e. anything on the \\NET 951 * mailslot, is handled by the smb_netlogon module. 952 */ 953 if (strncasecmp("\\MAILSLOT\\NET\\", mailbox, 14) == 0) { 954 smb_netlogon_receive(datagram, mailbox, data, datalen); 955 smb_msgbuf_term(&mb); 956 free(datagram); 957 return (0); 958 } 959 960 /* 961 * If it's not a netlogon message, assume it's a browser request. 962 * This is not the most elegant way to extract the command byte 963 * but at least we no longer use it to get the netlogon opcode. 964 */ 965 message_type = datagram->data[data_offset]; 966 967 switch (message_type) { 968 case ANNOUNCEMENT_REQUEST : 969 smb_browser_process_AnnouncementRequest(datagram, mailbox); 970 break; 971 972 default: 973 syslog(LOG_DEBUG, "smb browser: invalid message type(%d, %x)", 974 message_type, message_type); 975 break; 976 } 977 978 smb_msgbuf_term(&mb); 979 free(datagram); 980 return (0); 981 } 982 983 984 /* 985 * 11.1 Registered unique names 986 * 987 * <COMPUTER>(00) 988 * This name is used by all servers and clients to receive second 989 * class mailslot messages. A system must add this name in order to 990 * receive mailslot messages. The only browser requests that should 991 * appear on this name are BecomeBackup, GetBackupListResp, 992 * MasterAnnouncement, and LocalMasterAnnouncement frames. All other 993 * datagrams (other than the expected non-browser datagrams) may be 994 * ignored and an error logged. 995 * 996 * <DOMAIN>(1d) 997 * This name is used to identify a master browser server for domain 998 * "DOMAIN" on a subnet. A master browser server adds this name as a 999 * unique NETBIOS name when it becomes master browser. If the attempt 1000 * to add the name fails, the master browser server assumes that there 1001 * is another master in the domain and will fail to come up. It may 1002 * log an error if the failure occurs more than 3 times in a row (this 1003 * either indicates some form of network misconfiguration or a 1004 * software error). The only requests that should appear on this name 1005 * are GetBackupListRequest and HostAnnouncement requests. All other 1006 * datagrams on this name may be ignored (and an error logged). If 1007 * running a NETBIOS name service (NBNS, such as WINS), this name 1008 * should not be registered with the NBNS. 1009 * 1010 * <DOMAIN>(1b) 1011 * This name is used to identify the Domain Master Browser for domain 1012 * "DOMAIN" (which is also the primary domain controller). It is a 1013 * unique name added only by the primary domain controller. The 1014 * primary domain controller will respond to GetBackupListRequest on 1015 * this name just as it responds to these requests on the <DOMAIN>(1d) 1016 * name. 1017 * 1018 * 11.2 Registered group names 1019 * 1020 * (01)(02)__MSBROWSE__(02)(01) 1021 * This name is used by Master Browsers to announce themselves to the 1022 * other Master Browsers on a subnet. It is added as a group name by 1023 * all Master Browser servers. The only broadcasts that should appear 1024 * on this name is DomainAnnouncement requests. All other datagrams 1025 * can be ignored. 1026 * 1027 * <DOMAIN>(00) 1028 * This name is used by clients and servers in domain "DOMAIN" to 1029 * process server announcements. The only requests that should appear 1030 * on this name that the browser is interested in are 1031 * AnnouncementRequest and NETLOGON_QUERY (to locate the PDC) packets. 1032 * All other unidentifiable requests may be ignored (and an error 1033 * logged). 1034 * 1035 * <DOMAIN>(1E) 1036 * This name is used for announcements to browsers for domain "DOMAIN" 1037 * on a subnet. This name is registered by all the browser servers in 1038 * the domain. The only requests that should appear on this name are 1039 * RequestElection and AnnouncementRequest packets. All other 1040 * datagrams may be ignored (and an error logged). 1041 * 1042 * <DOMAIN>(1C) 1043 * This name is registered by Primary Domain Controllers. 1044 */ 1045 1046 static void 1047 smb_browser_config(void) 1048 { 1049 smb_hostinfo_t *hinfo; 1050 struct name_entry name; 1051 struct name_entry master; 1052 struct name_entry dest; 1053 struct name_entry *entry; 1054 char resource_domain[SMB_PI_MAX_DOMAIN]; 1055 int rc; 1056 1057 if (smb_browser_init() != 0) 1058 return; 1059 1060 if (smb_getdomainname(resource_domain, SMB_PI_MAX_DOMAIN) != 0) 1061 return; 1062 (void) smb_strupr(resource_domain); 1063 1064 /* domain<00> */ 1065 smb_init_name_struct((unsigned char *)resource_domain, NBT_WKSTA, 1066 0, 0, 0, 0, 0, &name); 1067 entry = smb_name_find_name(&name); 1068 smb_name_unlock_name(entry); 1069 1070 (void) rw_rdlock(&smb_binfo.bi_hlist_rwl); 1071 hinfo = list_head(&smb_binfo.bi_hlist); 1072 while (hinfo) { 1073 smb_init_name_struct((unsigned char *)resource_domain, 1074 NBT_WKSTA, 0, hinfo->hi_nic.nic_ip.a_ipv4, 1075 htons(IPPORT_NETBIOS_DGM), NAME_ATTR_GROUP, 1076 NAME_ATTR_LOCAL, &name); 1077 (void) smb_name_add_name(&name); 1078 1079 hinfo = list_next(&smb_binfo.bi_hlist, hinfo); 1080 } 1081 (void) rw_unlock(&smb_binfo.bi_hlist_rwl); 1082 1083 /* All our local master browsers */ 1084 smb_init_name_struct((unsigned char *)resource_domain, NBT_MB, 1085 0, 0, 0, 0, 0, &dest); 1086 entry = smb_name_find_name(&dest); 1087 1088 if (entry) { 1089 (void) rw_rdlock(&smb_binfo.bi_hlist_rwl); 1090 hinfo = list_head(&smb_binfo.bi_hlist); 1091 while (hinfo) { 1092 rc = smb_browser_addr_of_subnet(entry, hinfo, &master); 1093 if (rc == 0) { 1094 syslog(LOG_DEBUG, 1095 "smb browser: master browser found at %s", 1096 inet_ntoa(master.addr_list.sin.sin_addr)); 1097 } 1098 hinfo = list_next(&smb_binfo.bi_hlist, hinfo); 1099 } 1100 (void) rw_unlock(&smb_binfo.bi_hlist_rwl); 1101 1102 smb_name_unlock_name(entry); 1103 } 1104 1105 /* Domain master browser */ 1106 smb_init_name_struct((unsigned char *)resource_domain, 1107 NBT_DMB, 0, 0, 0, 0, 0, &dest); 1108 1109 if ((entry = smb_name_find_name(&dest)) != 0) { 1110 syslog(LOG_DEBUG, 1111 "smb browser: domain master browser for %s is %s", 1112 resource_domain, 1113 inet_ntoa(entry->addr_list.sin.sin_addr)); 1114 smb_name_unlock_name(entry); 1115 } 1116 } 1117 1118 static int 1119 smb_browser_init(void) 1120 { 1121 smb_hostinfo_t *hinfo; 1122 smb_niciter_t ni; 1123 uint32_t type; 1124 smb_version_t version; 1125 1126 smb_config_get_version(&version); 1127 1128 (void) rw_wrlock(&smb_binfo.bi_hlist_rwl); 1129 smb_browser_infofree(); 1130 1131 if (smb_nic_getfirst(&ni) != SMB_NIC_SUCCESS) { 1132 (void) rw_unlock(&smb_binfo.bi_hlist_rwl); 1133 return (-1); 1134 } 1135 1136 type = MY_SERVER_TYPE; 1137 if (smb_config_get_secmode() == SMB_SECMODE_DOMAIN) 1138 type |= SV_DOMAIN_MEMBER; 1139 1140 do { 1141 if ((ni.ni_nic.nic_smbflags & SMB_NICF_NBEXCL) || 1142 (ni.ni_nic.nic_smbflags & SMB_NICF_ALIAS)) 1143 continue; 1144 1145 hinfo = malloc(sizeof (smb_hostinfo_t)); 1146 if (hinfo == NULL) { 1147 smb_browser_infofree(); 1148 (void) rw_unlock(&smb_binfo.bi_hlist_rwl); 1149 return (-1); 1150 } 1151 1152 hinfo->hi_nic = ni.ni_nic; 1153 /* One Minute announcements for first five */ 1154 hinfo->hi_nextannouce = 1; 1155 hinfo->hi_interval = 1; 1156 hinfo->hi_reps = 5; 1157 hinfo->hi_updatecnt = 0; 1158 hinfo->hi_type = type; 1159 hinfo->hi_version = version; 1160 1161 /* This is the name used for HostAnnouncement */ 1162 (void) strlcpy(hinfo->hi_nbname, hinfo->hi_nic.nic_host, 1163 NETBIOS_NAME_SZ); 1164 (void) smb_strupr(hinfo->hi_nbname); 1165 /* 0x20: file server service */ 1166 smb_init_name_struct((unsigned char *)hinfo->hi_nbname, 1167 NBT_SERVER, 0, hinfo->hi_nic.nic_ip.a_ipv4, 1168 htons(IPPORT_NETBIOS_DGM), 1169 NAME_ATTR_UNIQUE, NAME_ATTR_LOCAL, 1170 &hinfo->hi_netname); 1171 1172 list_insert_tail(&smb_binfo.bi_hlist, hinfo); 1173 smb_binfo.bi_hcnt++; 1174 } while (smb_nic_getnext(&ni) == SMB_NIC_SUCCESS); 1175 1176 (void) rw_unlock(&smb_binfo.bi_hlist_rwl); 1177 return (0); 1178 } 1179 1180 /* 1181 * smb_browser_non_master_duties 1182 * 1183 * To advertise its presence, i.e. to publish itself as being available, a 1184 * non-browser server sends a HostAnnouncement browser frame. If the server 1185 * is a member of domain "D", this frame is sent to the NETBIOS unique name 1186 * D(1d) and mailslot "\\MAILSLOT\\BROWSE". 1187 */ 1188 static void 1189 smb_browser_non_master_duties(smb_hostinfo_t *hinfo, boolean_t remove) 1190 { 1191 struct name_entry name; 1192 struct name_entry *dest; 1193 addr_entry_t addr; 1194 char resource_domain[SMB_PI_MAX_DOMAIN]; 1195 1196 smb_browser_send_HostAnnouncement(hinfo, hinfo->hi_interval, 1197 remove, 0, NBT_MB); 1198 if (smb_getdomainname(resource_domain, SMB_PI_MAX_DOMAIN) != 0) 1199 return; 1200 1201 (void) smb_strupr(resource_domain); 1202 1203 smb_init_name_struct((unsigned char *)resource_domain, NBT_MB, 1204 0, 0, 0, 0, 0, &name); 1205 1206 if ((dest = smb_name_find_name(&name))) { 1207 addr = dest->addr_list; 1208 addr.forw = addr.back = &addr; 1209 smb_name_unlock_name(dest); 1210 smb_browser_send_HostAnnouncement(hinfo, hinfo->hi_interval, 1211 remove, &addr, NBT_MB); 1212 } else { 1213 smb_init_name_struct((unsigned char *)resource_domain, 1214 NBT_DMB, 0, 0, 0, 0, 0, &name); 1215 if ((dest = smb_name_find_name(&name))) { 1216 addr = dest->addr_list; 1217 addr.forw = addr.back = &addr; 1218 smb_name_unlock_name(dest); 1219 smb_browser_send_HostAnnouncement(hinfo, 1220 remove, hinfo->hi_interval, &addr, NBT_DMB); 1221 } 1222 } 1223 1224 /* 1225 * One Minute announcements for first five 1226 * minutes, one minute longer each round 1227 * until 12 minutes and every 12 minutes 1228 * thereafter. 1229 */ 1230 if (--hinfo->hi_reps == 0) { 1231 if (hinfo->hi_interval < 12) 1232 hinfo->hi_interval++; 1233 1234 hinfo->hi_reps = 1; 1235 } 1236 1237 hinfo->hi_nextannouce = hinfo->hi_interval; 1238 } 1239 1240 1241 /* 1242 * SMB NetBIOS Browser Service 1243 */ 1244 /*ARGSUSED*/ 1245 void * 1246 smb_browser_service(void *arg) 1247 { 1248 smb_hostinfo_t *hinfo; 1249 1250 smb_browser_infoinit(); 1251 smb_browser_config(); 1252 1253 smb_netbios_event(NETBIOS_EVENT_BROWSER_START); 1254 1255 restart: 1256 do { 1257 (void) rw_rdlock(&smb_binfo.bi_hlist_rwl); 1258 hinfo = list_head(&smb_binfo.bi_hlist); 1259 1260 while (hinfo) { 1261 if (--hinfo->hi_nextannouce > 0 || 1262 hinfo->hi_nic.nic_bcast == 0) { 1263 hinfo = list_next(&smb_binfo.bi_hlist, hinfo); 1264 continue; 1265 } 1266 1267 smb_browser_non_master_duties(hinfo, B_FALSE); 1268 1269 /* Check to see whether reconfig is needed */ 1270 (void) mutex_lock(&smb_binfo.bi_mtx); 1271 if (smb_binfo.bi_changed) { 1272 smb_binfo.bi_changed = B_FALSE; 1273 (void) mutex_unlock(&smb_binfo.bi_mtx); 1274 (void) rw_unlock(&smb_binfo.bi_hlist_rwl); 1275 smb_browser_config(); 1276 goto restart; 1277 } 1278 (void) mutex_unlock(&smb_binfo.bi_mtx); 1279 1280 hinfo = list_next(&smb_binfo.bi_hlist, hinfo); 1281 } 1282 1283 (void) rw_unlock(&smb_binfo.bi_hlist_rwl); 1284 smb_netbios_sleep(SECSPERMIN); /* 1 minute */ 1285 } while (smb_netbios_running()); 1286 1287 smb_browser_infoterm(); 1288 smb_netbios_event(NETBIOS_EVENT_BROWSER_STOP); 1289 return (0); 1290 } 1291 1292 /* 1293 * smb_browser_netlogon 1294 * 1295 * Sends SAMLOGON/NETLOGON request for all host/ips, except 1296 * aliases, to find a domain controller. 1297 * 1298 * The dc argument will be set if a DC is found. 1299 */ 1300 boolean_t 1301 smb_browser_netlogon(char *domain, char *dc, uint32_t dc_len) 1302 { 1303 smb_hostinfo_t *hinfo; 1304 boolean_t found = B_FALSE; 1305 timestruc_t to; 1306 int err; 1307 1308 (void) rw_rdlock(&smb_binfo.bi_hlist_rwl); 1309 hinfo = list_head(&smb_binfo.bi_hlist); 1310 while (hinfo) { 1311 if ((hinfo->hi_nic.nic_smbflags & SMB_NICF_ALIAS) == 0) 1312 smb_netlogon_request(&hinfo->hi_netname, domain); 1313 hinfo = list_next(&smb_binfo.bi_hlist, hinfo); 1314 } 1315 (void) rw_unlock(&smb_binfo.bi_hlist_rwl); 1316 1317 bzero(dc, dc_len); 1318 to.tv_sec = 30; 1319 to.tv_nsec = 0; 1320 (void) mutex_lock(&ntdomain_mtx); 1321 while (ntdomain_info.n_ipaddr == 0) { 1322 err = cond_reltimedwait(&ntdomain_cv, &ntdomain_mtx, &to); 1323 if (err == ETIME) 1324 break; 1325 } 1326 1327 if (ntdomain_info.n_ipaddr != 0) { 1328 (void) strlcpy(dc, ntdomain_info.n_name, dc_len); 1329 found = B_TRUE; 1330 } 1331 (void) mutex_unlock(&ntdomain_mtx); 1332 1333 return (found); 1334 } 1335 1336 /* 1337 * smb_browser_infoinit 1338 * 1339 * This function is called only once when the browser starts 1340 * to initialize the global smb_binfo structure. 1341 */ 1342 static void 1343 smb_browser_infoinit(void) 1344 { 1345 (void) mutex_lock(&ntdomain_mtx); 1346 bzero(&ntdomain_info, sizeof (ntdomain_info)); 1347 (void) mutex_unlock(&ntdomain_mtx); 1348 1349 (void) rw_wrlock(&smb_binfo.bi_hlist_rwl); 1350 list_create(&smb_binfo.bi_hlist, sizeof (smb_hostinfo_t), 1351 offsetof(smb_hostinfo_t, hi_lnd)); 1352 smb_binfo.bi_hcnt = 0; 1353 (void) rw_unlock(&smb_binfo.bi_hlist_rwl); 1354 1355 (void) mutex_lock(&smb_binfo.bi_mtx); 1356 smb_binfo.bi_changed = B_FALSE; 1357 (void) mutex_unlock(&smb_binfo.bi_mtx); 1358 } 1359 1360 /* 1361 * smb_browser_infoterm 1362 * 1363 * This function is called only once when the browser stops 1364 * to destroy the smb_binfo structure. 1365 */ 1366 static void 1367 smb_browser_infoterm(void) 1368 { 1369 (void) rw_wrlock(&smb_binfo.bi_hlist_rwl); 1370 smb_browser_infofree(); 1371 list_destroy(&smb_binfo.bi_hlist); 1372 (void) rw_unlock(&smb_binfo.bi_hlist_rwl); 1373 } 1374 1375 /* 1376 * smb_browser_infofree 1377 * 1378 * Removes all the hostinfo structures from the browser list 1379 * and frees the allocated memory 1380 */ 1381 static void 1382 smb_browser_infofree(void) 1383 { 1384 smb_hostinfo_t *hinfo; 1385 1386 while ((hinfo = list_head(&smb_binfo.bi_hlist)) != NULL) { 1387 list_remove(&smb_binfo.bi_hlist, hinfo); 1388 free(hinfo); 1389 } 1390 1391 smb_binfo.bi_hcnt = 0; 1392 } 1393