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 (c) 2008, 2010, Oracle and/or its affiliates. All rights reserved. 23 * Copyright (c) 2017 by Delphix. All rights reserved. 24 * Copyright 2019 Nexenta by DDN, Inc. All rights reserved. 25 * Copyright 2021-2023 RackTop Systems, Inc. 26 */ 27 28 /* 29 * General Structures Layout 30 * ------------------------- 31 * 32 * This is a simplified diagram showing the relationship between most of the 33 * main structures. 34 * 35 * +-------------------+ 36 * | SMB_SERVER | 37 * +-------------------+ 38 * | 39 * | 40 * v 41 * +-------------------+ +-------------------+ +-------------------+ 42 * | SESSION |<----->| SESSION |......| SESSION | 43 * +-------------------+ +-------------------+ +-------------------+ 44 * | 45 * | 46 * v 47 * +-------------------+ +-------------------+ +-------------------+ 48 * | USER |<----->| USER |......| USER | 49 * +-------------------+ +-------------------+ +-------------------+ 50 * | 51 * | 52 * v 53 * +-------------------+ +-------------------+ +-------------------+ 54 * | TREE |<----->| TREE |......| TREE | 55 * +-------------------+ +-------------------+ +-------------------+ 56 * | | 57 * | | 58 * | v 59 * | +-------+ +-------+ +-------+ 60 * | | OFILE |<----->| OFILE |......| OFILE | 61 * | +-------+ +-------+ +-------+ 62 * | 63 * | 64 * v 65 * +-------+ +------+ +------+ 66 * | ODIR |<----->| ODIR |......| ODIR | 67 * +-------+ +------+ +------+ 68 * 69 * 70 * Module Interface Overview 71 * ------------------------- 72 * 73 * 74 * +===================================+ 75 * | smbd daemon | 76 * +===================================+ 77 * | | ^ 78 * | | | 79 * User | | | 80 * -----------|--------------|----------------|-------------------------------- 81 * Kernel | | | 82 * | | | 83 * | | | 84 * +=========|==============|================|=================+ 85 * | v v | | 86 * | +-----------+ +--------------------+ +------------------+ | 87 * | | IO | | Kernel Door Server | | User Door Servers| | 88 * | | Interface | | Interface | | Interface | | 89 * | +-----------+ +--------------------+ +------------------+ | 90 * | | | ^ ^ | 91 * | v v | | | +=========+ 92 * | +-----------------------------------+ | | | | 93 * | + SMB Server Management (this file) |<------------------| ZFS | 94 * | +-----------------------------------+ | | | | 95 * | | | | Module | 96 * | +-----------------------------------+ | | | | 97 * | + SMB Server Internal Layers |------+ | +=========+ 98 * | +-----------------------------------+ | 99 * | | 100 * | | 101 * +===========================================================+ 102 * 103 * 104 * Server State Machine 105 * -------------------- 106 * | 107 * | T0 108 * | 109 * v 110 * +-----------------------------+ 111 * | SMB_SERVER_STATE_CREATED | 112 * +-----------------------------+ 113 * | 114 * | T1 115 * | 116 * v 117 * +-----------------------------+ 118 * | SMB_SERVER_STATE_CONFIGURED | 119 * +-----------------------------+ 120 * | 121 * | T2 122 * | 123 * v 124 * +-----------------------------+ 125 * | SMB_SERVER_STATE_RUNNING / | 126 * | SMB_SERVER_STATE_STOPPING | 127 * +-----------------------------+ 128 * | 129 * | T3 130 * | 131 * v 132 * +-----------------------------+ 133 * | SMB_SERVER_STATE_DELETING | 134 * +-----------------------------+ 135 * | 136 * | 137 * | 138 * v 139 * 140 * States 141 * ------ 142 * 143 * SMB_SERVER_STATE_CREATED 144 * 145 * This is the state of the server just after creation. 146 * 147 * SMB_SERVER_STATE_CONFIGURED 148 * 149 * The server has been configured. 150 * 151 * SMB_SERVER_STATE_RUNNING 152 * 153 * The server has been started. While in this state the threads listening on 154 * the sockets are started. 155 * 156 * When a client establishes a connection the thread listening dispatches 157 * a task with the new session as an argument. If the dispatch fails the new 158 * session context is destroyed. 159 * 160 * SMB_SERVER_STATE_STOPPING 161 * 162 * The threads listening on the NBT and TCP sockets are being terminated. 163 * 164 * 165 * Transitions 166 * ----------- 167 * 168 * Transition T0 169 * 170 * The daemon smbd triggers its creation by opening the smbsrv device. If 171 * the zone where the daemon lives doesn't have an smb server yet it is 172 * created. 173 * 174 * smb_drv_open() --> smb_server_create() 175 * 176 * Transition T1 177 * 178 * This transition occurs in smb_server_configure(). It is triggered by the 179 * daemon through an Ioctl. 180 * 181 * smb_drv_ioctl(SMB_IOC_CONFIG) --> smb_server_configure() 182 * 183 * Transition T2 184 * 185 * This transition occurs in smb_server_start(). It is triggered by the 186 * daemon through an Ioctl. 187 * 188 * smb_drv_ioctl(SMB_IOC_START) --> smb_server_start() 189 * 190 * Transition T3 191 * 192 * This transition occurs in smb_server_delete(). It is triggered by the 193 * daemon when closing the smbsrv device 194 * 195 * smb_drv_close() --> smb_server_delete() 196 * 197 * Comments 198 * -------- 199 * 200 * This files assumes that there will one SMB server per zone. For now the 201 * smb server works only in global zone. There's nothing in this file preventing 202 * an smb server from being created in a non global zone. That limitation is 203 * enforced in user space. 204 */ 205 206 #include <sys/cmn_err.h> 207 #include <sys/priv.h> 208 #include <sys/zone.h> 209 #include <sys/sysmacros.h> 210 #include <sys/callb.h> 211 #include <sys/class.h> 212 #include <sys/disp.h> 213 #include <netinet/in.h> 214 #include <netinet/in_systm.h> 215 #include <netinet/ip.h> 216 #include <netinet/ip_icmp.h> 217 #include <netinet/ip_var.h> 218 #include <netinet/tcp.h> 219 #include <smbsrv/smb2_kproto.h> 220 #include <smbsrv/string.h> 221 #include <smbsrv/netbios.h> 222 #include <smbsrv/smb_fsops.h> 223 #include <smbsrv/smb_share.h> 224 #include <smbsrv/smb_door.h> 225 #include <smbsrv/smb_kstat.h> 226 227 static void smb_server_kstat_init(smb_server_t *); 228 static void smb_server_kstat_fini(smb_server_t *); 229 static void smb_server_timers(smb_thread_t *, void *); 230 static void smb_server_store_cfg(smb_server_t *, smb_ioc_cfg_t *); 231 static void smb_server_shutdown(smb_server_t *); 232 static int smb_server_fsop_start(smb_server_t *); 233 static void smb_server_fsop_stop(smb_server_t *); 234 static void smb_event_cancel(smb_server_t *, uint32_t); 235 static uint32_t smb_event_alloc_txid(void); 236 237 static void smb_server_disconnect_share(smb_server_t *, const char *); 238 static void smb_server_enum_users(smb_server_t *, smb_svcenum_t *); 239 static void smb_server_enum_trees(smb_server_t *, smb_svcenum_t *); 240 static int smb_server_session_disconnect(smb_server_t *, const char *, 241 const char *); 242 static int smb_server_fclose(smb_server_t *, uint32_t); 243 static int smb_server_kstat_update(kstat_t *, int); 244 static int smb_server_legacy_kstat_update(kstat_t *, int); 245 static void smb_server_listener_init(smb_server_t *, smb_listener_daemon_t *, 246 char *, in_port_t, int); 247 static void smb_server_listener_destroy(smb_listener_daemon_t *); 248 static int smb_server_listener_start(smb_listener_daemon_t *); 249 static void smb_server_listener_stop(smb_listener_daemon_t *); 250 static void smb_server_listener(smb_thread_t *, void *); 251 static void smb_server_receiver(void *); 252 static void smb_server_create_session(smb_listener_daemon_t *, ksocket_t); 253 static void smb_server_destroy_session(smb_session_t *); 254 static uint16_t smb_spool_get_fid(smb_server_t *); 255 static boolean_t smb_spool_lookup_doc_byfid(smb_server_t *, uint16_t, 256 smb_kspooldoc_t *); 257 258 #ifdef _KERNEL 259 int smb_create_process = 1; 260 static void smb_server_delproc(smb_server_t *); 261 static int smb_server_newproc(smb_server_t *); 262 static void smb_server_proc_main(void *); 263 #endif 264 265 /* 266 * How many "buckets" should our hash tables use? On a "real" server, 267 * make them much larger than the number of CPUs we're likely to have. 268 * On "fksmbd" make it smaller so dtrace logs are shorter. 269 * These must be powers of two. 270 */ 271 #ifdef _KERNEL 272 #define DEFAULT_HASH_NBUCKETS 256 /* real server */ 273 #else 274 #define DEFAULT_HASH_NBUCKETS 16 /* for "fksmbd" */ 275 #endif 276 uint32_t SMB_OFILE_HASH_NBUCKETS = DEFAULT_HASH_NBUCKETS; 277 uint32_t SMB_LEASE_HASH_NBUCKETS = DEFAULT_HASH_NBUCKETS; 278 279 int smb_event_debug = 0; 280 281 static smb_llist_t smb_servers; 282 283 /* for smb_server_destroy_session() */ 284 static smb_llist_t smb_server_session_zombies; 285 286 kmem_cache_t *smb_cache_request; 287 kmem_cache_t *smb_cache_session; 288 kmem_cache_t *smb_cache_user; 289 kmem_cache_t *smb_cache_tree; 290 kmem_cache_t *smb_cache_ofile; 291 kmem_cache_t *smb_cache_odir; 292 kmem_cache_t *smb_cache_opipe; 293 kmem_cache_t *smb_cache_event; 294 kmem_cache_t *smb_cache_lock; 295 296 /* 297 * ***************************************************************************** 298 * **************** Functions called from the device interface ***************** 299 * ***************************************************************************** 300 * 301 * These functions typically have to determine the relevant smb server 302 * to which the call applies. 303 */ 304 305 /* 306 * How many zones have an SMB server active? 307 */ 308 int 309 smb_server_get_count(void) 310 { 311 return (smb_llist_get_count(&smb_servers)); 312 } 313 314 /* 315 * smb_server_g_init 316 * 317 * This function must be called from smb_drv_attach(). 318 */ 319 int 320 smb_server_g_init(void) 321 { 322 int rc; 323 324 if ((rc = smb_vop_init()) != 0) 325 goto errout; 326 if ((rc = smb_fem_init()) != 0) 327 goto errout; 328 329 smb_kshare_g_init(); 330 smb_codepage_init(); 331 smb_mbc_init(); /* smb_mbc_cache */ 332 smb_node_init(); /* smb_node_cache, lists */ 333 smb2_lease_init(); 334 335 smb_cache_request = kmem_cache_create("smb_request_cache", 336 sizeof (smb_request_t), 8, NULL, NULL, NULL, NULL, NULL, 0); 337 smb_cache_session = kmem_cache_create("smb_session_cache", 338 sizeof (smb_session_t), 8, NULL, NULL, NULL, NULL, NULL, 0); 339 smb_cache_user = kmem_cache_create("smb_user_cache", 340 sizeof (smb_user_t), 8, NULL, NULL, NULL, NULL, NULL, 0); 341 smb_cache_tree = kmem_cache_create("smb_tree_cache", 342 sizeof (smb_tree_t), 8, NULL, NULL, NULL, NULL, NULL, 0); 343 smb_cache_ofile = kmem_cache_create("smb_ofile_cache", 344 sizeof (smb_ofile_t), 8, NULL, NULL, NULL, NULL, NULL, 0); 345 smb_cache_odir = kmem_cache_create("smb_odir_cache", 346 sizeof (smb_odir_t), 8, NULL, NULL, NULL, NULL, NULL, 0); 347 smb_cache_opipe = kmem_cache_create("smb_opipe_cache", 348 sizeof (smb_opipe_t), 8, NULL, NULL, NULL, NULL, NULL, 0); 349 smb_cache_event = kmem_cache_create("smb_event_cache", 350 sizeof (smb_event_t), 8, NULL, NULL, NULL, NULL, NULL, 0); 351 smb_cache_lock = kmem_cache_create("smb_lock_cache", 352 sizeof (smb_lock_t), 8, NULL, NULL, NULL, NULL, NULL, 0); 353 354 smb_llist_init(); 355 smb_llist_constructor(&smb_servers, sizeof (smb_server_t), 356 offsetof(smb_server_t, sv_lnd)); 357 358 smb_llist_constructor(&smb_server_session_zombies, 359 sizeof (smb_session_t), offsetof(smb_session_t, s_lnd)); 360 361 return (0); 362 363 errout: 364 smb_fem_fini(); 365 smb_vop_fini(); 366 return (rc); 367 } 368 369 /* 370 * smb_server_g_fini 371 * 372 * This function must called from smb_drv_detach(). It will fail if servers 373 * still exist. 374 */ 375 void 376 smb_server_g_fini(void) 377 { 378 379 ASSERT(smb_llist_get_count(&smb_servers) == 0); 380 381 smb_llist_fini(); 382 383 kmem_cache_destroy(smb_cache_request); 384 kmem_cache_destroy(smb_cache_session); 385 kmem_cache_destroy(smb_cache_user); 386 kmem_cache_destroy(smb_cache_tree); 387 kmem_cache_destroy(smb_cache_ofile); 388 kmem_cache_destroy(smb_cache_odir); 389 kmem_cache_destroy(smb_cache_opipe); 390 kmem_cache_destroy(smb_cache_event); 391 kmem_cache_destroy(smb_cache_lock); 392 393 smb2_lease_fini(); 394 smb_node_fini(); 395 smb_mbc_fini(); 396 smb_codepage_fini(); 397 smb_kshare_g_fini(); 398 399 smb_fem_fini(); 400 smb_vop_fini(); 401 402 smb_llist_destructor(&smb_servers); 403 } 404 405 /* 406 * smb_server_create 407 * 408 * Called by driver open 409 * 410 * This function will fail if there's already a server associated with the 411 * caller's zone. 412 * 413 * This object is one-to-one with zones, so we could instead 414 * create/destroy this via zone_key_create callbacks. 415 * See smb_server_delete() for destruction. 416 */ 417 int 418 smb_server_create(void) 419 { 420 zoneid_t zid; 421 smb_server_t *sv; 422 423 zid = getzoneid(); 424 425 smb_llist_enter(&smb_servers, RW_WRITER); 426 sv = smb_llist_head(&smb_servers); 427 while (sv) { 428 SMB_SERVER_VALID(sv); 429 if (sv->sv_zid == zid) { 430 smb_llist_exit(&smb_servers); 431 return (EPERM); 432 } 433 sv = smb_llist_next(&smb_servers, sv); 434 } 435 436 sv = kmem_zalloc(sizeof (smb_server_t), KM_SLEEP); 437 438 sv->sv_magic = SMB_SERVER_MAGIC; 439 sv->sv_state = SMB_SERVER_STATE_CREATED; 440 sv->sv_zid = zid; 441 sv->sv_pid = ddi_get_pid(); 442 sv->sv_proc_state = SMB_THREAD_STATE_EXITED; 443 444 mutex_init(&sv->sv_mutex, NULL, MUTEX_DEFAULT, NULL); 445 cv_init(&sv->sv_cv, NULL, CV_DEFAULT, NULL); 446 cv_init(&sv->sp_info.sp_cv, NULL, CV_DEFAULT, NULL); 447 448 sv->sv_persistid_ht = smb_hash_create(sizeof (smb_ofile_t), 449 offsetof(smb_ofile_t, f_dh_lnd), SMB_OFILE_HASH_NBUCKETS); 450 451 sv->sv_lease_ht = smb_hash_create(sizeof (smb_lease_t), 452 offsetof(smb_lease_t, ls_lnd), SMB_LEASE_HASH_NBUCKETS); 453 454 smb_llist_constructor(&sv->sv_session_list, sizeof (smb_session_t), 455 offsetof(smb_session_t, s_lnd)); 456 457 smb_llist_constructor(&sv->sv_event_list, sizeof (smb_event_t), 458 offsetof(smb_event_t, se_lnd)); 459 460 smb_llist_constructor(&sv->sp_info.sp_list, sizeof (smb_kspooldoc_t), 461 offsetof(smb_kspooldoc_t, sd_lnd)); 462 463 smb_llist_constructor(&sv->sp_info.sp_fidlist, 464 sizeof (smb_spoolfid_t), offsetof(smb_spoolfid_t, sf_lnd)); 465 466 sv->sv_disp_stats1 = kmem_zalloc(SMB_COM_NUM * 467 sizeof (smb_disp_stats_t), KM_SLEEP); 468 469 sv->sv_disp_stats2 = kmem_zalloc(SMB2__NCMDS * 470 sizeof (smb_disp_stats_t), KM_SLEEP); 471 472 smb_thread_init(&sv->si_thread_timers, "smb_timers", 473 smb_server_timers, sv, smbsrv_timer_pri, sv); 474 475 smb_srqueue_init(&sv->sv_srqueue); 476 477 smb_kdoor_init(sv); 478 smb_kshare_init(sv); 479 smb_server_kstat_init(sv); 480 481 smb_threshold_init(&sv->sv_ssetup_ct, SMB_SSETUP_CMD, 482 smb_ssetup_threshold, smb_ssetup_timeout); 483 smb_threshold_init(&sv->sv_tcon_ct, SMB_TCON_CMD, 484 smb_tcon_threshold, smb_tcon_timeout); 485 smb_threshold_init(&sv->sv_opipe_ct, SMB_OPIPE_CMD, 486 smb_opipe_threshold, smb_opipe_timeout); 487 smb_threshold_init(&sv->sv_logoff_ct, SMB_LOGOFF_CMD, 488 smb_logoff_threshold, smb_logoff_timeout); 489 490 smb_llist_insert_tail(&smb_servers, sv); 491 smb_llist_exit(&smb_servers); 492 493 return (0); 494 } 495 496 /* 497 * smb_server_delete 498 * 499 * Called by driver close 500 * 501 * This function will delete the server passed in. It will make sure that all 502 * activity associated that server has ceased before destroying it. 503 */ 504 int 505 smb_server_delete(smb_server_t *sv) 506 { 507 508 mutex_enter(&sv->sv_mutex); 509 switch (sv->sv_state) { 510 case SMB_SERVER_STATE_RUNNING: 511 sv->sv_state = SMB_SERVER_STATE_STOPPING; 512 mutex_exit(&sv->sv_mutex); 513 smb_server_shutdown(sv); 514 mutex_enter(&sv->sv_mutex); 515 cv_broadcast(&sv->sp_info.sp_cv); 516 sv->sv_state = SMB_SERVER_STATE_DELETING; 517 break; 518 case SMB_SERVER_STATE_STOPPING: 519 sv->sv_state = SMB_SERVER_STATE_DELETING; 520 break; 521 case SMB_SERVER_STATE_CONFIGURED: 522 case SMB_SERVER_STATE_CREATED: 523 sv->sv_state = SMB_SERVER_STATE_DELETING; 524 break; 525 default: 526 SMB_SERVER_STATE_VALID(sv->sv_state); 527 mutex_exit(&sv->sv_mutex); 528 smb_server_release(sv); 529 return (ENOTTY); 530 } 531 532 ASSERT(sv->sv_state == SMB_SERVER_STATE_DELETING); 533 534 sv->sv_refcnt--; 535 while (sv->sv_refcnt) 536 cv_wait(&sv->sv_cv, &sv->sv_mutex); 537 538 mutex_exit(&sv->sv_mutex); 539 540 smb_llist_enter(&smb_servers, RW_WRITER); 541 smb_llist_remove(&smb_servers, sv); 542 smb_llist_exit(&smb_servers); 543 544 smb_threshold_fini(&sv->sv_ssetup_ct); 545 smb_threshold_fini(&sv->sv_tcon_ct); 546 smb_threshold_fini(&sv->sv_opipe_ct); 547 smb_threshold_fini(&sv->sv_logoff_ct); 548 549 smb_server_listener_destroy(&sv->sv_nbt_daemon); 550 smb_server_listener_destroy(&sv->sv_tcp_daemon); 551 rw_destroy(&sv->sv_cfg_lock); 552 smb_server_kstat_fini(sv); 553 smb_kshare_fini(sv); 554 smb_kdoor_fini(sv); 555 smb_llist_destructor(&sv->sv_event_list); 556 smb_llist_destructor(&sv->sv_session_list); 557 558 kmem_free(sv->sv_disp_stats1, 559 SMB_COM_NUM * sizeof (smb_disp_stats_t)); 560 561 kmem_free(sv->sv_disp_stats2, 562 SMB2__NCMDS * sizeof (smb_disp_stats_t)); 563 564 smb_srqueue_destroy(&sv->sv_srqueue); 565 smb_thread_destroy(&sv->si_thread_timers); 566 567 mutex_destroy(&sv->sv_mutex); 568 smb_hash_destroy(sv->sv_lease_ht); 569 smb_hash_destroy(sv->sv_persistid_ht); 570 cv_destroy(&sv->sv_cv); 571 sv->sv_magic = 0; 572 kmem_free(sv, sizeof (smb_server_t)); 573 574 return (0); 575 } 576 577 /* 578 * smb_server_configure 579 * 580 * Called via SMB_IOC_CONFIG, for smbd startup or refresh. 581 */ 582 int 583 smb_server_configure(smb_ioc_cfg_t *ioc) 584 { 585 int rc = 0; 586 smb_server_t *sv; 587 588 /* 589 * Reality check negotiation token length vs. #define'd maximum. 590 */ 591 if (ioc->negtok_len > SMB_PI_MAX_NEGTOK) 592 return (EINVAL); 593 594 rc = smb_server_lookup(&sv); 595 if (rc) 596 return (rc); 597 598 mutex_enter(&sv->sv_mutex); 599 switch (sv->sv_state) { 600 case SMB_SERVER_STATE_CREATED: 601 smb_server_store_cfg(sv, ioc); 602 sv->sv_state = SMB_SERVER_STATE_CONFIGURED; 603 break; 604 605 case SMB_SERVER_STATE_CONFIGURED: 606 smb_server_store_cfg(sv, ioc); 607 break; 608 609 case SMB_SERVER_STATE_RUNNING: 610 case SMB_SERVER_STATE_STOPPING: 611 rw_enter(&sv->sv_cfg_lock, RW_WRITER); 612 smb_server_store_cfg(sv, ioc); 613 rw_exit(&sv->sv_cfg_lock); 614 break; 615 616 default: 617 SMB_SERVER_STATE_VALID(sv->sv_state); 618 rc = EFAULT; 619 break; 620 } 621 mutex_exit(&sv->sv_mutex); 622 623 smb_server_release(sv); 624 625 return (rc); 626 } 627 628 /* 629 * smb_server_start 630 * 631 * Called via SMB_IOC_START during smbd startup. 632 * Bring up the activities requried for SMB service. 633 */ 634 int 635 smb_server_start(smb_ioc_start_t *ioc) 636 { 637 int rc = 0; 638 int family; 639 smb_server_t *sv; 640 cred_t *ucr; 641 struct proc *tqproc; 642 643 rc = smb_server_lookup(&sv); 644 if (rc) 645 return (rc); 646 647 mutex_enter(&sv->sv_mutex); 648 switch (sv->sv_state) { 649 case SMB_SERVER_STATE_CONFIGURED: 650 651 #ifdef _KERNEL 652 if (smb_create_process) { 653 rc = smb_server_newproc(sv); 654 if (rc != 0) 655 break; 656 } 657 #endif /* _KERNEL */ 658 659 if ((rc = smb_server_fsop_start(sv)) != 0) 660 break; 661 662 /* 663 * Note: smb_kshare_start needs sv_session. 664 */ 665 sv->sv_session = smb_session_create(NULL, 0, sv, 0); 666 if (sv->sv_session == NULL) { 667 rc = ENOMEM; 668 break; 669 } 670 671 /* 672 * Create a logon on the server session, 673 * used when importing CA shares. 674 */ 675 sv->sv_rootuser = smb_user_new(sv->sv_session); 676 ucr = smb_kcred_create(); 677 rc = smb_user_logon(sv->sv_rootuser, ucr, "", "root", 678 SMB_USER_FLAG_ADMIN, 0, 0); 679 crfree(ucr); 680 ucr = NULL; 681 if (rc != 0) { 682 cmn_err(CE_NOTE, "smb_server_start: " 683 "failed to create root user"); 684 break; 685 } 686 687 if ((rc = smb_kshare_start(sv)) != 0) 688 break; 689 690 /* 691 * Create our taskq's (thread pools) 692 * 693 * NB: the proc passed here has to be a "system" one. 694 * Normally that's p0, or the NGZ eqivalent. 695 * 696 * The notify pool is sized at a quarter the number of 697 * worker threads (instead of another config item). 698 */ 699 tqproc = (sv->sv_proc_p != NULL) ? 700 sv->sv_proc_p : curzone->zone_zsched; 701 702 sv->sv_notify_pool = taskq_create_proc("smb_notify", 703 sv->sv_cfg.skc_maxworkers / 4, smbsrv_notify_pri, 704 sv->sv_cfg.skc_maxworkers / 4, INT_MAX, 705 tqproc, TASKQ_DYNAMIC|TASKQ_THREADS_LWP); 706 707 sv->sv_worker_pool = taskq_create_proc("smb_workers", 708 sv->sv_cfg.skc_maxworkers, smbsrv_worker_pri, 709 sv->sv_cfg.skc_maxworkers, INT_MAX, 710 tqproc, TASKQ_DYNAMIC|TASKQ_THREADS_LWP); 711 712 sv->sv_receiver_pool = taskq_create_proc("smb_receivers", 713 sv->sv_cfg.skc_maxconnections, smbsrv_receive_pri, 714 sv->sv_cfg.skc_maxconnections, INT_MAX, 715 tqproc, TASKQ_DYNAMIC|TASKQ_THREADS_LWP); 716 717 if (sv->sv_notify_pool == NULL || 718 sv->sv_worker_pool == NULL || 719 sv->sv_receiver_pool == NULL) { 720 rc = ENOMEM; 721 break; 722 } 723 724 #ifdef _KERNEL 725 ASSERT(sv->sv_lmshrd == NULL); 726 sv->sv_lmshrd = smb_kshare_door_init(ioc->lmshrd); 727 if (sv->sv_lmshrd == NULL) 728 break; 729 if ((rc = smb_kdoor_open(sv, ioc->udoor)) != 0) { 730 cmn_err(CE_WARN, "Cannot open smbd door"); 731 break; 732 } 733 #else /* _KERNEL */ 734 /* Fake kernel does not use the kshare_door */ 735 fksmb_kdoor_open(sv, ioc->udoor_func); 736 #endif /* _KERNEL */ 737 738 if ((rc = smb_thread_start(&sv->si_thread_timers)) != 0) 739 break; 740 741 family = AF_INET; 742 smb_server_listener_init(sv, &sv->sv_nbt_daemon, 743 "smb_nbt_listener", IPPORT_NETBIOS_SSN, family); 744 if (sv->sv_cfg.skc_ipv6_enable) 745 family = AF_INET6; 746 smb_server_listener_init(sv, &sv->sv_tcp_daemon, 747 "smb_tcp_listener", IPPORT_SMB, family); 748 rc = smb_server_listener_start(&sv->sv_tcp_daemon); 749 if (rc != 0) 750 break; 751 if (sv->sv_cfg.skc_netbios_enable) 752 (void) smb_server_listener_start(&sv->sv_nbt_daemon); 753 754 sv->sv_state = SMB_SERVER_STATE_RUNNING; 755 sv->sv_start_time = gethrtime(); 756 mutex_exit(&sv->sv_mutex); 757 smb_server_release(sv); 758 smb_export_start(sv); 759 return (0); 760 default: 761 SMB_SERVER_STATE_VALID(sv->sv_state); 762 mutex_exit(&sv->sv_mutex); 763 smb_server_release(sv); 764 return (ENOTTY); 765 } 766 767 mutex_exit(&sv->sv_mutex); 768 smb_server_shutdown(sv); 769 smb_server_release(sv); 770 return (rc); 771 } 772 773 /* 774 * An smbd is shutting down. 775 */ 776 int 777 smb_server_stop(void) 778 { 779 smb_server_t *sv; 780 int rc; 781 782 if ((rc = smb_server_lookup(&sv)) != 0) 783 return (rc); 784 785 mutex_enter(&sv->sv_mutex); 786 switch (sv->sv_state) { 787 case SMB_SERVER_STATE_RUNNING: 788 sv->sv_state = SMB_SERVER_STATE_STOPPING; 789 mutex_exit(&sv->sv_mutex); 790 smb_server_shutdown(sv); 791 mutex_enter(&sv->sv_mutex); 792 cv_broadcast(&sv->sp_info.sp_cv); 793 break; 794 default: 795 SMB_SERVER_STATE_VALID(sv->sv_state); 796 break; 797 } 798 mutex_exit(&sv->sv_mutex); 799 800 smb_server_release(sv); 801 return (0); 802 } 803 804 boolean_t 805 smb_server_is_stopping(smb_server_t *sv) 806 { 807 boolean_t status; 808 809 SMB_SERVER_VALID(sv); 810 811 mutex_enter(&sv->sv_mutex); 812 813 switch (sv->sv_state) { 814 case SMB_SERVER_STATE_STOPPING: 815 case SMB_SERVER_STATE_DELETING: 816 status = B_TRUE; 817 break; 818 default: 819 status = B_FALSE; 820 break; 821 } 822 823 mutex_exit(&sv->sv_mutex); 824 return (status); 825 } 826 827 void 828 smb_server_cancel_event(smb_server_t *sv, uint32_t txid) 829 { 830 smb_event_cancel(sv, txid); 831 } 832 833 int 834 smb_server_notify_event(smb_ioc_event_t *ioc) 835 { 836 smb_server_t *sv; 837 int rc; 838 839 if ((rc = smb_server_lookup(&sv)) == 0) { 840 smb_event_notify(sv, ioc->txid); 841 smb_server_release(sv); 842 } 843 844 return (rc); 845 } 846 847 /* 848 * smb_server_spooldoc 849 * 850 * Waits for print file close broadcast. 851 * Gets the head of the fid list, 852 * then searches the spooldoc list and returns 853 * this info via the ioctl to user land. 854 * 855 * rc - 0 success 856 */ 857 858 int 859 smb_server_spooldoc(smb_ioc_spooldoc_t *ioc) 860 { 861 smb_server_t *sv; 862 int rc; 863 smb_kspooldoc_t *spdoc; 864 uint16_t fid; 865 866 if ((rc = smb_server_lookup(&sv)) != 0) 867 return (rc); 868 869 if (sv->sv_cfg.skc_print_enable == 0) { 870 rc = ENOTTY; 871 goto out; 872 } 873 874 mutex_enter(&sv->sv_mutex); 875 for (;;) { 876 if (sv->sv_state != SMB_SERVER_STATE_RUNNING) { 877 rc = ECANCELED; 878 break; 879 } 880 if ((fid = smb_spool_get_fid(sv)) != 0) { 881 rc = 0; 882 break; 883 } 884 if (cv_wait_sig(&sv->sp_info.sp_cv, &sv->sv_mutex) == 0) { 885 rc = EINTR; 886 break; 887 } 888 } 889 mutex_exit(&sv->sv_mutex); 890 if (rc != 0) 891 goto out; 892 893 spdoc = kmem_zalloc(sizeof (*spdoc), KM_SLEEP); 894 if (smb_spool_lookup_doc_byfid(sv, fid, spdoc)) { 895 ioc->spool_num = spdoc->sd_spool_num; 896 ioc->ipaddr = spdoc->sd_ipaddr; 897 (void) strlcpy(ioc->path, spdoc->sd_path, 898 MAXPATHLEN); 899 (void) strlcpy(ioc->username, 900 spdoc->sd_username, MAXNAMELEN); 901 } else { 902 /* Did not find that print job. */ 903 rc = EAGAIN; 904 } 905 kmem_free(spdoc, sizeof (*spdoc)); 906 907 out: 908 smb_server_release(sv); 909 return (rc); 910 } 911 912 int 913 smb_server_set_gmtoff(smb_ioc_gmt_t *ioc) 914 { 915 int rc; 916 smb_server_t *sv; 917 918 if ((rc = smb_server_lookup(&sv)) == 0) { 919 sv->si_gmtoff = ioc->offset; 920 smb_server_release(sv); 921 } 922 923 return (rc); 924 } 925 926 int 927 smb_server_numopen(smb_ioc_opennum_t *ioc) 928 { 929 smb_server_t *sv; 930 int rc; 931 932 if ((rc = smb_server_lookup(&sv)) == 0) { 933 ioc->open_users = sv->sv_users; 934 ioc->open_trees = sv->sv_trees; 935 ioc->open_files = sv->sv_files + sv->sv_pipes; 936 smb_server_release(sv); 937 } 938 return (rc); 939 } 940 941 /* 942 * Enumerate objects within the server. The svcenum provides the 943 * enumeration context, i.e. what the caller want to get back. 944 */ 945 int 946 smb_server_enum(smb_ioc_svcenum_t *ioc) 947 { 948 smb_svcenum_t *svcenum = &ioc->svcenum; 949 smb_server_t *sv; 950 int rc; 951 952 /* 953 * Reality check that the buffer-length insize the enum doesn't 954 * overrun the ioctl's total length. 955 */ 956 if (svcenum->se_buflen + sizeof (*ioc) > ioc->hdr.len) 957 return (EINVAL); 958 959 if ((rc = smb_server_lookup(&sv)) != 0) 960 return (rc); 961 962 svcenum->se_bavail = svcenum->se_buflen; 963 svcenum->se_bused = 0; 964 svcenum->se_nitems = 0; 965 966 switch (svcenum->se_type) { 967 case SMB_SVCENUM_TYPE_USER: 968 smb_server_enum_users(sv, svcenum); 969 break; 970 case SMB_SVCENUM_TYPE_TREE: 971 case SMB_SVCENUM_TYPE_FILE: 972 smb_server_enum_trees(sv, svcenum); 973 break; 974 default: 975 rc = EINVAL; 976 } 977 978 smb_server_release(sv); 979 return (rc); 980 } 981 982 /* 983 * Look for sessions to disconnect by client and user name. 984 */ 985 int 986 smb_server_session_close(smb_ioc_session_t *ioc) 987 { 988 smb_server_t *sv; 989 int cnt; 990 int rc; 991 992 if ((rc = smb_server_lookup(&sv)) != 0) 993 return (rc); 994 995 cnt = smb_server_session_disconnect(sv, ioc->client, ioc->username); 996 997 smb_server_release(sv); 998 999 if (cnt == 0) 1000 return (ENOENT); 1001 return (0); 1002 } 1003 1004 /* 1005 * Close a file by uniqid. 1006 */ 1007 int 1008 smb_server_file_close(smb_ioc_fileid_t *ioc) 1009 { 1010 uint32_t uniqid = ioc->uniqid; 1011 smb_server_t *sv; 1012 int rc; 1013 1014 if ((rc = smb_server_lookup(&sv)) != 0) 1015 return (rc); 1016 1017 rc = smb_server_fclose(sv, uniqid); 1018 1019 smb_server_release(sv); 1020 return (rc); 1021 } 1022 1023 /* 1024 * These functions determine the relevant smb server to which the call apply. 1025 */ 1026 1027 uint32_t 1028 smb_server_get_session_count(smb_server_t *sv) 1029 { 1030 uint32_t counter = 0; 1031 1032 counter = smb_llist_get_count(&sv->sv_session_list); 1033 1034 return (counter); 1035 } 1036 1037 /* 1038 * Gets the smb_node of the specified share path. 1039 * Node is returned held (caller must rele.) 1040 */ 1041 int 1042 smb_server_share_lookup(smb_server_t *sv, const char *shr_path, 1043 smb_node_t **nodepp) 1044 { 1045 smb_request_t *sr; 1046 smb_node_t *fnode = NULL; 1047 smb_node_t *dnode = NULL; 1048 char last_comp[MAXNAMELEN]; 1049 int rc = 0; 1050 1051 ASSERT(shr_path); 1052 1053 mutex_enter(&sv->sv_mutex); 1054 switch (sv->sv_state) { 1055 case SMB_SERVER_STATE_RUNNING: 1056 break; 1057 default: 1058 mutex_exit(&sv->sv_mutex); 1059 return (ENOTACTIVE); 1060 } 1061 mutex_exit(&sv->sv_mutex); 1062 1063 if ((sr = smb_request_alloc(sv->sv_session, 0)) == NULL) { 1064 return (ENOTCONN); 1065 } 1066 sr->user_cr = zone_kcred(); 1067 1068 rc = smb_pathname_reduce(sr, sr->user_cr, shr_path, 1069 NULL, NULL, &dnode, last_comp); 1070 1071 if (rc == 0) { 1072 rc = smb_fsop_lookup(sr, sr->user_cr, SMB_FOLLOW_LINKS, 1073 sv->si_root_smb_node, dnode, last_comp, &fnode); 1074 smb_node_release(dnode); 1075 } 1076 1077 smb_request_free(sr); 1078 1079 if (rc != 0) 1080 return (rc); 1081 1082 ASSERT(fnode->vp && fnode->vp->v_vfsp); 1083 1084 *nodepp = fnode; 1085 1086 return (0); 1087 } 1088 1089 #ifdef _KERNEL 1090 /* 1091 * This is a special interface that will be utilized by ZFS to cause a share to 1092 * be added/removed. 1093 * 1094 * arg is either a lmshare_info_t or share_name from userspace. 1095 * It will need to be copied into the kernel. It is lmshare_info_t 1096 * for add operations and share_name for delete operations. 1097 */ 1098 int 1099 smb_server_share(void *arg, boolean_t add_share) 1100 { 1101 smb_server_t *sv; 1102 int rc; 1103 1104 if ((rc = smb_server_lookup(&sv)) == 0) { 1105 mutex_enter(&sv->sv_mutex); 1106 switch (sv->sv_state) { 1107 case SMB_SERVER_STATE_RUNNING: 1108 mutex_exit(&sv->sv_mutex); 1109 (void) smb_kshare_upcall(sv->sv_lmshrd, arg, add_share); 1110 break; 1111 default: 1112 mutex_exit(&sv->sv_mutex); 1113 break; 1114 } 1115 smb_server_release(sv); 1116 } 1117 1118 return (rc); 1119 } 1120 #endif /* _KERNEL */ 1121 1122 int 1123 smb_server_unshare(const char *sharename) 1124 { 1125 smb_server_t *sv; 1126 int rc; 1127 1128 if ((rc = smb_server_lookup(&sv))) 1129 return (rc); 1130 1131 mutex_enter(&sv->sv_mutex); 1132 switch (sv->sv_state) { 1133 case SMB_SERVER_STATE_RUNNING: 1134 case SMB_SERVER_STATE_STOPPING: 1135 break; 1136 default: 1137 mutex_exit(&sv->sv_mutex); 1138 smb_server_release(sv); 1139 return (ENOTACTIVE); 1140 } 1141 mutex_exit(&sv->sv_mutex); 1142 1143 smb_server_disconnect_share(sv, sharename); 1144 1145 smb_server_release(sv); 1146 return (0); 1147 } 1148 1149 /* 1150 * Disconnect the specified share. 1151 * Typically called when a share has been removed. 1152 */ 1153 static void 1154 smb_server_disconnect_share(smb_server_t *sv, const char *sharename) 1155 { 1156 smb_llist_t *ll; 1157 smb_session_t *session; 1158 1159 ll = &sv->sv_session_list; 1160 smb_llist_enter(ll, RW_READER); 1161 1162 session = smb_llist_head(ll); 1163 while (session) { 1164 SMB_SESSION_VALID(session); 1165 smb_rwx_rwenter(&session->s_lock, RW_READER); 1166 switch (session->s_state) { 1167 case SMB_SESSION_STATE_NEGOTIATED: 1168 smb_rwx_rwexit(&session->s_lock); 1169 smb_session_disconnect_share(session, sharename); 1170 break; 1171 default: 1172 smb_rwx_rwexit(&session->s_lock); 1173 break; 1174 } 1175 session = smb_llist_next(ll, session); 1176 } 1177 1178 smb_llist_exit(ll); 1179 } 1180 1181 #ifdef _KERNEL 1182 1183 /* 1184 * Create a process to own SMB server threads (like zfs spa.c) 1185 * so we can see the CPU usage etc. with "prstat -L". 1186 * The new process MUST be in the same zone as the caller. 1187 */ 1188 static int 1189 smb_server_newproc(smb_server_t *sv) 1190 { 1191 int rc; 1192 1193 /* 1194 * Todo: Fix newproc() for zones. 1195 * At present, it always creates in p0. 1196 * For now, only do this for the global zone. 1197 */ 1198 if (getzoneid() != GLOBAL_ZONEID) 1199 return (0); 1200 1201 mutex_enter(&sv->sv_proc_lock); 1202 if (sv->sv_proc_p != NULL) { 1203 /* restart? re-use proc */ 1204 rc = 0; 1205 goto out; 1206 } 1207 1208 sv->sv_proc_state = SMB_THREAD_STATE_STARTING; 1209 rc = newproc(smb_server_proc_main, (caddr_t)sv, 1210 syscid, smbsrv_base_pri, NULL, 0); 1211 if (rc != 0) { 1212 cmn_err(CE_WARN, "newproc failed, rc=%d", rc); 1213 goto out; 1214 } 1215 1216 /* Rendez-vous with new proc thread. */ 1217 while (sv->sv_proc_state == SMB_THREAD_STATE_STARTING) { 1218 cv_wait(&sv->sv_proc_cv, &sv->sv_proc_lock); 1219 1220 } 1221 if (sv->sv_proc_state != SMB_THREAD_STATE_RUNNING) { 1222 rc = ESRCH; 1223 goto out; 1224 } 1225 ASSERT(sv->sv_proc_p != NULL); 1226 1227 out: 1228 mutex_exit(&sv->sv_proc_lock); 1229 return (rc); 1230 } 1231 1232 /* 1233 * Main thread for the process we create to own SMB server threads. 1234 */ 1235 static void 1236 smb_server_proc_main(void *arg) 1237 { 1238 callb_cpr_t cprinfo; 1239 smb_server_t *sv = arg; 1240 user_t *pu = PTOU(curproc); 1241 zoneid_t zid = getzoneid(); 1242 1243 ASSERT(curproc != &p0); 1244 ASSERT(zid == sv->sv_zid); 1245 1246 (void) strlcpy(pu->u_comm, "smbsrv", sizeof (pu->u_comm)); 1247 (void) snprintf(pu->u_psargs, sizeof (pu->u_psargs), 1248 "smbsrv %d", (int)zid); 1249 1250 CALLB_CPR_INIT(&cprinfo, &sv->sv_proc_lock, callb_generic_cpr, 1251 pu->u_psargs); 1252 1253 mutex_enter(&sv->sv_proc_lock); 1254 ASSERT(sv->sv_proc_state == SMB_THREAD_STATE_STARTING); 1255 1256 sv->sv_proc_p = curproc; 1257 sv->sv_proc_did = curthread->t_did; 1258 1259 sv->sv_proc_state = SMB_THREAD_STATE_RUNNING; 1260 cv_broadcast(&sv->sv_proc_cv); 1261 1262 CALLB_CPR_SAFE_BEGIN(&cprinfo); 1263 while (sv->sv_proc_state == SMB_THREAD_STATE_RUNNING) 1264 cv_wait(&sv->sv_proc_cv, &sv->sv_proc_lock); 1265 CALLB_CPR_SAFE_END(&cprinfo, &sv->sv_proc_lock); 1266 1267 ASSERT(sv->sv_proc_state == SMB_THREAD_STATE_EXITING); 1268 sv->sv_proc_state = SMB_THREAD_STATE_EXITED; 1269 sv->sv_proc_p = NULL; 1270 cv_broadcast(&sv->sv_proc_cv); 1271 CALLB_CPR_EXIT(&cprinfo); /* mutex_exit sv_proc_lock */ 1272 1273 /* Note: lwp_exit() expects p_lock entered. */ 1274 mutex_enter(&curproc->p_lock); 1275 lwp_exit(); 1276 } 1277 1278 /* 1279 * Delete the server proc (if any) 1280 */ 1281 static void 1282 smb_server_delproc(smb_server_t *sv) 1283 { 1284 1285 mutex_enter(&sv->sv_proc_lock); 1286 1287 if (sv->sv_proc_state != SMB_THREAD_STATE_RUNNING) 1288 goto out; 1289 ASSERT(sv->sv_proc_p != NULL); 1290 1291 sv->sv_proc_state = SMB_THREAD_STATE_EXITING; 1292 cv_broadcast(&sv->sv_proc_cv); 1293 1294 /* Rendez-vous with proc thread. */ 1295 while (sv->sv_proc_state == SMB_THREAD_STATE_EXITING) { 1296 cv_wait(&sv->sv_proc_cv, &sv->sv_proc_lock); 1297 1298 } 1299 if (sv->sv_proc_state != SMB_THREAD_STATE_EXITED) { 1300 cmn_err(CE_WARN, "smb_server_delproc, state=%d", 1301 sv->sv_proc_state); 1302 goto out; 1303 } 1304 if (sv->sv_proc_did != 0) { 1305 thread_join(sv->sv_proc_did); 1306 sv->sv_proc_did = 0; 1307 } 1308 1309 out: 1310 mutex_exit(&sv->sv_proc_lock); 1311 } 1312 1313 #endif /* _KERNEL */ 1314 1315 /* 1316 * ***************************************************************************** 1317 * **************** Functions called from the internal layers ****************** 1318 * ***************************************************************************** 1319 * 1320 * These functions are provided the relevant smb server by the caller. 1321 */ 1322 1323 void 1324 smb_server_get_cfg(smb_server_t *sv, smb_kmod_cfg_t *cfg) 1325 { 1326 rw_enter(&sv->sv_cfg_lock, RW_READER); 1327 bcopy(&sv->sv_cfg, cfg, sizeof (*cfg)); 1328 rw_exit(&sv->sv_cfg_lock); 1329 } 1330 1331 /* 1332 * 1333 */ 1334 void 1335 smb_server_inc_nbt_sess(smb_server_t *sv) 1336 { 1337 SMB_SERVER_VALID(sv); 1338 atomic_inc_32(&sv->sv_nbt_sess); 1339 } 1340 1341 void 1342 smb_server_dec_nbt_sess(smb_server_t *sv) 1343 { 1344 SMB_SERVER_VALID(sv); 1345 atomic_dec_32(&sv->sv_nbt_sess); 1346 } 1347 1348 void 1349 smb_server_inc_tcp_sess(smb_server_t *sv) 1350 { 1351 SMB_SERVER_VALID(sv); 1352 atomic_inc_32(&sv->sv_tcp_sess); 1353 } 1354 1355 void 1356 smb_server_dec_tcp_sess(smb_server_t *sv) 1357 { 1358 SMB_SERVER_VALID(sv); 1359 atomic_dec_32(&sv->sv_tcp_sess); 1360 } 1361 1362 void 1363 smb_server_inc_users(smb_server_t *sv) 1364 { 1365 SMB_SERVER_VALID(sv); 1366 atomic_inc_32(&sv->sv_users); 1367 } 1368 1369 void 1370 smb_server_dec_users(smb_server_t *sv) 1371 { 1372 SMB_SERVER_VALID(sv); 1373 atomic_dec_32(&sv->sv_users); 1374 } 1375 1376 void 1377 smb_server_inc_trees(smb_server_t *sv) 1378 { 1379 SMB_SERVER_VALID(sv); 1380 atomic_inc_32(&sv->sv_trees); 1381 } 1382 1383 void 1384 smb_server_dec_trees(smb_server_t *sv) 1385 { 1386 SMB_SERVER_VALID(sv); 1387 atomic_dec_32(&sv->sv_trees); 1388 } 1389 1390 void 1391 smb_server_inc_files(smb_server_t *sv) 1392 { 1393 SMB_SERVER_VALID(sv); 1394 atomic_inc_32(&sv->sv_files); 1395 } 1396 1397 void 1398 smb_server_dec_files(smb_server_t *sv) 1399 { 1400 SMB_SERVER_VALID(sv); 1401 atomic_dec_32(&sv->sv_files); 1402 } 1403 1404 void 1405 smb_server_inc_pipes(smb_server_t *sv) 1406 { 1407 SMB_SERVER_VALID(sv); 1408 atomic_inc_32(&sv->sv_pipes); 1409 } 1410 1411 void 1412 smb_server_dec_pipes(smb_server_t *sv) 1413 { 1414 SMB_SERVER_VALID(sv); 1415 atomic_dec_32(&sv->sv_pipes); 1416 } 1417 1418 void 1419 smb_server_add_rxb(smb_server_t *sv, int64_t value) 1420 { 1421 SMB_SERVER_VALID(sv); 1422 atomic_add_64(&sv->sv_rxb, value); 1423 } 1424 1425 void 1426 smb_server_add_txb(smb_server_t *sv, int64_t value) 1427 { 1428 SMB_SERVER_VALID(sv); 1429 atomic_add_64(&sv->sv_txb, value); 1430 } 1431 1432 void 1433 smb_server_inc_req(smb_server_t *sv) 1434 { 1435 SMB_SERVER_VALID(sv); 1436 atomic_inc_64(&sv->sv_nreq); 1437 } 1438 1439 /* 1440 * ***************************************************************************** 1441 * *************************** Static Functions ******************************** 1442 * ***************************************************************************** 1443 */ 1444 1445 static void 1446 smb_server_timers(smb_thread_t *thread, void *arg) 1447 { 1448 smb_server_t *sv = (smb_server_t *)arg; 1449 1450 ASSERT(sv != NULL); 1451 1452 /* 1453 * This kills old inactive sessions and expired durable 1454 * handles. The session code expects one call per minute. 1455 */ 1456 while (smb_thread_continue_timedwait(thread, 60 /* Seconds */)) { 1457 if (sv->sv_cfg.skc_keepalive != 0) 1458 smb_session_timers(sv); 1459 smb2_durable_timers(sv); 1460 } 1461 } 1462 1463 /* 1464 * smb_server_kstat_init 1465 */ 1466 static void 1467 smb_server_kstat_init(smb_server_t *sv) 1468 { 1469 1470 sv->sv_ksp = kstat_create_zone(SMBSRV_KSTAT_MODULE, 0, 1471 SMBSRV_KSTAT_STATISTICS, SMBSRV_KSTAT_CLASS, KSTAT_TYPE_RAW, 1472 sizeof (smbsrv_kstats_t), 0, sv->sv_zid); 1473 1474 if (sv->sv_ksp != NULL) { 1475 sv->sv_ksp->ks_update = smb_server_kstat_update; 1476 sv->sv_ksp->ks_private = sv; 1477 ((smbsrv_kstats_t *)sv->sv_ksp->ks_data)->ks_start_time = 1478 sv->sv_start_time; 1479 smb_dispatch_stats_init(sv); 1480 smb2_dispatch_stats_init(sv); 1481 kstat_install(sv->sv_ksp); 1482 } else { 1483 cmn_err(CE_WARN, "SMB Server: Statistics unavailable"); 1484 } 1485 1486 sv->sv_legacy_ksp = kstat_create_zone(SMBSRV_KSTAT_MODULE, 0, 1487 SMBSRV_KSTAT_NAME, SMBSRV_KSTAT_CLASS, KSTAT_TYPE_NAMED, 1488 sizeof (smb_server_legacy_kstat_t) / sizeof (kstat_named_t), 1489 0, sv->sv_zid); 1490 1491 if (sv->sv_legacy_ksp != NULL) { 1492 smb_server_legacy_kstat_t *ksd; 1493 1494 ksd = sv->sv_legacy_ksp->ks_data; 1495 1496 (void) strlcpy(ksd->ls_files.name, "open_files", 1497 sizeof (ksd->ls_files.name)); 1498 ksd->ls_files.data_type = KSTAT_DATA_UINT32; 1499 1500 (void) strlcpy(ksd->ls_trees.name, "connections", 1501 sizeof (ksd->ls_trees.name)); 1502 ksd->ls_trees.data_type = KSTAT_DATA_UINT32; 1503 1504 (void) strlcpy(ksd->ls_users.name, "connections", 1505 sizeof (ksd->ls_users.name)); 1506 ksd->ls_users.data_type = KSTAT_DATA_UINT32; 1507 1508 mutex_init(&sv->sv_legacy_ksmtx, NULL, MUTEX_DEFAULT, NULL); 1509 sv->sv_legacy_ksp->ks_lock = &sv->sv_legacy_ksmtx; 1510 sv->sv_legacy_ksp->ks_update = smb_server_legacy_kstat_update; 1511 kstat_install(sv->sv_legacy_ksp); 1512 } 1513 } 1514 1515 /* 1516 * smb_server_kstat_fini 1517 */ 1518 static void 1519 smb_server_kstat_fini(smb_server_t *sv) 1520 { 1521 if (sv->sv_legacy_ksp != NULL) { 1522 kstat_delete(sv->sv_legacy_ksp); 1523 mutex_destroy(&sv->sv_legacy_ksmtx); 1524 sv->sv_legacy_ksp = NULL; 1525 } 1526 1527 if (sv->sv_ksp != NULL) { 1528 kstat_delete(sv->sv_ksp); 1529 sv->sv_ksp = NULL; 1530 smb_dispatch_stats_fini(sv); 1531 smb2_dispatch_stats_fini(sv); 1532 } 1533 } 1534 1535 /* 1536 * Verify the defines in smb_kstat.h used by ks_reqs1 ks_reqs2 1537 */ 1538 CTASSERT(SMBSRV_KS_NREQS1 == SMB_COM_NUM); 1539 CTASSERT(SMBSRV_KS_NREQS2 == SMB2__NCMDS); 1540 1541 /* 1542 * smb_server_kstat_update 1543 */ 1544 static int 1545 smb_server_kstat_update(kstat_t *ksp, int rw) 1546 { 1547 smb_server_t *sv; 1548 smbsrv_kstats_t *ksd; 1549 1550 if (rw == KSTAT_READ) { 1551 sv = ksp->ks_private; 1552 SMB_SERVER_VALID(sv); 1553 ksd = (smbsrv_kstats_t *)ksp->ks_data; 1554 /* 1555 * Counters 1556 */ 1557 ksd->ks_nbt_sess = sv->sv_nbt_sess; 1558 ksd->ks_tcp_sess = sv->sv_tcp_sess; 1559 ksd->ks_users = sv->sv_users; 1560 ksd->ks_trees = sv->sv_trees; 1561 ksd->ks_files = sv->sv_files; 1562 ksd->ks_pipes = sv->sv_pipes; 1563 /* 1564 * Throughput 1565 */ 1566 ksd->ks_txb = sv->sv_txb; 1567 ksd->ks_rxb = sv->sv_rxb; 1568 ksd->ks_nreq = sv->sv_nreq; 1569 /* 1570 * Busyness 1571 */ 1572 ksd->ks_maxreqs = sv->sv_cfg.skc_maxworkers; 1573 smb_srqueue_update(&sv->sv_srqueue, 1574 &ksd->ks_utilization); 1575 /* 1576 * Latency & Throughput of the requests 1577 */ 1578 smb_dispatch_stats_update(sv, ksd->ks_reqs1, 0, SMB_COM_NUM); 1579 smb2_dispatch_stats_update(sv, ksd->ks_reqs2, 0, SMB2__NCMDS); 1580 return (0); 1581 } 1582 if (rw == KSTAT_WRITE) 1583 return (EACCES); 1584 1585 return (EIO); 1586 } 1587 1588 static int 1589 smb_server_legacy_kstat_update(kstat_t *ksp, int rw) 1590 { 1591 smb_server_t *sv; 1592 smb_server_legacy_kstat_t *ksd; 1593 int rc; 1594 1595 switch (rw) { 1596 case KSTAT_WRITE: 1597 rc = EACCES; 1598 break; 1599 case KSTAT_READ: 1600 if (!smb_server_lookup(&sv)) { 1601 ASSERT(MUTEX_HELD(ksp->ks_lock)); 1602 ASSERT(sv->sv_legacy_ksp == ksp); 1603 ksd = (smb_server_legacy_kstat_t *)ksp->ks_data; 1604 ksd->ls_files.value.ui32 = sv->sv_files + sv->sv_pipes; 1605 ksd->ls_trees.value.ui32 = sv->sv_trees; 1606 ksd->ls_users.value.ui32 = sv->sv_users; 1607 smb_server_release(sv); 1608 rc = 0; 1609 break; 1610 } 1611 /* FALLTHROUGH */ 1612 default: 1613 rc = EIO; 1614 break; 1615 } 1616 return (rc); 1617 1618 } 1619 1620 int smb_server_shutdown_wait1 = 15; /* seconds */ 1621 1622 /* 1623 * smb_server_shutdown 1624 */ 1625 static void 1626 smb_server_shutdown(smb_server_t *sv) 1627 { 1628 smb_llist_t *sl = &sv->sv_session_list; 1629 smb_session_t *session; 1630 clock_t time0, time1, time2; 1631 1632 SMB_SERVER_VALID(sv); 1633 1634 /* 1635 * Stop the listeners first, so we can't get any more 1636 * new sessions while we're trying to shut down. 1637 */ 1638 smb_server_listener_stop(&sv->sv_nbt_daemon); 1639 smb_server_listener_stop(&sv->sv_tcp_daemon); 1640 1641 /* 1642 * Disconnect all of the sessions. This causes all the 1643 * smb_server_receiver threads to see a disconnect and 1644 * begin tear-down (in parallel) in smb_session_cancel. 1645 */ 1646 smb_llist_enter(sl, RW_READER); 1647 session = smb_llist_head(sl); 1648 while (session != NULL) { 1649 smb_session_disconnect(session); 1650 session = smb_llist_next(sl, session); 1651 } 1652 smb_llist_exit(sl); 1653 1654 /* 1655 * Wake up any threads we might have blocked. 1656 * Must precede kdoor_close etc. because those will 1657 * wait for such threads to get out. 1658 */ 1659 smb_event_cancel(sv, 0); 1660 smb_threshold_wake_all(&sv->sv_ssetup_ct); 1661 smb_threshold_wake_all(&sv->sv_tcon_ct); 1662 smb_threshold_wake_all(&sv->sv_opipe_ct); 1663 smb_threshold_wake_all(&sv->sv_logoff_ct); 1664 1665 /* 1666 * Wait for the session list to empty. 1667 * (cv_signal in smb_server_destroy_session) 1668 * 1669 * We must wait for all the SMB session readers to finish, or 1670 * we could proceed here while there might be worker threads 1671 * running in any of those sessions. See smb_session_logoff 1672 * for timeouts applied to session tear-down. If this takes 1673 * longer than expected, make some noise, and fire a dtrace 1674 * probe one might use to investigate. 1675 */ 1676 time0 = ddi_get_lbolt(); 1677 time1 = SEC_TO_TICK(smb_server_shutdown_wait1) + time0; 1678 mutex_enter(&sv->sv_mutex); 1679 while (sv->sv_session_list.ll_count != 0) { 1680 if (cv_timedwait(&sv->sv_cv, &sv->sv_mutex, time1) < 0) { 1681 cmn_err(CE_NOTE, "!shutdown waited %d seconds" 1682 " with %d sessions still remaining", 1683 smb_server_shutdown_wait1, 1684 sv->sv_session_list.ll_count); 1685 DTRACE_PROBE1(max__wait, smb_server_t *, sv); 1686 break; 1687 } 1688 } 1689 while (sv->sv_session_list.ll_count != 0) { 1690 cv_wait(&sv->sv_cv, &sv->sv_mutex); 1691 } 1692 mutex_exit(&sv->sv_mutex); 1693 1694 time2 = ddi_get_lbolt(); 1695 if (time2 > time1) { 1696 cmn_err(CE_NOTE, "!shutdown waited %d seconds" 1697 " for all sessions to finish", 1698 (int)TICK_TO_SEC(time2 - time0)); 1699 } 1700 1701 smb_kdoor_close(sv); 1702 #ifdef _KERNEL 1703 smb_kshare_door_fini(sv->sv_lmshrd); 1704 #endif /* _KERNEL */ 1705 sv->sv_lmshrd = NULL; 1706 1707 smb_export_stop(sv); 1708 smb_kshare_stop(sv); 1709 smb_thread_stop(&sv->si_thread_timers); 1710 1711 /* 1712 * Both kshare and the oplock break sub-systems may have 1713 * taskq jobs on the spcial "server" session, until we've 1714 * closed all ofiles and stopped the kshare exporter. 1715 * Now it's safe to destroy the server session, but first 1716 * wait for any requests on it to finish. Note that for 1717 * normal sessions, this happens in smb_session_cancel, 1718 * but that's not called for the server session. 1719 */ 1720 if (sv->sv_rootuser != NULL) { 1721 smb_user_logoff(sv->sv_rootuser); 1722 smb_user_release(sv->sv_rootuser); 1723 sv->sv_rootuser = NULL; 1724 } 1725 if (sv->sv_session != NULL) { 1726 smb_session_cancel_requests(sv->sv_session, NULL, NULL); 1727 smb_slist_wait_for_empty(&sv->sv_session->s_req_list); 1728 1729 /* Just in case import left users and trees */ 1730 smb_session_logoff(sv->sv_session); 1731 1732 smb_session_delete(sv->sv_session); 1733 sv->sv_session = NULL; 1734 } 1735 1736 if (sv->sv_receiver_pool != NULL) { 1737 taskq_destroy(sv->sv_receiver_pool); 1738 sv->sv_receiver_pool = NULL; 1739 } 1740 1741 if (sv->sv_worker_pool != NULL) { 1742 taskq_destroy(sv->sv_worker_pool); 1743 sv->sv_worker_pool = NULL; 1744 } 1745 1746 if (sv->sv_notify_pool != NULL) { 1747 taskq_destroy(sv->sv_notify_pool); 1748 sv->sv_notify_pool = NULL; 1749 } 1750 1751 /* 1752 * Clean out any durable handles. After this we should 1753 * have no ofiles remaining (and no more oplock breaks). 1754 */ 1755 smb2_dh_shutdown(sv); 1756 1757 smb_server_fsop_stop(sv); 1758 1759 #ifdef _KERNEL 1760 if (sv->sv_proc_p != NULL) { 1761 smb_server_delproc(sv); 1762 } 1763 #endif 1764 } 1765 1766 /* 1767 * smb_server_listener_init 1768 * 1769 * Initializes listener contexts. 1770 */ 1771 static void 1772 smb_server_listener_init( 1773 smb_server_t *sv, 1774 smb_listener_daemon_t *ld, 1775 char *name, 1776 in_port_t port, 1777 int family) 1778 { 1779 ASSERT(ld->ld_magic != SMB_LISTENER_MAGIC); 1780 1781 bzero(ld, sizeof (*ld)); 1782 1783 ld->ld_sv = sv; 1784 ld->ld_family = family; 1785 ld->ld_port = port; 1786 1787 if (family == AF_INET) { 1788 ld->ld_sin.sin_family = (uint32_t)family; 1789 ld->ld_sin.sin_port = htons(port); 1790 ld->ld_sin.sin_addr.s_addr = htonl(INADDR_ANY); 1791 } else { 1792 ld->ld_sin6.sin6_family = (uint32_t)family; 1793 ld->ld_sin6.sin6_port = htons(port); 1794 (void) memset(&ld->ld_sin6.sin6_addr.s6_addr, 0, 1795 sizeof (ld->ld_sin6.sin6_addr.s6_addr)); 1796 } 1797 1798 smb_thread_init(&ld->ld_thread, name, smb_server_listener, ld, 1799 smbsrv_listen_pri, sv); 1800 ld->ld_magic = SMB_LISTENER_MAGIC; 1801 } 1802 1803 /* 1804 * smb_server_listener_destroy 1805 * 1806 * Destroyes listener contexts. 1807 */ 1808 static void 1809 smb_server_listener_destroy(smb_listener_daemon_t *ld) 1810 { 1811 /* 1812 * Note that if startup fails early, we can legitimately 1813 * get here with an all-zeros object. 1814 */ 1815 if (ld->ld_magic == 0) 1816 return; 1817 1818 SMB_LISTENER_VALID(ld); 1819 ASSERT(ld->ld_so == NULL); 1820 smb_thread_destroy(&ld->ld_thread); 1821 ld->ld_magic = 0; 1822 } 1823 1824 /* 1825 * smb_server_listener_start 1826 * 1827 * Starts the listener associated with the context passed in. 1828 * 1829 * Return: 0 Success 1830 * not 0 Failure 1831 */ 1832 static int 1833 smb_server_listener_start(smb_listener_daemon_t *ld) 1834 { 1835 int rc; 1836 uint32_t on; 1837 uint32_t off; 1838 1839 SMB_LISTENER_VALID(ld); 1840 1841 if (ld->ld_so != NULL) 1842 return (EINVAL); 1843 1844 ld->ld_so = smb_socreate(ld->ld_family, SOCK_STREAM, 0); 1845 if (ld->ld_so == NULL) { 1846 cmn_err(CE_WARN, "port %d: socket create failed", ld->ld_port); 1847 return (ENOMEM); 1848 } 1849 1850 off = 0; 1851 (void) ksocket_setsockopt(ld->ld_so, SOL_SOCKET, 1852 SO_MAC_EXEMPT, &off, sizeof (off), CRED()); 1853 1854 on = 1; 1855 (void) ksocket_setsockopt(ld->ld_so, SOL_SOCKET, 1856 SO_REUSEADDR, &on, sizeof (on), CRED()); 1857 1858 if (ld->ld_family == AF_INET) { 1859 rc = ksocket_bind(ld->ld_so, 1860 (struct sockaddr *)&ld->ld_sin, 1861 sizeof (ld->ld_sin), CRED()); 1862 } else { 1863 rc = ksocket_bind(ld->ld_so, 1864 (struct sockaddr *)&ld->ld_sin6, 1865 sizeof (ld->ld_sin6), CRED()); 1866 } 1867 1868 if (rc != 0) { 1869 cmn_err(CE_WARN, "port %d: bind failed", ld->ld_port); 1870 return (rc); 1871 } 1872 1873 rc = ksocket_listen(ld->ld_so, 20, CRED()); 1874 if (rc < 0) { 1875 cmn_err(CE_WARN, "port %d: listen failed", ld->ld_port); 1876 return (rc); 1877 } 1878 1879 ksocket_hold(ld->ld_so); 1880 rc = smb_thread_start(&ld->ld_thread); 1881 if (rc != 0) { 1882 ksocket_rele(ld->ld_so); 1883 cmn_err(CE_WARN, "port %d: listener failed to start", 1884 ld->ld_port); 1885 return (rc); 1886 } 1887 return (0); 1888 } 1889 1890 /* 1891 * smb_server_listener_stop 1892 * 1893 * Stops the listener associated with the context passed in. 1894 */ 1895 static void 1896 smb_server_listener_stop(smb_listener_daemon_t *ld) 1897 { 1898 SMB_LISTENER_VALID(ld); 1899 1900 if (ld->ld_so != NULL) { 1901 smb_soshutdown(ld->ld_so); 1902 smb_sodestroy(ld->ld_so); 1903 smb_thread_stop(&ld->ld_thread); 1904 ld->ld_so = NULL; 1905 } 1906 } 1907 1908 /* 1909 * smb_server_listener 1910 * 1911 * Entry point of the listeners. 1912 */ 1913 static void 1914 smb_server_listener(smb_thread_t *thread, void *arg) 1915 { 1916 _NOTE(ARGUNUSED(thread)) 1917 smb_listener_daemon_t *ld; 1918 ksocket_t s_so; 1919 int on; 1920 int txbuf_size; 1921 1922 ld = (smb_listener_daemon_t *)arg; 1923 1924 SMB_LISTENER_VALID(ld); 1925 1926 DTRACE_PROBE1(so__wait__accept, struct sonode *, ld->ld_so); 1927 1928 while (smb_thread_continue_nowait(&ld->ld_thread) && 1929 ld->ld_sv->sv_state != SMB_SERVER_STATE_STOPPING) { 1930 int ret = ksocket_accept(ld->ld_so, NULL, NULL, &s_so, CRED()); 1931 1932 switch (ret) { 1933 case 0: 1934 break; 1935 case ECONNABORTED: 1936 continue; 1937 1938 case EINTR: 1939 case EBADF: 1940 case ENOTSOCK: 1941 /* These are normal during shutdown. Silence. */ 1942 if (ld->ld_sv->sv_state == SMB_SERVER_STATE_STOPPING) 1943 goto out; 1944 /* FALLTHROUGH */ 1945 default: 1946 cmn_err(CE_WARN, 1947 "smb_server_listener: ksocket_accept failed (%d)", 1948 ret); 1949 /* avoid a tight CPU-burn loop here */ 1950 delay(MSEC_TO_TICK(10)); 1951 continue; 1952 } 1953 1954 DTRACE_PROBE1(so__accept, struct sonode *, s_so); 1955 1956 on = 1; 1957 (void) ksocket_setsockopt(s_so, IPPROTO_TCP, TCP_NODELAY, 1958 &on, sizeof (on), CRED()); 1959 1960 on = 1; 1961 (void) ksocket_setsockopt(s_so, SOL_SOCKET, SO_KEEPALIVE, 1962 &on, sizeof (on), CRED()); 1963 1964 txbuf_size = 128*1024; 1965 (void) ksocket_setsockopt(s_so, SOL_SOCKET, SO_SNDBUF, 1966 (const void *)&txbuf_size, sizeof (txbuf_size), CRED()); 1967 1968 /* 1969 * Create a session for this connection. 1970 */ 1971 smb_server_create_session(ld, s_so); 1972 } 1973 out: 1974 ksocket_rele(ld->ld_so); 1975 } 1976 1977 /* 1978 * smb_server_receiver 1979 * 1980 * Entry point of the receiver threads. 1981 * Also does cleanup when socket disconnected. 1982 */ 1983 static void 1984 smb_server_receiver(void *arg) 1985 { 1986 smb_session_t *session; 1987 1988 session = (smb_session_t *)arg; 1989 1990 /* We stay in here until socket disconnect. */ 1991 smb_session_receiver(session); 1992 1993 smb_server_destroy_session(session); 1994 } 1995 1996 /* 1997 * smb_server_lookup 1998 * 1999 * This function finds the server associated with the zone of the 2000 * caller. Note: requires a fix in the dynamic taskq code: 2001 * 1501 taskq_create_proc ... TQ_DYNAMIC puts tasks in p0 2002 */ 2003 int 2004 smb_server_lookup(smb_server_t **psv) 2005 { 2006 zoneid_t zid; 2007 smb_server_t *sv; 2008 2009 zid = getzoneid(); 2010 2011 smb_llist_enter(&smb_servers, RW_READER); 2012 sv = smb_llist_head(&smb_servers); 2013 while (sv) { 2014 SMB_SERVER_VALID(sv); 2015 if (sv->sv_zid == zid) { 2016 mutex_enter(&sv->sv_mutex); 2017 if (sv->sv_state != SMB_SERVER_STATE_DELETING) { 2018 sv->sv_refcnt++; 2019 mutex_exit(&sv->sv_mutex); 2020 smb_llist_exit(&smb_servers); 2021 *psv = sv; 2022 return (0); 2023 } 2024 mutex_exit(&sv->sv_mutex); 2025 break; 2026 } 2027 sv = smb_llist_next(&smb_servers, sv); 2028 } 2029 smb_llist_exit(&smb_servers); 2030 return (EPERM); 2031 } 2032 2033 /* 2034 * smb_server_release 2035 * 2036 * This function decrements the reference count of the server and signals its 2037 * condition variable if the state of the server is SMB_SERVER_STATE_DELETING. 2038 */ 2039 void 2040 smb_server_release(smb_server_t *sv) 2041 { 2042 SMB_SERVER_VALID(sv); 2043 2044 mutex_enter(&sv->sv_mutex); 2045 ASSERT(sv->sv_refcnt); 2046 sv->sv_refcnt--; 2047 if ((sv->sv_refcnt == 0) && (sv->sv_state == SMB_SERVER_STATE_DELETING)) 2048 cv_signal(&sv->sv_cv); 2049 mutex_exit(&sv->sv_mutex); 2050 } 2051 2052 /* 2053 * smb_server_lookup_user 2054 * 2055 * Find an smb_user by its user_id 2056 * Optional ssn_id (if non-zero) restricts search to a specific session. 2057 * 2058 * Returns smb_user_t * held. Caller must smb_user_rele(user) 2059 * Returns NULL if not found. 2060 */ 2061 smb_user_t * 2062 smb_server_lookup_user(smb_server_t *sv, uint64_t ssn_id, uint64_t user_id) 2063 { 2064 smb_llist_t *slist = &sv->sv_session_list; 2065 smb_session_t *sn; 2066 smb_user_t *user = NULL; 2067 2068 smb_llist_enter(slist, RW_READER); 2069 2070 for (sn = smb_llist_head(slist); 2071 sn != NULL && user == NULL; 2072 sn = smb_llist_next(slist, sn)) { 2073 SMB_SESSION_VALID(sn); 2074 2075 if (ssn_id != 0 && ssn_id != sn->s_kid) 2076 continue; 2077 if (sn->s_state != SMB_SESSION_STATE_NEGOTIATED) 2078 continue; 2079 2080 user = smb_session_lookup_ssnid(sn, user_id); 2081 } 2082 smb_llist_exit(slist); 2083 2084 return (user); 2085 } 2086 2087 /* 2088 * Enumerate the users associated with a session list. 2089 */ 2090 static void 2091 smb_server_enum_users(smb_server_t *sv, smb_svcenum_t *svcenum) 2092 { 2093 smb_llist_t *ll = &sv->sv_session_list; 2094 smb_session_t *sn; 2095 smb_llist_t *ulist; 2096 smb_user_t *user; 2097 int rc = 0; 2098 2099 smb_llist_enter(ll, RW_READER); 2100 sn = smb_llist_head(ll); 2101 2102 while (sn != NULL) { 2103 SMB_SESSION_VALID(sn); 2104 ulist = &sn->s_user_list; 2105 smb_llist_enter(ulist, RW_READER); 2106 user = smb_llist_head(ulist); 2107 2108 while (user != NULL) { 2109 if (smb_user_hold(user)) { 2110 rc = smb_user_enum(user, svcenum); 2111 smb_user_release(user); 2112 if (rc != 0) 2113 break; 2114 } 2115 2116 user = smb_llist_next(ulist, user); 2117 } 2118 2119 smb_llist_exit(ulist); 2120 2121 if (rc != 0) 2122 break; 2123 2124 sn = smb_llist_next(ll, sn); 2125 } 2126 2127 smb_llist_exit(ll); 2128 } 2129 2130 /* 2131 * Enumerate the trees/files associated with a session list. 2132 */ 2133 static void 2134 smb_server_enum_trees(smb_server_t *sv, smb_svcenum_t *svcenum) 2135 { 2136 smb_llist_t *ll = &sv->sv_session_list; 2137 smb_session_t *sn; 2138 smb_llist_t *tlist; 2139 smb_tree_t *tree; 2140 int rc = 0; 2141 2142 smb_llist_enter(ll, RW_READER); 2143 sn = smb_llist_head(ll); 2144 2145 while (sn != NULL) { 2146 SMB_SESSION_VALID(sn); 2147 tlist = &sn->s_tree_list; 2148 smb_llist_enter(tlist, RW_READER); 2149 tree = smb_llist_head(tlist); 2150 2151 while (tree != NULL) { 2152 if (smb_tree_hold(tree)) { 2153 rc = smb_tree_enum(tree, svcenum); 2154 smb_tree_release(tree); 2155 if (rc != 0) 2156 break; 2157 } 2158 2159 tree = smb_llist_next(tlist, tree); 2160 } 2161 2162 smb_llist_exit(tlist); 2163 2164 if (rc != 0) 2165 break; 2166 2167 sn = smb_llist_next(ll, sn); 2168 } 2169 2170 smb_llist_exit(ll); 2171 } 2172 2173 /* 2174 * Disconnect sessions associated with the specified client and username. 2175 * Empty strings are treated as wildcards. 2176 */ 2177 static int 2178 smb_server_session_disconnect(smb_server_t *sv, 2179 const char *client, const char *name) 2180 { 2181 smb_llist_t *ll = &sv->sv_session_list; 2182 smb_session_t *sn; 2183 smb_llist_t *ulist; 2184 smb_user_t *user; 2185 int count = 0; 2186 2187 smb_llist_enter(ll, RW_READER); 2188 2189 for (sn = smb_llist_head(ll); 2190 sn != NULL; 2191 sn = smb_llist_next(ll, sn)) { 2192 SMB_SESSION_VALID(sn); 2193 2194 if (*client != '\0' && !smb_session_isclient(sn, client)) 2195 continue; 2196 2197 ulist = &sn->s_user_list; 2198 smb_llist_enter(ulist, RW_READER); 2199 2200 for (user = smb_llist_head(ulist); 2201 user != NULL; 2202 user = smb_llist_next(ulist, user)) { 2203 2204 if (smb_user_hold(user)) { 2205 2206 if (*name == '\0' || 2207 smb_user_namecmp(user, name)) { 2208 smb_user_logoff(user); 2209 count++; 2210 } 2211 2212 smb_user_release(user); 2213 } 2214 } 2215 2216 smb_llist_exit(ulist); 2217 } 2218 2219 smb_llist_exit(ll); 2220 return (count); 2221 } 2222 2223 /* 2224 * Close a file by its unique id. 2225 */ 2226 static int 2227 smb_server_fclose(smb_server_t *sv, uint32_t uniqid) 2228 { 2229 smb_llist_t *ll; 2230 smb_session_t *sn; 2231 smb_llist_t *tlist; 2232 smb_tree_t *tree; 2233 int rc = ENOENT; 2234 2235 ll = &sv->sv_session_list; 2236 smb_llist_enter(ll, RW_READER); 2237 sn = smb_llist_head(ll); 2238 2239 while ((sn != NULL) && (rc == ENOENT)) { 2240 SMB_SESSION_VALID(sn); 2241 tlist = &sn->s_tree_list; 2242 smb_llist_enter(tlist, RW_READER); 2243 tree = smb_llist_head(tlist); 2244 2245 while ((tree != NULL) && (rc == ENOENT)) { 2246 if (smb_tree_hold(tree)) { 2247 rc = smb_tree_fclose(tree, uniqid); 2248 smb_tree_release(tree); 2249 } 2250 2251 tree = smb_llist_next(tlist, tree); 2252 } 2253 2254 smb_llist_exit(tlist); 2255 sn = smb_llist_next(ll, sn); 2256 } 2257 2258 smb_llist_exit(ll); 2259 return (rc); 2260 } 2261 2262 /* 2263 * This is used by SMB2 session setup to logoff a previous session, 2264 * so it can force a logoff that we haven't noticed yet. 2265 * This is not called frequently, so we just walk the list of 2266 * connections searching for the user. 2267 * 2268 * Note that this must wait for any durable handles (ofiles) 2269 * owned by this user to become "orphaned", so that a reconnect 2270 * that may immediately follow can find and use such ofiles. 2271 */ 2272 void 2273 smb_server_logoff_ssnid(smb_request_t *sr, uint64_t ssnid) 2274 { 2275 smb_server_t *sv = sr->sr_server; 2276 smb_llist_t *sess_list; 2277 smb_session_t *sess; 2278 smb_user_t *user = NULL; 2279 boolean_t do_logoff = B_FALSE; 2280 2281 SMB_SERVER_VALID(sv); 2282 2283 if (sv->sv_state != SMB_SERVER_STATE_RUNNING) 2284 return; 2285 2286 sess_list = &sv->sv_session_list; 2287 smb_llist_enter(sess_list, RW_READER); 2288 2289 for (sess = smb_llist_head(sess_list); 2290 sess != NULL; 2291 sess = smb_llist_next(sess_list, sess)) { 2292 2293 SMB_SESSION_VALID(sess); 2294 2295 if (sess->dialect < SMB_VERS_2_BASE) 2296 continue; 2297 2298 switch (sess->s_state) { 2299 case SMB_SESSION_STATE_NEGOTIATED: 2300 case SMB_SESSION_STATE_TERMINATED: 2301 case SMB_SESSION_STATE_DISCONNECTED: 2302 break; 2303 default: 2304 continue; 2305 } 2306 2307 /* 2308 * Normal situation is to find a LOGGED_ON user. 2309 */ 2310 user = smb_session_lookup_uid_st(sess, ssnid, 0, 2311 SMB_USER_STATE_LOGGED_ON); 2312 if (user != NULL) { 2313 if (smb_is_same_user(user->u_cred, sr->user_cr)) { 2314 do_logoff = B_TRUE; 2315 break; 2316 } 2317 smb_user_release(user); 2318 user = NULL; 2319 } 2320 2321 /* 2322 * If we raced with disconnect, may find LOGGING_OFF, 2323 * in which case we want to just wait for it. 2324 */ 2325 user = smb_session_lookup_uid_st(sess, ssnid, 0, 2326 SMB_USER_STATE_LOGGING_OFF); 2327 if (user != NULL) { 2328 if (smb_is_same_user(user->u_cred, sr->user_cr)) 2329 break; 2330 smb_user_release(user); 2331 user = NULL; 2332 } 2333 } 2334 2335 smb_llist_exit(sess_list); 2336 2337 /* 2338 * Note that smb_user_logoff() can block for a while if 2339 * smb_session_disconnect_owned_trees, smb_ofile_close_all 2340 * ends up blocked on locks held by running requests. 2341 * Do that while not holding the session list rwlock. 2342 */ 2343 if (user != NULL) { 2344 if (do_logoff) { 2345 /* Treat this as if we lost the connection */ 2346 user->preserve_opens = SMB2_DH_PRESERVE_SOME; 2347 smb_user_logoff(user); 2348 } 2349 2350 /* 2351 * Wait for durable handles to be orphaned. 2352 * Note: not holding the sess list rwlock. 2353 */ 2354 smb_user_wait_trees(user); 2355 2356 /* 2357 * Could be doing the last release on a user below, 2358 * which can leave work on the delete queues for 2359 * s_user_list or s_tree_list so flush those. 2360 * Must hold the session list after the user release 2361 * so that the session can't go away while we flush. 2362 */ 2363 smb_llist_enter(sess_list, RW_READER); 2364 2365 sess = user->u_session; 2366 smb_user_release(user); 2367 2368 smb_llist_flush(&sess->s_tree_list); 2369 smb_llist_flush(&sess->s_user_list); 2370 2371 smb_llist_exit(sess_list); 2372 } 2373 } 2374 2375 /* See also: libsmb smb_kmod_setcfg */ 2376 static void 2377 smb_server_store_cfg(smb_server_t *sv, smb_ioc_cfg_t *ioc) 2378 { 2379 if (ioc->maxconnections == 0) 2380 ioc->maxconnections = 0xFFFFFFFF; 2381 2382 if (ioc->encrypt == SMB_CONFIG_REQUIRED && 2383 ioc->max_protocol < SMB_VERS_3_0) { 2384 cmn_err(CE_WARN, "Server set to require encryption; " 2385 "forcing max_protocol to 3.0"); 2386 ioc->max_protocol = SMB_VERS_3_0; 2387 } 2388 sv->sv_cfg.skc_maxworkers = ioc->maxworkers; 2389 sv->sv_cfg.skc_maxconnections = ioc->maxconnections; 2390 sv->sv_cfg.skc_keepalive = ioc->keepalive; 2391 sv->sv_cfg.skc_restrict_anon = ioc->restrict_anon; 2392 sv->sv_cfg.skc_signing_enable = ioc->signing_enable; 2393 sv->sv_cfg.skc_signing_required = ioc->signing_required; 2394 sv->sv_cfg.skc_oplock_enable = ioc->oplock_enable; 2395 sv->sv_cfg.skc_sync_enable = ioc->sync_enable; 2396 sv->sv_cfg.skc_secmode = ioc->secmode; 2397 sv->sv_cfg.skc_netbios_enable = ioc->netbios_enable; 2398 sv->sv_cfg.skc_ipv6_enable = ioc->ipv6_enable; 2399 sv->sv_cfg.skc_print_enable = ioc->print_enable; 2400 sv->sv_cfg.skc_traverse_mounts = ioc->traverse_mounts; 2401 sv->sv_cfg.skc_short_names = ioc->short_names; 2402 sv->sv_cfg.skc_max_protocol = ioc->max_protocol; 2403 sv->sv_cfg.skc_min_protocol = ioc->min_protocol; 2404 sv->sv_cfg.skc_encrypt = ioc->encrypt; 2405 sv->sv_cfg.skc_encrypt_ciphers = ioc->encrypt_ciphers; 2406 sv->sv_cfg.skc_execflags = ioc->exec_flags; 2407 sv->sv_cfg.skc_negtok_len = ioc->negtok_len; 2408 sv->sv_cfg.skc_max_opens = ioc->max_opens; 2409 sv->sv_cfg.skc_version = ioc->version; 2410 sv->sv_cfg.skc_initial_credits = ioc->initial_credits; 2411 sv->sv_cfg.skc_maximum_credits = ioc->maximum_credits; 2412 2413 (void) memcpy(sv->sv_cfg.skc_machine_uuid, ioc->machine_uuid, 2414 sizeof (uuid_t)); 2415 (void) memcpy(sv->sv_cfg.skc_negtok, ioc->negtok, 2416 sizeof (sv->sv_cfg.skc_negtok)); 2417 (void) memcpy(sv->sv_cfg.skc_native_os, ioc->native_os, 2418 sizeof (sv->sv_cfg.skc_native_os)); 2419 (void) memcpy(sv->sv_cfg.skc_native_lm, ioc->native_lm, 2420 sizeof (sv->sv_cfg.skc_native_lm)); 2421 2422 (void) strlcpy(sv->sv_cfg.skc_nbdomain, ioc->nbdomain, 2423 sizeof (sv->sv_cfg.skc_nbdomain)); 2424 (void) strlcpy(sv->sv_cfg.skc_fqdn, ioc->fqdn, 2425 sizeof (sv->sv_cfg.skc_fqdn)); 2426 (void) strlcpy(sv->sv_cfg.skc_hostname, ioc->hostname, 2427 sizeof (sv->sv_cfg.skc_hostname)); 2428 (void) strlcpy(sv->sv_cfg.skc_system_comment, ioc->system_comment, 2429 sizeof (sv->sv_cfg.skc_system_comment)); 2430 } 2431 2432 static int 2433 smb_server_fsop_start(smb_server_t *sv) 2434 { 2435 int error; 2436 2437 error = smb_node_root_init(sv, &sv->si_root_smb_node); 2438 if (error != 0) 2439 sv->si_root_smb_node = NULL; 2440 2441 return (error); 2442 } 2443 2444 static void 2445 smb_server_fsop_stop(smb_server_t *sv) 2446 { 2447 if (sv->si_root_smb_node != NULL) { 2448 smb_node_release(sv->si_root_smb_node); 2449 sv->si_root_smb_node = NULL; 2450 } 2451 } 2452 2453 smb_event_t * 2454 smb_event_create(smb_server_t *sv, int timeout) 2455 { 2456 smb_event_t *event; 2457 2458 if (smb_server_is_stopping(sv)) 2459 return (NULL); 2460 2461 event = kmem_cache_alloc(smb_cache_event, KM_SLEEP); 2462 2463 bzero(event, sizeof (smb_event_t)); 2464 mutex_init(&event->se_mutex, NULL, MUTEX_DEFAULT, NULL); 2465 cv_init(&event->se_cv, NULL, CV_DEFAULT, NULL); 2466 event->se_magic = SMB_EVENT_MAGIC; 2467 event->se_txid = smb_event_alloc_txid(); 2468 event->se_server = sv; 2469 event->se_timeout = timeout; 2470 2471 smb_llist_enter(&sv->sv_event_list, RW_WRITER); 2472 smb_llist_insert_tail(&sv->sv_event_list, event); 2473 smb_llist_exit(&sv->sv_event_list); 2474 2475 return (event); 2476 } 2477 2478 void 2479 smb_event_destroy(smb_event_t *event) 2480 { 2481 smb_server_t *sv; 2482 2483 if (event == NULL) 2484 return; 2485 2486 SMB_EVENT_VALID(event); 2487 ASSERT(event->se_waittime == 0); 2488 sv = event->se_server; 2489 SMB_SERVER_VALID(sv); 2490 2491 smb_llist_enter(&sv->sv_event_list, RW_WRITER); 2492 smb_llist_remove(&sv->sv_event_list, event); 2493 smb_llist_exit(&sv->sv_event_list); 2494 2495 event->se_magic = (uint32_t)~SMB_EVENT_MAGIC; 2496 cv_destroy(&event->se_cv); 2497 mutex_destroy(&event->se_mutex); 2498 2499 kmem_cache_free(smb_cache_event, event); 2500 } 2501 2502 /* 2503 * Get the txid for the specified event. 2504 */ 2505 uint32_t 2506 smb_event_txid(smb_event_t *event) 2507 { 2508 if (event != NULL) { 2509 SMB_EVENT_VALID(event); 2510 return (event->se_txid); 2511 } 2512 2513 cmn_err(CE_NOTE, "smb_event_txid failed"); 2514 return ((uint32_t)-1); 2515 } 2516 2517 /* 2518 * Wait for event notification. 2519 */ 2520 int 2521 smb_event_wait(smb_event_t *event) 2522 { 2523 int seconds = 1; 2524 int ticks; 2525 int err; 2526 2527 if (event == NULL) 2528 return (EINVAL); 2529 2530 SMB_EVENT_VALID(event); 2531 2532 mutex_enter(&event->se_mutex); 2533 event->se_waittime = 1; 2534 event->se_errno = 0; 2535 2536 while (!(event->se_notified)) { 2537 if (smb_event_debug && ((event->se_waittime % 30) == 0)) 2538 cmn_err(CE_NOTE, "smb_event_wait[%d] (%d sec)", 2539 event->se_txid, event->se_waittime); 2540 2541 if (event->se_errno != 0) 2542 break; 2543 2544 if (event->se_waittime > event->se_timeout) { 2545 event->se_errno = ETIME; 2546 break; 2547 } 2548 2549 ticks = SEC_TO_TICK(seconds); 2550 (void) cv_reltimedwait(&event->se_cv, 2551 &event->se_mutex, (clock_t)ticks, TR_CLOCK_TICK); 2552 ++event->se_waittime; 2553 } 2554 2555 err = event->se_errno; 2556 event->se_waittime = 0; 2557 event->se_notified = B_FALSE; 2558 cv_signal(&event->se_cv); 2559 mutex_exit(&event->se_mutex); 2560 return (err); 2561 } 2562 2563 /* 2564 * If txid is non-zero, cancel the specified event. 2565 * Otherwise, cancel all events. 2566 */ 2567 static void 2568 smb_event_cancel(smb_server_t *sv, uint32_t txid) 2569 { 2570 smb_event_t *event; 2571 smb_llist_t *event_list; 2572 2573 SMB_SERVER_VALID(sv); 2574 2575 event_list = &sv->sv_event_list; 2576 smb_llist_enter(event_list, RW_WRITER); 2577 2578 event = smb_llist_head(event_list); 2579 while (event) { 2580 SMB_EVENT_VALID(event); 2581 2582 if (txid == 0 || event->se_txid == txid) { 2583 mutex_enter(&event->se_mutex); 2584 event->se_errno = ECANCELED; 2585 event->se_notified = B_TRUE; 2586 cv_signal(&event->se_cv); 2587 mutex_exit(&event->se_mutex); 2588 2589 if (txid != 0) 2590 break; 2591 } 2592 2593 event = smb_llist_next(event_list, event); 2594 } 2595 2596 smb_llist_exit(event_list); 2597 } 2598 2599 /* 2600 * If txid is non-zero, notify the specified event. 2601 * Otherwise, notify all events. 2602 */ 2603 void 2604 smb_event_notify(smb_server_t *sv, uint32_t txid) 2605 { 2606 smb_event_t *event; 2607 smb_llist_t *event_list; 2608 2609 SMB_SERVER_VALID(sv); 2610 2611 event_list = &sv->sv_event_list; 2612 smb_llist_enter(event_list, RW_READER); 2613 2614 event = smb_llist_head(event_list); 2615 while (event) { 2616 SMB_EVENT_VALID(event); 2617 2618 if (txid == 0 || event->se_txid == txid) { 2619 mutex_enter(&event->se_mutex); 2620 event->se_notified = B_TRUE; 2621 cv_signal(&event->se_cv); 2622 mutex_exit(&event->se_mutex); 2623 2624 if (txid != 0) 2625 break; 2626 } 2627 2628 event = smb_llist_next(event_list, event); 2629 } 2630 2631 smb_llist_exit(event_list); 2632 } 2633 2634 /* 2635 * Allocate a new transaction id (txid). 2636 * 2637 * 0 or -1 are not assigned because they are used to detect invalid 2638 * conditions or to indicate all open id's. 2639 */ 2640 static uint32_t 2641 smb_event_alloc_txid(void) 2642 { 2643 static kmutex_t txmutex; 2644 static uint32_t txid; 2645 uint32_t txid_ret; 2646 2647 mutex_enter(&txmutex); 2648 2649 if (txid == 0) 2650 txid = ddi_get_lbolt() << 11; 2651 2652 do { 2653 ++txid; 2654 } while (txid == 0 || txid == (uint32_t)-1); 2655 2656 txid_ret = txid; 2657 mutex_exit(&txmutex); 2658 2659 return (txid_ret); 2660 } 2661 2662 /* 2663 * Called by the ioctl to find the corresponding 2664 * spooldoc node. removes node on success 2665 * 2666 * Return values 2667 * rc 2668 * B_FALSE - not found 2669 * B_TRUE - found 2670 * 2671 */ 2672 2673 static boolean_t 2674 smb_spool_lookup_doc_byfid(smb_server_t *sv, uint16_t fid, 2675 smb_kspooldoc_t *spdoc) 2676 { 2677 smb_kspooldoc_t *sp; 2678 smb_llist_t *splist; 2679 2680 splist = &sv->sp_info.sp_list; 2681 smb_llist_enter(splist, RW_WRITER); 2682 sp = smb_llist_head(splist); 2683 while (sp != NULL) { 2684 /* 2685 * check for a matching fid 2686 */ 2687 if (sp->sd_fid == fid) { 2688 *spdoc = *sp; 2689 smb_llist_remove(splist, sp); 2690 smb_llist_exit(splist); 2691 kmem_free(sp, sizeof (smb_kspooldoc_t)); 2692 return (B_TRUE); 2693 } 2694 sp = smb_llist_next(splist, sp); 2695 } 2696 cmn_err(CE_WARN, "smb_spool_lookup_user_byfid: no fid:%d", fid); 2697 smb_llist_exit(splist); 2698 return (B_FALSE); 2699 } 2700 2701 /* 2702 * Adds the spool fid to a linked list to be used 2703 * as a search key in the spooldoc queue 2704 * 2705 * Return values 2706 * rc non-zero error 2707 * rc zero success 2708 * 2709 */ 2710 2711 void 2712 smb_spool_add_fid(smb_server_t *sv, uint16_t fid) 2713 { 2714 smb_llist_t *fidlist; 2715 smb_spoolfid_t *sf; 2716 2717 if (sv->sv_cfg.skc_print_enable == 0) 2718 return; 2719 2720 sf = kmem_zalloc(sizeof (smb_spoolfid_t), KM_SLEEP); 2721 fidlist = &sv->sp_info.sp_fidlist; 2722 smb_llist_enter(fidlist, RW_WRITER); 2723 sf->sf_fid = fid; 2724 smb_llist_insert_tail(fidlist, sf); 2725 smb_llist_exit(fidlist); 2726 cv_broadcast(&sv->sp_info.sp_cv); 2727 } 2728 2729 /* 2730 * Called by the ioctl to get and remove the head of the fid list 2731 * 2732 * Return values 2733 * int fd 2734 * greater than 0 success 2735 * 0 - error 2736 * 2737 */ 2738 2739 static uint16_t 2740 smb_spool_get_fid(smb_server_t *sv) 2741 { 2742 smb_spoolfid_t *spfid; 2743 smb_llist_t *splist; 2744 uint16_t fid; 2745 2746 splist = &sv->sp_info.sp_fidlist; 2747 smb_llist_enter(splist, RW_WRITER); 2748 spfid = smb_llist_head(splist); 2749 if (spfid != NULL) { 2750 fid = spfid->sf_fid; 2751 smb_llist_remove(&sv->sp_info.sp_fidlist, spfid); 2752 kmem_free(spfid, sizeof (smb_spoolfid_t)); 2753 } else { 2754 fid = 0; 2755 } 2756 smb_llist_exit(splist); 2757 return (fid); 2758 } 2759 2760 /* 2761 * Adds the spooldoc to the tail of the spooldoc list 2762 * 2763 * Return values 2764 * rc non-zero error 2765 * rc zero success 2766 */ 2767 int 2768 smb_spool_add_doc(smb_tree_t *tree, smb_kspooldoc_t *sp) 2769 { 2770 smb_llist_t *splist; 2771 smb_server_t *sv = tree->t_server; 2772 int rc = 0; 2773 2774 splist = &sv->sp_info.sp_list; 2775 smb_llist_enter(splist, RW_WRITER); 2776 sp->sd_spool_num = atomic_inc_32_nv(&sv->sp_info.sp_cnt); 2777 smb_llist_insert_tail(splist, sp); 2778 smb_llist_exit(splist); 2779 2780 return (rc); 2781 } 2782 2783 /* 2784 * smb_server_create_session 2785 */ 2786 static void 2787 smb_server_create_session(smb_listener_daemon_t *ld, ksocket_t s_so) 2788 { 2789 smb_server_t *sv = ld->ld_sv; 2790 smb_session_t *session; 2791 smb_llist_t *sl; 2792 taskqid_t tqid; 2793 clock_t now; 2794 2795 session = smb_session_create(s_so, ld->ld_port, sv, 2796 ld->ld_family); 2797 2798 if (session == NULL) { 2799 /* This should be rare (create sleeps) */ 2800 smb_soshutdown(s_so); 2801 smb_sodestroy(s_so); 2802 cmn_err(CE_WARN, "SMB Session: alloc failed"); 2803 return; 2804 } 2805 2806 sl = &sv->sv_session_list; 2807 smb_llist_enter(sl, RW_WRITER); 2808 if (smb_llist_get_count(sl) >= sv->sv_cfg.skc_maxconnections) { 2809 /* 2810 * New session not in sv_session_list, so we can just 2811 * delete it directly. 2812 */ 2813 smb_llist_exit(sl); 2814 DTRACE_PROBE1(maxconn, smb_session_t *, session); 2815 smb_soshutdown(session->sock); 2816 smb_session_delete(session); 2817 goto logmaxconn; 2818 } 2819 smb_llist_insert_tail(sl, session); 2820 smb_llist_exit(sl); 2821 2822 /* 2823 * These taskq entries must run independently of one another, 2824 * so TQ_NOQUEUE. TQ_SLEEP (==0) just for clarity. 2825 */ 2826 tqid = taskq_dispatch(sv->sv_receiver_pool, 2827 smb_server_receiver, session, TQ_NOQUEUE | TQ_SLEEP); 2828 if (tqid != TASKQID_INVALID) { 2829 /* Success */ 2830 return; 2831 } 2832 2833 /* 2834 * Have: tqid == TASKQID_INVALID 2835 * We never entered smb_server_receiver() 2836 * so need to do its return cleanup 2837 */ 2838 DTRACE_PROBE1(maxconn, smb_session_t *, session); 2839 smb_session_disconnect(session); 2840 smb_session_logoff(session); 2841 smb_server_destroy_session(session); 2842 2843 logmaxconn: 2844 /* 2845 * If we hit max_connections, log something so an admin 2846 * can find out why new connections are failing, but 2847 * log this no more than once a minute. 2848 */ 2849 now = ddi_get_lbolt(); 2850 if (now > ld->ld_quiet) { 2851 ld->ld_quiet = now + SEC_TO_TICK(60); 2852 cmn_err(CE_WARN, "SMB can't create session: " 2853 "Would exceed max_connections."); 2854 } 2855 } 2856 2857 static void 2858 smb_server_destroy_session(smb_session_t *session) 2859 { 2860 smb_server_t *sv; 2861 smb_llist_t *ll; 2862 uint32_t count; 2863 2864 ASSERT(session->s_server != NULL); 2865 sv = session->s_server; 2866 ll = &sv->sv_session_list; 2867 2868 smb_llist_flush(&session->s_tree_list); 2869 smb_llist_flush(&session->s_user_list); 2870 2871 smb_llist_enter(ll, RW_WRITER); 2872 smb_llist_remove(ll, session); 2873 count = ll->ll_count; 2874 smb_llist_exit(ll); 2875 2876 /* 2877 * Normally, the session should have state SHUTDOWN here. 2878 * If the session has any ofiles remaining, eg. due to 2879 * forgotten ofile references or something, the state 2880 * will be _DISCONNECTED or _TERMINATED. Keep such 2881 * sessions in the list of zombies (for debugging). 2882 */ 2883 if (session->s_state == SMB_SESSION_STATE_SHUTDOWN) { 2884 smb_session_delete(session); 2885 } else { 2886 cmn_err(CE_NOTE, "!Leaked session: 0x%p", (void *)session); 2887 DTRACE_PROBE1(new__zombie, smb_session_t *, session); 2888 smb_llist_enter(&smb_server_session_zombies, RW_WRITER); 2889 smb_llist_insert_head(&smb_server_session_zombies, session); 2890 smb_llist_exit(&smb_server_session_zombies); 2891 } 2892 2893 if (count == 0) { 2894 /* See smb_server_shutdown */ 2895 cv_signal(&sv->sv_cv); 2896 } 2897 } 2898